# @suaveplan/cbor - RFC 8949 CBOR encoder/decoder + RFC 8742 sequences + RFC 9052 COSE bridge + RFC 8392 CWT + RFC 8610 CDDL — zero browser/Node deps ## Summary RFC 8949 (CBOR) encoder + decoder, RFC 8742 (CBOR Sequences), pull-style streaming decoder (`AsyncIterable` / `ReadableStream`), RFC 9052 §7 `COSE_Key` ↔ JWK round-trip + IANA algorithm bridge, deterministic-encoding shortcut, RFC 8949 §8 diagnostic notation, tag registry with IANA built-in handlers, and a strict §5.1 well-formedness predicate. Universal — runs unmodified in Bun, Node, Deno, and the browser. Zero browser/Node deps. > **Wave 1 status.** This package is the foundational codec layer. Larger > capabilities authored in the design proposal — > COSE structures (RFC 9052 §4–§6), CWT (RFC 8392), CDDL (RFC 8610), and the > `ChunkDecoder` partial-item streaming surface — are scoped IN and queued > as follow-up waves on top of this codec. ## Documentation tree - [ast](./src/cddl/ast.md) — Typed AST shapes per RFC 8610 §3 — the contract between the parser and the validator (and any future code generator). E… - [lexer](./src/cddl/lexer.md) — CDDL tokenizer per RFC 8610 §3 ABNF grammar. Reads a CDDL source string and emits a sequence of `Token` objects termina… - [parser](./src/cddl/parser.md) — CDDL parser per RFC 8610 §3 grammar. Consumes the token stream from the `tokenize` function and produces a typed AST (`… - [validate](./src/cddl/validate.md) — Walk a decoded CBOR value against a parsed CDDL schema and report the first mismatch (with a JSON-pointer-like path). T… - [alg-map](./src/cose/alg-map.md) — Bridge between IANA COSE Algorithm identifiers (`CoseAlg` literal strings or the equivalent numeric labels from RFC 905… - [cose-key](./src/cose/cose-key.md) — Decodes and encodes RFC 9052 §7 `COSE_Key` structures. The decoder maps an RFC-encoded CBOR map onto a typed discrimina… - [encrypt](./src/cose/encrypt.md) — `COSE_Encrypt` (RFC 9052 §5.1) — multi-recipient AEAD-encrypted COSE message in CBOR tag 96. Each recipient holds its o… - [encrypt0](./src/cose/encrypt0.md) — `COSE_Encrypt0` (RFC 9052 §5.2) — single-recipient AEAD-encrypted COSE message in CBOR tag 16. Wraps AES-256-GCM and Ch… - [headers](./src/cose/headers.md) — Typed `CoseHeader` map shape covering RFC 9052 §3.1 + IANA COSE Header Parameters (alg, crit, content type, kid, IV, Pa… - [jwk](./src/cose/jwk.md) — Round-trip converter between RFC 9052 `COSE_Key` instances and RFC 7517 JWK shapes. WebAuthn attestation flows often ne… - [mac](./src/cose/mac.md) — `COSE_Mac` (RFC 9052 §6.1) — multi-recipient MAC message in CBOR tag 97. Each recipient gets a wrapped copy of the cont… - [mac0](./src/cose/mac0.md) — `COSE_Mac0` (RFC 9052 §6.2) — single-recipient MAC message in CBOR tag 17. Used for symmetric-key authentication of CWT… - [sig-structure](./src/cose/sig-structure.md) — Builders for the canonical input to COSE signature, MAC, and AEAD computations per RFC 9052 §4.4 / §6.3 / §5.3. Every s… - [sign](./src/cose/sign.md) — `COSE_Sign` (RFC 9052 §4.1) — multi-signer COSE message in CBOR tag 98. Use when a payload needs to be co-signed by mul… - [sign1](./src/cose/sign1.md) — `COSE_Sign1` (RFC 9052 §4.2) — single-signer COSE message in CBOR tag 18. WebAuthn attestation, COSE-signed firmware, a… - [claims](./src/cwt/claims.md) — Encode and decode RFC 8392 CBOR Web Token claim sets. The seven IANA- registered claims (`iss`, `sub`, `aud`, `exp`, `n… - [verify](./src/cwt/verify.md) — End-to-end CWT verification: parse the COSE wrapper, verify the signature or MAC, decode the claim set, and check the s… - [decoder](./src/decoder/decoder.md) — _(no submodules)_ - half-float — Decodes 2 big-endian bytes representin… - [decoder](./src/decoder/decoder.md) — _(no submodules)_ - half-float — Decodes 2 big-endian bytes representin… - [half-float](./src/decoder/half-float.md) — Decodes 2 big-endian bytes representing IEEE 754 binary16 to a JavaScript `number`. The decoder is always available — n… - [well-formed](./src/decoder/well-formed.md) — `isWellFormed(bytes)` returns `true` iff `bytes` represent a single well-formed CBOR item per RFC 8949 §5.1. The functi… - [deterministic](./src/deterministic/deterministic.md) — _(no submodules)_ - [deterministic](./src/deterministic/deterministic.md) — _(no submodules)_ - [diagnostic](./src/diagnostic/diagnostic.md) — _(no submodules)_ - [diagnostic](./src/diagnostic/diagnostic.md) — _(no submodules)_ - [encoder](./src/encoder/encoder.md) — _(no submodules)_ - half-float — Encodes a JavaScript `number` as IEEE…… - [encoder](./src/encoder/encoder.md) — _(no submodules)_ - half-float — Encodes a JavaScript `number` as IEEE…… - [half-float](./src/encoder/half-float.md) — Encodes a JavaScript `number` as IEEE 754 binary16 (CBOR major 7 / value 25) when the round-trip is exact, and otherwis… - [errors](./src/errors/error-codes.md) — _(no submodules)_ - [error-codes](./src/errors/error-codes.md) — _(no submodules)_ - [sequences](./src/sequences/sequences.md) — _(no submodules)_ - [sequences](./src/sequences/sequences.md) — _(no submodules)_ - [chunk-decoder](./src/streaming/chunk-decoder.md) — Partial-item streaming decoder. While `PullDecoder` yields one whole CBOR item at a time (waiting until each item is fu… - [pull-decoder](./src/streaming/pull-decoder.md) — `PullDecoder` is a pull-style streaming decoder over an `AsyncIterable` or `ReadableStream`. Ea… - [builtin](./src/tags/builtin.md) — Provides `defaultTagHandlers()`, a `TagRegistry` populated with handlers for the most-used IANA-registered CBOR tags. C… - [registry](./src/tags/registry.md) — `TagRegistry` is the in-memory mutable container for CBOR tag handlers. The decoder consults a snapshot of the registry… - [tagged](./src/tags/tagged.md) — Provides the `Tagged` value object used by `@suaveplan/cbor` to materialise RFC 8949 §3.4 tagged items. The decoder… - half-float — Decodes 2 big-endian bytes representin… - [decoder](./src/decoder/decoder.md) — _(no submodules)_- half-float — Decodes 2 big-endian bytes representin… - [half-float](./src/decoder/half-float.md) — Decodes 2 big-endian bytes representing IEEE 754 binary16 to a JavaScript `number`. The decoder is always available — n… - [well-formed](./src/decoder/well-formed.md) — `isWellFormed(bytes)` returns `true` iff `bytes` represent a single well-formed CBOR item per RFC 8949 §5.1. The functi… - [deterministic](./src/deterministic/deterministic.md) — _(no submodules)_- [deterministic](./src/deterministic/deterministic.md) — _(no submodules)_- [diagnostic](./src/diagnostic/diagnostic.md) — _(no submodules)_- [diagnostic](./src/diagnostic/diagnostic.md) — _(no submodules)_- [encoder](./src/encoder/encoder.md) — _(no submodules)_- half-float — Encodes a JavaScript `number` as IEEE…… - [encoder](./src/encoder/encoder.md) — _(no submodules)_- half-float — Encodes a JavaScript `number` as IEEE…… - [half-float](./src/encoder/half-float.md) — Encodes a JavaScript `number` as IEEE 754 binary16 (CBOR major 7 / value 25) when the round-trip is exact, and otherwis… - [errors](./src/errors/error-codes.md) — _(no submodules)_- [error-codes](./src/errors/error-codes.md) — _(no submodules)_- [sequences](./src/sequences/sequences.md) — _(no submodules)_- [sequences](./src/sequences/sequences.md) — _(no submodules)_- [chunk-decoder](./src/streaming/chunk-decoder.md) — Partial-item streaming decoder. While `PullDecoder` yields one whole CBOR item at a time (waiting until each item is fu… - [pull-decoder](./src/streaming/pull-decoder.md) — `PullDecoder` is a pull-style streaming decoder over an `AsyncIterable` or `ReadableStream`. Ea… - [builtin](./src/tags/builtin.md) — Provides `defaultTagHandlers()`, a `TagRegistry` populated with handlers for the most-used IANA-registered CBOR tags. C… - [registry](./src/tags/registry.md) — `TagRegistry` is the in-memory mutable container for CBOR tag handlers. The decoder consults a snapshot of the registry… - [tagged](./src/tags/tagged.md) — Provides the `Tagged` value object used by `@suaveplan/cbor` to materialise RFC 8949 §3.4 tagged items. The decoder… - half-float — Decodes 2 big-endian bytes representin… - [decoder](./src/decoder/decoder.md) — _(no submodules)_- half-float — Decodes 2 big-endian bytes representin… - [half-float](./src/decoder/half-float.md) — Decodes 2 big-endian bytes representing IEEE 754 binary16 to a JavaScript `number`. The decoder is always available — n… - [well-formed](./src/decoder/well-formed.md) — `isWellFormed(bytes)` returns `true` iff `bytes` represent a single well-formed CBOR item per RFC 8949 §5.1. The functi… - [deterministic](./src/deterministic/deterministic.md) — _(no submodules)_- [deterministic](./src/deterministic/deterministic.md) — _(no submodules)_- [diagnostic](./src/diagnostic/diagnostic.md) — _(no submodules)_- [diagnostic](./src/diagnostic/diagnostic.md) — _(no submodules)_- [encoder](./src/encoder/encoder.md) — _(no submodules)_- half-float — Encodes a JavaScript `number` as IEEE…… - [encoder](./src/encoder/encoder.md) — _(no submodules)_- half-float — Encodes a JavaScript `number` as IEEE…… - [half-float](./src/encoder/half-float.md) — Encodes a JavaScript `number` as IEEE 754 binary16 (CBOR major 7 / value 25) when the round-trip is exact, and otherwis… - [errors](./src/errors/error-codes.md) — _(no submodules)_- [error-codes](./src/errors/error-codes.md) — _(no submodules)_- [sequences](./src/sequences/sequences.md) — _(no submodules)_- [sequences](./src/sequences/sequences.md) — _(no submodules)_- [chunk-decoder](./src/streaming/chunk-decoder.md) — Partial-item streaming decoder. While `PullDecoder` yields one whole CBOR item at a time (waiting until each item is fu… - [pull-decoder](./src/streaming/pull-decoder.md) — `PullDecoder` is a pull-style streaming decoder over an `AsyncIterable` or `ReadableStream`. Ea… - [builtin](./src/tags/builtin.md) — Provides `defaultTagHandlers()`, a `TagRegistry` populated with handlers for the most-used IANA-registered CBOR tags. C… - [registry](./src/tags/registry.md) — `TagRegistry` is the in-memory mutable container for CBOR tag handlers. The decoder consults a snapshot of the registry… - [tagged](./src/tags/tagged.md) — Provides the `Tagged` value object used by `@suaveplan/cbor` to materialise RFC 8949 §3.4 tagged items. The decoder… - half-float — Decodes 2 big-endian bytes representin… - [decoder](./src/decoder/decoder.md) — _(no submodules)_- half-float — Decodes 2 big-endian bytes representin… - [half-float](./src/decoder/half-float.md) — Decodes 2 big-endian bytes representing IEEE 754 binary16 to a JavaScript `number`. The decoder is always available — n… - [well-formed](./src/decoder/well-formed.md) — `isWellFormed(bytes)` returns `true` iff `bytes` represent a single well-formed CBOR item per RFC 8949 §5.1. The functi… - [deterministic](./src/deterministic/deterministic.md) — _(no submodules)_- [deterministic](./src/deterministic/deterministic.md) — _(no submodules)_- [diagnostic](./src/diagnostic/diagnostic.md) — _(no submodules)_- [diagnostic](./src/diagnostic/diagnostic.md) — _(no submodules)_- [encoder](./src/encoder/encoder.md) — _(no submodules)_- half-float — Encodes a JavaScript `number` as IEEE… - [encoder](./src/encoder/encoder.md) — _(no submodules)_- half-float — Encodes a JavaScript `number` as IEEE… - [half-float](./src/encoder/half-float.md) — Encodes a JavaScript `number` as IEEE 754 binary16 (CBOR major 7 / value 25) when the round-trip is exact, and otherwis… - [errors](./src/errors/error-codes.md) — _(no submodules)_- [error-codes](./src/errors/error-codes.md) — _(no submodules)_- [sequences](./src/sequences/sequences.md) — _(no submodules)_- [sequences](./src/sequences/sequences.md) — _(no submodules)_- [chunk-decoder](./src/streaming/chunk-decoder.md) — Partial-item streaming decoder. While `PullDecoder` yields one whole CBOR item at a time (waiting until each item is fu… - [pull-decoder](./src/streaming/pull-decoder.md) — `PullDecoder` is a pull-style streaming decoder over an `AsyncIterable` or `ReadableStream`. Ea… - [builtin](./src/tags/builtin.md) — Provides `defaultTagHandlers()`, a `TagRegistry` populated with handlers for the most-used IANA-registered CBOR tags. C… - [registry](./src/tags/registry.md) — `TagRegistry` is the in-memory mutable container for CBOR tag handlers. The decoder consults a snapshot of the registry… - [tagged](./src/tags/tagged.md) — Provides the `Tagged` value object used by `@suaveplan/cbor` to materialise RFC 8949 §3.4 tagged items. The decoder… - [decoder](./src/decoder/decoder.md) — _(no submodules)_- [half-float](./src/decoder/half-float.md) — Decodes 2 big-endian bytes representing IEEE 754 binary16 to a JavaScript `number`. The decoder is always available — n… - [well-formed](./src/decoder/well-formed.md) — `isWellFormed(bytes)` returns `true` iff `bytes` represent a single well-formed CBOR item per RFC 8949 §5.1. The functi… - [deterministic](./src/deterministic/deterministic.md) — _(no submodules)_ - [deterministic](./src/deterministic/deterministic.md) — _(no submodules)_- [diagnostic](./src/diagnostic/diagnostic.md) — _(no submodules)_ - [diagnostic](./src/diagnostic/diagnostic.md) — _(no submodules)_- [encoder](./src/encoder/encoder.md) — _(no submodules)_ - [encoder](./src/encoder/encoder.md) — _(no submodules)_ - [half-float](./src/encoder/half-float.md) — Encodes a JavaScript `number` as IEEE 754 binary16 (CBOR major 7 / value 25) when the round-trip is exact, and otherwis… - [errors](./src/errors/error-codes.md) — _(no submodules)_ - [error-codes](./src/errors/error-codes.md) — _(no submodules)_- [sequences](./src/sequences/sequences.md) — _(no submodules)_ - [sequences](./src/sequences/sequences.md) — _(no submodules)_- [chunk-decoder](./src/streaming/chunk-decoder.md) — Partial-item streaming decoder. While `PullDecoder` yields one whole CBOR item at a time (waiting until each item is fu… - [pull-decoder](./src/streaming/pull-decoder.md) — `PullDecoder` is a pull-style streaming decoder over an `AsyncIterable` or `ReadableStream`. Ea… - [builtin](./src/tags/builtin.md) — Provides `defaultTagHandlers()`, a `TagRegistry` populated with handlers for the most-used IANA-registered CBOR tags. C… - [registry](./src/tags/registry.md) — `TagRegistry` is the in-memory mutable container for CBOR tag handlers. The decoder consults a snapshot of the registry… - [tagged](./src/tags/tagged.md) — Provides the `Tagged` value object used by `@suaveplan/cbor` to materialise RFC 8949 §3.4 tagged items. The decoder… ## Install ```bash bun add @suaveplan/cbor ``` ## Quick Start ```ts import { encode, decode } from "@suaveplan/cbor"; const bytes = encode({ a: 1, b: [true, "two"] }); const value = decode(bytes); ``` ## Modules | Module | Doc | |---|---| | `encoder` | [`src/encoder/encoder.md`](src/encoder/encoder.md) | | `encoder/half-float` | [`src/encoder/half-float.md`](src/encoder/half-float.md) | | `decoder` | [`src/decoder/decoder.md`](src/decoder/decoder.md) | | `decoder/half-float` | [`src/decoder/half-float.md`](src/decoder/half-float.md) | | `decoder/well-formed` | [`src/decoder/well-formed.md`](src/decoder/well-formed.md) | | `streaming/pull-decoder` | [`src/streaming/pull-decoder.md`](src/streaming/pull-decoder.md) | | `deterministic` | [`src/deterministic/deterministic.md`](src/deterministic/deterministic.md) | | `diagnostic` | [`src/diagnostic/diagnostic.md`](src/diagnostic/diagnostic.md) | | `cose/cose-key` | [`src/cose/cose-key.md`](src/cose/cose-key.md) | | `cose/jwk` | [`src/cose/jwk.md`](src/cose/jwk.md) | | `cose/alg-map` | [`src/cose/alg-map.md`](src/cose/alg-map.md) | | `cose/headers` | [`src/cose/headers.md`](src/cose/headers.md) | | `cose/sig-structure` | [`src/cose/sig-structure.md`](src/cose/sig-structure.md) | | `cose/sign1` | [`src/cose/sign1.md`](src/cose/sign1.md) | | `cose/mac0` | [`src/cose/mac0.md`](src/cose/mac0.md) | | `cwt/claims` | [`src/cwt/claims.md`](src/cwt/claims.md) | | `cwt/verify` | [`src/cwt/verify.md`](src/cwt/verify.md) | | `streaming/chunk-decoder` | [`src/streaming/chunk-decoder.md`](src/streaming/chunk-decoder.md) | | `cose/sign` | [`src/cose/sign.md`](src/cose/sign.md) | | `cose/mac` | [`src/cose/mac.md`](src/cose/mac.md) | | `cose/encrypt0` | [`src/cose/encrypt0.md`](src/cose/encrypt0.md) | | `cose/encrypt` | [`src/cose/encrypt.md`](src/cose/encrypt.md) | | `tags/registry` | [`src/tags/registry.md`](src/tags/registry.md) | | `tags/tagged` | [`src/tags/tagged.md`](src/tags/tagged.md) | | `tags/builtin` | [`src/tags/builtin.md`](src/tags/builtin.md) | | `sequences` | [`src/sequences/sequences.md`](src/sequences/sequences.md) | | `errors` | [`src/errors/error-codes.md`](src/errors/error-codes.md) | ## Subpath exports - `@suaveplan/cbor` — root barrel: `encode`, `decode`, `Tagged`, error codes - `@suaveplan/cbor/encoder` — encoder + half-float - `@suaveplan/cbor/decoder` — decoder + half-float + `isWellFormed` - `@suaveplan/cbor/streaming` — `PullDecoder` over async-iterable / WHATWG streams - `@suaveplan/cbor/sequences` — RFC 8742 - `@suaveplan/cbor/deterministic` — `encodeDeterministic` shortcut for §4.2 - `@suaveplan/cbor/diagnostic` — RFC 8949 §8 notation emitter - `@suaveplan/cbor/cose` — `COSE_Key` ↔ JWK + IANA algorithm bridge (RFC 9052 §7), Sig_structure builders (§4.4 / §6.3 / §5.3), `COSE_Sign1` encode/decode/verify (§4.2, ES256/EdDSA), `COSE_Mac0` create/encode/decode/verify (§6.2, HS256/384/512) - `@suaveplan/cbor/cwt` — RFC 8392 CBOR Web Token claim encode/decode + `verifyCwtSign1` / `verifyCwtMac0` with time-window + audience + issuer validation - `@suaveplan/cbor/cddl` — RFC 8610 CDDL lexer + parser + AST + validator (primitive prelude, ranges, choices, arrays, maps, occurrence indicators, `.size`/`.regexp`/`.cbor` control operators, generics, named references) - `@suaveplan/cbor/tags` — `Tagged`, `TagRegistry`, `defaultTagHandlers` - `@suaveplan/cbor/errors` — `CBOR_CODES`, `CborError`, `CborErrorCode` ## Conformance - RFC 8949 §3.1 — major types 0–7 encode + decode - RFC 8949 §3.2 — indefinite-length text/byte strings, arrays, maps (decoder) - RFC 8949 §3.3 — IEEE 754 binary16 encode (opt-in) + decode (always-on) - RFC 8949 §3.4 — tagged-item registry - RFC 8949 §4.1 — preferred serialization (shortest-form integers always-on, shortest-exact float widths) - RFC 8949 §4.2 — deterministic-encoding profile (sorted map keys, no indefinite-length, half-float disabled in deterministic mode) - RFC 8949 §5.1 — strict-mode well-formedness; every malformed-input class raises `CborError(MALFORMED)` - RFC 8742 §2 + §3 — CBOR Sequences encode + decode + async-iterator stream