@mikestools/usecompression
v0.0.2
Published
Vue 3 composables for browser-based gzip compression/decompression with reactive state and base64 encoding
Maintainers
Readme
@mikestools/usecompression
Vue 3 composables for browser-based compression/decompression using native CompressionStream/DecompressionStream APIs with reactive state. Supports gzip, deflate, and deflate-raw formats.
Features
- Multiple Formats - Gzip, Deflate, and Deflate-raw (ZIP-compatible) compression
- Separate Named Functions - No magic string parameters; each format has dedicated functions
- Reactive State - Vue 3 refs for processing state and errors
- Base64 Encoding - Encode/decode for localStorage compatibility
- Blob Utilities - Compress/decompress blobs and convert to/from data URLs
- Statistics - Track compression ratios and space savings
- Zero Dependencies - Uses native browser APIs only
- TypeScript - Full type safety with exported types
Installation
npm install @mikestools/usecompressionQuick Start
import { useCompression } from '@mikestools/usecompression'
const compression = useCompression()
// Compress text for localStorage using gzip
const result = await compression.compressGzipTextToBase64(JSON.stringify(largeData))
if (result.success) {
localStorage.setItem('data', result.data)
console.log(`Saved ${result.stats?.savings.toFixed(1)}% space`)
}
// Decompress from localStorage
const stored = localStorage.getItem('data')
if (stored) {
const restored = await compression.decompressGzipBase64ToText(stored)
if (restored.success) {
const data = JSON.parse(restored.data)
}
}
// Use grouped operations for cleaner code
const gzipResult = await compression.gzip.compressTextToBase64(text)
const deflateResult = await compression.deflate.compressTextToBase64(text)
const rawResult = await compression.deflateRaw.compressTextToBase64(text)
// Check state
if (compression.isProcessing.value) {
console.log('Operation in progress...')
}
if (compression.error.value) {
console.error(compression.error.value)
}useCompression
The main composable for compression operations with reactive state. Supports three formats:
- gzip - Standard gzip compression with header/trailer
- deflate - Deflate with zlib wrapper
- deflate-raw - Raw deflate without wrapper (ZIP-compatible)
Gzip Compression Methods
const compression = useCompression()
// Compress Uint8Array to Uint8Array
const result = await compression.compressGzip(data)
// Compress Uint8Array to base64 string
const result = await compression.compressGzipToBase64(data)
// Compress text to Uint8Array
const result = await compression.compressGzipText('Hello World!')
// Compress text to base64 (ideal for localStorage)
const result = await compression.compressGzipTextToBase64(jsonString)
// Compress Blob
const result = await compression.compressGzipBlob(blob)Gzip Decompression Methods
// Decompress to Uint8Array
const result = await compression.decompressGzip(compressedData)
// Decompress base64 to Uint8Array
const result = await compression.decompressGzipFromBase64(base64String)
// Decompress to text
const result = await compression.decompressGzipToText(compressedData)
// Decompress base64 to text (ideal for localStorage)
const result = await compression.decompressGzipBase64ToText(base64String)
// Decompress Blob
const result = await compression.decompressGzipBlob(compressedBlob)Deflate Methods
// All deflate methods follow the same pattern as gzip
const result = await compression.compressDeflate(data)
const result = await compression.compressDeflateToBase64(data)
const result = await compression.compressDeflateText(text)
const result = await compression.compressDeflateTextToBase64(text)
const result = await compression.compressDeflateBlob(blob)
const result = await compression.decompressDeflate(data)
const result = await compression.decompressDeflateFromBase64(base64)
const result = await compression.decompressDeflateToText(data)
const result = await compression.decompressDeflateBase64ToText(base64)
const result = await compression.decompressDeflateBlob(blob)Deflate-Raw Methods (ZIP-compatible)
// Raw deflate without zlib wrapper - used internally by ZIP files
const result = await compression.compressDeflateRaw(data)
const result = await compression.compressDeflateRawToBase64(data)
const result = await compression.compressDeflateRawText(text)
const result = await compression.compressDeflateRawTextToBase64(text)
const result = await compression.compressDeflateRawBlob(blob)
const result = await compression.decompressDeflateRaw(data)
const result = await compression.decompressDeflateRawFromBase64(base64)
const result = await compression.decompressDeflateRawToText(data)
const result = await compression.decompressDeflateRawBase64ToText(base64)
const result = await compression.decompressDeflateRawBlob(blob)Grouped Operations
For cleaner code, use the grouped operation namespaces:
const compression = useCompression()
// All formats have identical API through their namespaces
await compression.gzip.compress(data)
await compression.gzip.compressToBase64(data)
await compression.gzip.compressText(text)
await compression.gzip.compressTextToBase64(text)
await compression.gzip.compressBlob(blob)
await compression.gzip.decompress(data)
await compression.gzip.decompressFromBase64(base64)
await compression.gzip.decompressToText(data)
await compression.gzip.decompressBase64ToText(base64)
await compression.gzip.decompressBlob(blob)
// Same API for deflate and deflateRaw
await compression.deflate.compressTextToBase64(text)
await compression.deflateRaw.compressTextToBase64(text)Base64 Utilities
// Convert Uint8Array to base64
const base64 = compression.toBase64(data)
// Convert base64 to Uint8Array
const data = compression.fromBase64(base64)
// Extract base64 from data URL
const base64 = compression.dataUrlToBase64(dataUrl)
// Create data URL from base64
const dataUrl = compression.base64ToDataUrl(base64, 'text/plain')Blob Utilities
// Convert Blob to data URL
const dataUrl = await compression.blobToDataUrl(blob)
// Convert data URL to Blob
const blob = compression.dataUrlToBlob(dataUrl)Statistics
// Get compression statistics
const stats = compression.getStats(originalData, compressedData)
console.log(stats.originalSize) // Original size in bytes
console.log(stats.compressedSize) // Compressed size in bytes
console.log(stats.compressionRatio) // Ratio (original / compressed)
console.log(stats.savings) // Space saved as percentageReactive State
// Check if processing
console.log(compression.isProcessing.value) // boolean
// Check for errors
console.log(compression.error.value) // string | undefined
// Clear error
compression.clearError()Standalone Functions
All core functionality is available without Vue reactivity:
import {
// Gzip
compressBytesGzip,
decompressBytesGzip,
compressTextToBase64Gzip,
decompressBase64ToTextGzip,
compressBlobGzip,
decompressBlobGzip,
// Deflate
compressBytesDeflate,
decompressBytesDeflate,
compressTextToBase64Deflate,
decompressBase64ToTextDeflate,
compressBlobDeflate,
decompressBlobDeflate,
// Deflate-raw
compressBytesDeflateRaw,
decompressBytesDeflateRaw,
compressTextToBase64DeflateRaw,
decompressBase64ToTextDeflateRaw,
compressBlobDeflateRaw,
decompressBlobDeflateRaw,
// Utilities
toBase64,
fromBase64,
dataUrlToBase64,
base64ToDataUrl,
blobToDataUrl,
dataUrlToBlob,
getCompressionStats
} from '@mikestools/usecompression'
// Compress binary data with gzip
const compressed = await compressBytesGzip(data)
const decompressed = await decompressBytesGzip(compressed)
// Compress text for localStorage
const base64 = await compressTextToBase64Gzip(jsonString)
const text = await decompressBase64ToTextGzip(base64)
// Use deflate-raw for ZIP file content
const zipData = await compressBytesDeflateRaw(fileContent)
const original = await decompressBytesDeflateRaw(zipData)
// Base64 utilities
const base64 = toBase64(data)
const data = fromBase64(base64)
// Blob utilities
const dataUrl = await blobToDataUrl(blob)
const blob = dataUrlToBlob(dataUrl)
// Statistics
const stats = getCompressionStats(original, compressed)Types
All types are exported:
import type {
CompressionFormat,
CompressionStats,
CompressionResult,
CompressionState,
CompressionOperations,
UseCompressionReturn
} from '@mikestools/usecompression'Type Definitions
type CompressionFormat = 'gzip' | 'deflate' | 'deflate-raw'
interface CompressionStats {
readonly originalSize: number
readonly compressedSize: number
readonly compressionRatio: number
readonly savings: number
}
interface CompressionResult<T = Uint8Array> {
readonly success: boolean
readonly data?: T
readonly error?: string
readonly stats?: CompressionStats
}
interface CompressionState {
readonly isProcessing: Ref<boolean>
readonly error: Ref<string | undefined>
}
interface CompressionOperations {
compress(data: Uint8Array): Promise<CompressionResult<Uint8Array>>
compressToBase64(data: Uint8Array): Promise<CompressionResult<string>>
compressText(text: string): Promise<CompressionResult<Uint8Array>>
compressTextToBase64(text: string): Promise<CompressionResult<string>>
compressBlob(blob: Blob): Promise<CompressionResult<Blob>>
decompress(data: Uint8Array): Promise<CompressionResult<Uint8Array>>
decompressFromBase64(base64: string): Promise<CompressionResult<Uint8Array>>
decompressToText(data: Uint8Array): Promise<CompressionResult<string>>
decompressBase64ToText(base64: string): Promise<CompressionResult<string>>
decompressBlob(blob: Blob): Promise<CompressionResult<Blob>>
}Browser Support
Requires browsers with support for:
- CompressionStream/DecompressionStream (Chrome 80+, Firefox 113+, Safari 16.4+)
- TextEncoder/TextDecoder
- Blob, ArrayBuffer, Uint8Array
Use Cases
localStorage Compression
const compression = useCompression()
// Save compressed data
async function save(key: string, data: unknown) {
const json = JSON.stringify(data)
const result = await compression.compressGzipTextToBase64(json)
if (result.success) {
localStorage.setItem(key, result.data)
}
}
// Load compressed data
async function load<T>(key: string): Promise<T | undefined> {
const stored = localStorage.getItem(key)
if (!stored) return undefined
const result = await compression.decompressGzipBase64ToText(stored)
if (result.success) {
return JSON.parse(result.data) as T
}
return undefined
}File Compression
const compression = useCompression()
// Compress a file for download
async function compressFile(file: File): Promise<Blob> {
const result = await compression.compressGzipBlob(file)
if (result.success) {
return result.data
}
throw new Error(result.error)
}ZIP File Content (deflate-raw)
const compression = useCompression()
// Prepare file content for ZIP archive
async function prepareForZip(content: Uint8Array): Promise<Uint8Array> {
const result = await compression.compressDeflateRaw(content)
if (result.success) {
return result.data
}
throw new Error(result.error)
}
// Extract content from ZIP archive
async function extractFromZip(compressedContent: Uint8Array): Promise<Uint8Array> {
const result = await compression.decompressDeflateRaw(compressedContent)
if (result.success) {
return result.data
}
throw new Error(result.error)
}API Response Caching
const compression = useCompression()
// Cache API response
async function cacheResponse(key: string, response: unknown) {
const json = JSON.stringify(response)
const result = await compression.compressGzipTextToBase64(json)
if (result.success) {
sessionStorage.setItem(key, result.data)
console.log(`Cached with ${result.stats?.savings.toFixed(1)}% compression`)
}
}License
MIT
