std/compression/lib
std/compression/src/lib.trb
Compressed bytes: DEFLATE (RFC 1951) with Bytes.deflated and Bytes.inflated, gzip (RFC 1952) around it with
Bytes.gzipped and Bytes.gunzipped, and the Bytes.crc32 gzip checks a member with; and the two byte-oriented
block formats of the Snappy and LZ4 projects, Bytes.snappyCompressed with Bytes.snappyDecompressed and
Bytes.lz4BlockCompressed with Bytes.lz4BlockDecompressed. All of them are methods of Bytes, imported by the
name of the list they extend: use Buffer.gzipped from "std/compression". What a package archive of the registry is
compressed with (docs/design/RELEASE.md section 7.2), and what an HTTP body with Content-Encoding: gzip is.
Ordinary TorbScript over Bytes, with no native. Inflating reads every stream the format allows - stored,
fixed and dynamic blocks, and gzip members one after the other. Deflating is deterministic and simple: one block
of the fixed codes, with a greedy match search over the last 32 KiB. It compresses text to roughly half, where zlib's
dynamic codes get to a third; what it writes is the same for the same bytes on every machine, which is what a
reproducible archive needs, and any inflater reads it.
Snappy and LZ4 trade ratio for speed: literals and copies of whole bytes, no entropy coding and no checksum, which
is what the wire formats of MongoDB (Snappy) and Kafka (Snappy, LZ4) put around a message. Both write one block -
the frame formats come beside them - and both compressors are greedy and deterministic. A Snappy block holds the
length of what it decompresses to; an LZ4 block does not, so Bytes.lz4BlockDecompressed is told the largest output
it accepts.
Examples
use Buffer.gzipped, Buffer.gunzipped from "std/compression"
use Buffer.snappyCompressed, Buffer.snappyDecompressed from "std/compression"
const bytes = "hello, hello, hello".bytes()
const packed = bytes.gzipped()
print(packed.gunzipped() == Ok(bytes))
print(bytes.snappyCompressed().snappyDecompressed() == Ok(bytes))
extend Bytes
extend Bytes
The operations of the module, written where they are imported from: a member another package names is found in the
module of the package that is imported, so use Buffer.gzipped from "std/compression" needs them here.
fn inflated
fn inflated(): Result<Bytes, CompressionError>
Everything these bytes hold as a raw DEFLATE stream, which has to end with its last block.
fn deflated
fn deflated(): Bytes
These bytes as a raw DEFLATE stream: one final block of the fixed Huffman codes.
fn gzipped
fn gzipped(): Bytes
These bytes as one gzip member, with nothing in its header that depends on the machine or the moment: no file name, no time, the operating system "unknown". The same bytes give the same member everywhere.
fn gunzipped
fn gunzipped(): Result<Bytes, CompressionError>
What every gzip member of these bytes holds, one after the other. Each member's checksum and length are checked.
Errors
CompressionErrorwhere a header is not gzip's, a method is not DEFLATE, the DEFLATE stream is broken, or a checksum or a length does not match what was inflated.
fn snappyCompressed
fn snappyCompressed(): Bytes
These bytes as one Snappy block: the length of the bytes, then literals and copies. The same bytes give the same block everywhere.
Panics
When there are more than 4294967295 bytes, which is the most a Snappy block can say it holds.
fn snappyDecompressed
fn snappyDecompressed(): Result<Bytes, CompressionError>
The bytes of one Snappy block, which is the whole input. The length at its start has to be what the elements produce, and is checked before anything is allocated for it.
Errors
CompressionErrorwhere the input ends inside the length or an element, a copy has the offset 0 or reaches back before the start of the output, or the elements do not add up to the length the block starts with.
fn lz4BlockCompressed
fn lz4BlockCompressed(): Bytes
These bytes as one LZ4 block, with the end of block rules of the format kept: the last match starts at least 12 bytes before the end, and the last five bytes are literals. The same bytes give the same block everywhere.
fn lz4BlockDecompressed
fn lz4BlockDecompressed(maximumSize: Int): Result<Bytes, CompressionError>
The bytes of one LZ4 block, which is the whole input and holds no size of its own: maximumSize is the largest
output the caller accepts, and nothing is written past it.
Errors
CompressionErrorwhere the input ends inside a sequence, a match has the offset 0 or reaches back before the start of the output, the block does not end with literals, or the output would be larger thanmaximumSize.
fn crc32
fn crc32(): UInt32
The CRC-32 of ISO 3309 and ITU-T V.42 - the reflected polynomial 0xEDB88320 - of these bytes.