Safe by default
Ignore the BBP payload and the file is still a valid image with its redacted regions intact.
Open image format · BBP v1
BBP carries a useful, redacted image for everyone — then lets compliant viewers reveal individual regions only when they hold the right private keys.
Ignore the BBP payload and the file is still a valid image with its redacted regions intact.
Each face or region is an independent encrypted entity. The same file can reveal different regions to different viewers.
BBP adds a JUMBF payload to a normal image carrier. No special server or file extension is required.
Reference implementation
The complete example runs locally in your browser. Protect regions with X-Wing public keys, download a BBP image, and reveal it again with the matching private seed.
Publish locally
Draw regions over a photo, assign each one to a public key, and create a BBP-enabled image.
Demo image pre-loaded, or upload an image to replace it. The original stays in this browser tab.
Protect faces
Regions can be encrypted using a public key. Assign each region to the person who should be able to reveal it.
Recipients
These keys encrypt regions of the image. Keep each matching private seed with the intended viewer.
Publish
BBP keeps the base image in the format you choose. WebP, JPEG, and PNG export here; HEIF is already supported as a carrier by the reference library.
Open locally
Load an encrypted image, then reveal only the regions your private keys can open.
Demo image pre-loaded, or load a BBP-enabled image to inspect its safe base and encrypted regions.
Reveal locally
Load a private key to reveal the regions it can open. Keys stay in browser memory and are never uploaded.
The format
BBP is an additive image format. The normal image is the privacy floor; the encrypted payload is a capability layer for compliant viewers.
Payload = {
v: uint,
entities: [ Entity, ... ]
}
Entity = {
kind: "face" | "intersection",
body: bytes, // AEAD ciphertext
wraps: [ Wrap, ... ] // opaque recipients
}
// A compliant viewer paints every entity
// it can open over the safe base.Non-compliant viewers render the base and ignore the ancillary payload. Losing the BBP payload loses the reveal capability; it never exposes a hidden original.
The base still reveals the scene and the detected mosaic geometry. BBP protects the selected regions, not the existence of the photograph. A downloaded file is a frozen snapshot.
Carrier adapters
The payload is the same JUMBF superbox. Only the small binding that places it into the image changes.
Ancillary RIFF JUMB chunk. The default for the browser demo and a strong photo carrier.
Read · write · web exportBBP JUMBF payload in JPEG APP11 segments, with fragmentation for larger metadata.
Read · write · web exportPrivate ancillary bBPj chunk with a valid PNG CRC.
Read · write · web exportTop-level ISO BMFF uuid box. The carrier implementation exists in @brightblur/bbp.
Read · write · web readReference implementation
The implementation is deliberately split into a format package, a viewer element, and this small static app. Use the package directly or embed the viewer in an existing product.
@brightblur/bbpCBOR payloads, X-Wing recipient wraps, detection, and carrier embedding/extraction for WebP, JPEG, PNG, and HEIF.
<bbp-viewer>A framework-neutral custom element. Set src and privateKeys; the preview updates as keys change.
apps/bbp-previewThe page above is the runnable reference: local redaction, key assignment, export, and reveal with no server dependency.
A fully native macOS preview app reads ordinary and BBP image files, exposes the metadata inspector, and uses the same Rust crypto core.
import { bbpEncode } from '@brightblur/bbp';
import '@brightblur/bbp-viewer';
const bytes = await bbpEncode({
base: redactedImageBytes,
faces: [{ bbox, epoch: 0, pixels: crop, recipientPublicKey }],
intersections: []
});
viewer.src = bytes;
viewer.privateKeys = [privateKey];To add a carrier, preserve the same payload and implement the four boundary operations below. Then add the carrier to detection and the public dispatch. Keep the binding ancillary so ordinary decoders still render the safe base.
type CarrierAdapter = {
detect(bytes): boolean;
embed(base, jumbf): Uint8Array;
extract(file): Uint8Array | null;
strip(file): Uint8Array;
};packages/bbp/src/container.ts contains the carrier dispatch and the WebP, JPEG, PNG, and HEIF bindings. packages/bbp/src/encoder.ts assembles the CBOR payload; packages/bbp-viewer/src/index.ts performs local trial-decryption and composition.
The format document is the normative starting point. The current implementation is a reference for the draft, not a claim that the draft has completed its independent security audit or final test-vector freeze.