#733: GZIPHelper.java

projectforge-business/src/main/java/org/projectforge/framework/utils/GZIPHelper.java Lines: 81 · Type: Java utility — org.projectforge.framework.utils 81 lines · 45 code · 30 comments · 6 blank

Purpose

Compresses and decompresses strings using GZIP + Base64 encoding. Solves two problems: (1) some database fields have limited character length (e.g. VARCHAR(4000)), and (2) storing large JSON blobs in database columns wastes space. This utility compresses the string with GZIP, then Base64-encodes the binary result so it can be stored as a plain string in a database VARCHAR or TEXT column. The decompression reverses the process: Base64 decode → GZIP decompress → original string.

Why Base64 after GZIP? GZIP produces binary bytes — not safe for storage in text-based database columns (which use character encodings like UTF-8 that may interpret certain byte values as control characters). Base64 converts binary data into a pure ASCII string (using 64 safe characters: A-Z, a-z, 0-9, +, /) — guaranteed safe for any text storage.

API — two methods

compress(String str) → String

Takes any string (null-safe — returns null for null/empty input). Wraps user preference XML, JSON configuration blobs, and large text fields for database storage. Algorithm:

  1. str.getBytes() — converts to platform-default charset bytes. Warning: uses the JVM's default charset (typically UTF-8 on modern systems but could be different on legacy setups). If the original string contains non-ASCII characters, different JVMs could produce different compressed results
  2. Wraps in GZIPOutputStream — the Java standard library GZIP implementation (RFC 1952)
  3. Closes the GZIP stream — this flushes the compressed data to the underlying ByteArrayOutputStream
  4. Encodes the compressed bytes to Base64 string via Base64Helper.encodeObject() — returns the Base64 string
Error handling: On IOException, logs the error at ERROR level and returns null. The caller must handle null — most callers treat null the same as empty string.

uncompress(String base64ByteArray) → String

Reverses compress(). Takes a Base64-encoded compressed string, returns the original. Algorithm:

  1. Base64Helper.decodeObject(base64ByteArray) — decodes Base64 to raw bytes (cast from Object to byte[] — note the unchecked cast. The decodeObject method returns Object for historical XStream compatibility)
  2. Wraps in GZIPInputStream — decompresses the GZIP data
  3. Uses IOUtils.copy(gzip, out) (Apache Commons IO) to stream decompressed data into a ByteArrayOutputStream
  4. out.toString() — converts bytes back to string using the platform default charset (same charset assumption as compress)
Error handling: Catches both IOException and ClassNotFoundException (the latter from Base64Helper.decodeObject() which uses Java object deserialization under the hood — a potential security issue if malicious Base64 data is passed). Returns null on any error.

Usage in ProjectForge

Used by two key components:

Notably, this is not used for the license key BLOB storage (LicenseDO) — binary files use direct JDBC BLOB columns, not text compression.

Key design decisions and gotchas