Packages

Pure Elixir implementation to wrap binary data in uncompressed Snappy format

Current section

Files

Jump to
snappywrap lib snappywrap.ex
Raw

lib/snappywrap.ex

defmodule Snappywrap do
@moduledoc """
A pure Elixir library to wrap a binary as _uncompressed_ data in Snappy format.
This library _does not_ provide compress/decompress functions, but only wraps the data
in Snappy framing or block format that can be decompressed (decoded) by Snappy-compatible libraries.
This library is mostly for testing and/or low performance situations where using NIFs
such as [`snappyrex`](https://github.com/c2bw/snappyrex) is not required.
"""
@doc """
Wraps binary data in Snappy `framing` format.
Returns `{:ok, wrapped}` when the input is within the supported Snappy size
limit of `2^32 - 1` bytes, or `{:error, message}` when it is too large.
This function only accepts binaries. Passing any other type raises a
`FunctionClauseError`.
"""
@spec wrap_framed(binary) :: {:ok, binary} | {:error, String.t()}
def wrap_framed(data) when is_binary(data), do: data |> maybe_encode(&Snappywrap.Framing.encode/1)
@doc """
Wraps binary data in Snappy `block` format.
Returns `{:ok, wrapped}` when the input is within the supported Snappy size
limit of `2^32 - 1` bytes, or `{:error, message}` when it is too large.
This function only accepts binaries. Passing any other type raises a
`FunctionClauseError`.
"""
@spec wrap(binary) :: {:ok, binary} | {:error, String.t()}
def wrap(data) when is_binary(data), do: data |> maybe_encode(&Snappywrap.Block.encode/1)
defp maybe_encode(data, encode_fn) do
data
|> byte_size()
|> validate_input_size()
|> case do
:ok -> {:ok, encode_fn.(data)}
{:error, _message} = error -> error
end
end
@doc false
@spec validate_input_size(non_neg_integer()) :: :ok | {:error, String.t()}
def validate_input_size(data_bytes) when is_integer(data_bytes) and data_bytes >= 0 do
max_bytes = Snappywrap.Helper.input_max_bytes()
case data_bytes do
data_bytes when data_bytes > max_bytes -> {:error, "Input exceeds the maximum allowed size of #{max_bytes} bytes"}
_ -> :ok
end
end
end