jedisct1/zig-uricrypt
Prefix-preserving, deterministic encryption for URIs.
A Zig library and CLI tool for prefix-preserving, deterministic URI encryption that maintains path hierarchy in encrypted form.
This library provides privacy-preserving URI encryption where URIs sharing the same prefix components produce ciphertexts with common prefixes. This property:
This is particularly useful for applications that need to:
encryptUri(allocator, uri, secret_key, context) ![]u8
Encrypts a URI using the provided secret key and context.
allocator
: Memory allocator for the encrypted outputuri
: URI to encrypt (e.g., "https://example.com/path"
or "/path/to/file"
)secret_key
: Secret key for encryption (any string)context
: Context string for domain separationReturns encrypted URI as allocated slice. Caller must free the result.
decryptUri(allocator, encrypted_uri, secret_key, context) ![]u8
Decrypts a previously encrypted URI.
allocator
: Memory allocator for the decrypted outputencrypted_uri
: Encrypted URI from encryptUri
secret_key
: Same secret key used for encryptioncontext
: Same context used for encryptionReturns original URI as allocated slice. Caller must free the result.
/
prefix for path-only URIsGiven these related URIs:
https://api.example.com/v1/users
https://api.example.com/v1/users/123
https://api.example.com/v1/users/123/profile
Their encrypted forms will share common prefixes:
YWJjZGVmZ2hpams=
YWJjZGVmZ2hpams=bG1ub3BxcnN0dXY=
YWJjZGVmZ2hpams=bG1ub3BxcnN0dXY=eHl6MDEyMzQ1Njc4OQ==
This allows you to:
/v1/users/
without decryptionconst encrypted = try uricrypt.encryptUri(
allocator,
"https://api.example.com/v1/users/123",
"api_key_123",
"production"
);
const encrypted = try uricrypt.encryptUri(
allocator,
"/uploads/2024/documents/report.pdf",
"file_storage_key",
"user_uploads"
);