Skip to content

micro509/der ​

DER reading and writing primitives.

The building blocks every other entrypoint is made of, for the cases the typed APIs do not cover:

Reading accepts definite lengths and minimal length encodings, rejects the high-tag-number form, and applies a nesting-depth guard capped at DEFAULT_MAX_DER_DEPTH. BER-only constructs fail.

Readers and decoders take untrusted bytes, so each one comes as a pair:

Writers take typed input and throw, matching encodeName and pemEncode.

All operations are synchronous.

DecodeDerErrorCode ​

Machine-readable failure reason for the DER readers and decoders.

ts
type DecodeDerErrorCode = malformed

DecodeDerFailure ​

Structured failure payload for DER reading and decoding.

ts
interface DecodeDerFailure extends Micro509Error<DecodeDerErrorCode> {
	readonly ok: false;
}

Properties

  • readonly ok: false — Always false for failures.

DecodeDerResult ​

Success-or-failure result from a DER reader or decoder.

ts
type DecodeDerResult<TValue> = {
  readonly ok: true;
  readonly value: TValue
} | ErrorResult<DecodeDerErrorCode, Record<never, never>, DecodeDerFailure>

decodeDerBitString ​

Decodes a BIT STRING element (tag 0x03) into a DerBitString.

Unused trailing bits are returned as encoded, with a violation of X.690 §11.2.1 reported through DerBitString.nonZeroPadding, since certificates in the wild carry them.

ts
function decodeDerBitString(
	element: DerElement,
): DecodeDerResult<DerBitString>

Parameters

decodeDerBitStringOrThrow ​

Decodes a BIT STRING element (tag 0x03) into a DerBitString.

Unused trailing bits are returned as encoded, with a violation of X.690 §11.2.1 reported through DerBitString.nonZeroPadding, since certificates in the wild carry them.

ts
function decodeDerBitStringOrThrow(
	element: DerElement,
): DerBitString

Parameters

Throws

  • if element is mis-tagged, or claims more than seven unused bits.

decodeDerBoolean ​

Decodes a BOOLEAN element (tag 0x01).

ts
function decodeDerBoolean(
	element: DerElement,
): DecodeDerResult<boolean>

Parameters

decodeDerBooleanOrThrow ​

Decodes a BOOLEAN element (tag 0x01).

ts
function decodeDerBooleanOrThrow(
	element: DerElement,
): boolean

Parameters

Throws

  • if element is mis-tagged, or holds anything but 0x00 or 0xff.

decodeDerInteger ​

Decodes an INTEGER element (tag 0x02) into a number.

ts
function decodeDerInteger(
	element: DerElement,
): DecodeDerResult<number>

Parameters

decodeDerIntegerOrThrow ​

Decodes an INTEGER element (tag 0x02) into a number.

ts
function decodeDerIntegerOrThrow(
	element: DerElement,
): number

Parameters

Throws

  • if element is mis-tagged, negative, non-minimally encoded, or exceeds Number.MAX_SAFE_INTEGER.

decodeDerOctetString ​

Decodes an OCTET STRING element (tag 0x04) into its payload bytes.

ts
function decodeDerOctetString(
	element: DerElement,
): DecodeDerResult<Uint8Array>

Parameters

decodeDerOctetStringOrThrow ​

Decodes an OCTET STRING element (tag 0x04) into its payload bytes.

ts
function decodeDerOctetStringOrThrow(
	element: DerElement,
): Uint8Array

Parameters

Throws

decodeDerOid ​

Decodes an OBJECT IDENTIFIER element (tag 0x06) into dotted-decimal form.

ts
function decodeDerOid(
	element: DerElement,
): DecodeDerResult<string>

Parameters

decodeDerOidOrThrow ​

Decodes an OBJECT IDENTIFIER element (tag 0x06) into dotted-decimal form.

ts
function decodeDerOidOrThrow(
	element: DerElement,
): string

Parameters

Throws

  • if element is mis-tagged, or holds a malformed sub-identifier.

decodeDerString ​

Decodes a string element into text, dispatching on its tag.

Supports UTF8String, PrintableString, IA5String, UniversalString, and BMPString.

ts
function decodeDerString(
	element: DerElement,
): DecodeDerResult<string>

Parameters

decodeDerStringOrThrow ​

Decodes a string element into text, dispatching on its tag.

Supports UTF8String, PrintableString, IA5String, UniversalString, and BMPString.

ts
function decodeDerStringOrThrow(
	element: DerElement,
): string

Parameters

Throws

  • on TeletexString, and on every other string tag.

decodeDerTime ​

Decodes a UTCTime (tag 0x17) or GeneralizedTime (tag 0x18) element into a Date.

ts
function decodeDerTime(
	element: DerElement,
): DecodeDerResult<Date>

Parameters

decodeDerTimeOrThrow ​

Decodes a UTCTime (tag 0x17) or GeneralizedTime (tag 0x18) element into a Date.

ts
function decodeDerTimeOrThrow(
	element: DerElement,
): Date

Parameters

Throws

  • if element carries any other tag, or a malformed time value.

derChildren ​

Reads the direct children of a constructed parent within source.

ts
function derChildren(
	source: Uint8Array,
	parent: DerElement,
): DecodeDerResult<DerElement[]>

Parameters

derChildrenOrThrow ​

Reads the direct children of a constructed parent within source.

ts
function derChildrenOrThrow(
	source: Uint8Array,
	parent: DerElement,
): DerElement[]

Parameters

Throws

  • if a child overflows parent, or data is left between the last child and its end.

readDerElement ​

Reads one TLV element from bytes starting at offset.

ts
function readDerElement(
	bytes: Uint8Array,
	offset: number,
): DecodeDerResult<DerElement>

Parameters

  • bytes: Uint8Array
  • offset: number — Byte position of the tag octet. Defaults to 0.

readDerElementOrThrow ​

Reads one TLV element from bytes starting at offset.

ts
function readDerElementOrThrow(
	bytes: Uint8Array,
	offset: number,
): DerElement

Parameters

  • bytes: Uint8Array
  • offset: number — Byte position of the tag octet. Defaults to 0.

Throws

  • if the element is truncated, indefinite-length, or non-minimally encoded.

readDerRoot ​

Reads the single top-level TLV element from bytes.

ts
function readDerRoot(
	bytes: Uint8Array,
	options?: ReadRootElementOptions,
): DecodeDerResult<DerElement>

Parameters

readDerRootOrThrow ​

Reads the single top-level TLV element from bytes.

ts
function readDerRootOrThrow(
	bytes: Uint8Array,
	options?: ReadRootElementOptions,
): DerElement

Parameters

Throws

  • if bytes carries trailing data, or nesting exceeds the depth guard.

readDerSequence ​

Reads a DER-encoded SEQUENCE from bytes and returns its direct children.

ts
function readDerSequence(
	bytes: Uint8Array,
	options?: ReadSequenceChildrenOptions,
): DecodeDerResult<DerElement[]>

Parameters

readDerSequenceOrThrow ​

Reads a DER-encoded SEQUENCE from bytes and returns its direct children.

ts
function readDerSequenceOrThrow(
	bytes: Uint8Array,
	options?: ReadSequenceChildrenOptions,
): DerElement[]

Parameters

Throws

  • if the root element is not a SEQUENCE, or if child boundaries are inconsistent.

DerBitString ​

A BIT STRING payload and the number of unused trailing bits in its final byte.

ts
interface DerBitString {
	readonly bytes: Uint8Array;
	readonly unusedBits: number;
	readonly nonZeroPadding: boolean;
}

Properties

  • readonly bytes: Uint8Array — Payload bytes, excluding the leading unused-bit count octet.
  • readonly unusedBits: number — Unused trailing bits in the final byte, 0 through 7.
  • readonly nonZeroPadding: boolean — true when the original encoding had non-zero padding bits (DER violation).

hexToBytes ​

Converts a hex string (even or odd length) to a Uint8Array. Odd-length strings are left-padded with a zero nibble.

ts
function hexToBytes(
	value: string,
): Uint8Array

Parameters

  • value: string

toHex ​

Converts raw bytes to a lowercase hex string with no separator.

ts
function toHex(
	bytes: Uint8Array,
): string

Parameters

  • bytes: Uint8Array

DerElement ​

A single parsed ASN.1 TLV element with byte-range metadata.

ts
interface DerElement {
	readonly tag: number;
	readonly headerLength: number;
	readonly length: number;
	readonly start: number;
	readonly end: number;
	readonly value: Uint8Array;
}

Properties

  • readonly tag: number — ASN.1 tag byte (e.g. 0x30 for SEQUENCE, 0x02 for INTEGER).
  • readonly headerLength: number — Number of bytes occupied by the tag + length octets.
  • readonly length: number — Byte length of the value portion (excluding tag and length octets).
  • readonly start: number — Byte offset where the value portion begins in the source buffer.
  • readonly end: number — Byte offset one past the last value byte. Equals the next element's header offset.
  • readonly value: Uint8Array — The raw value bytes (slice of the source buffer).

ReadRootElementOptions ​

Options for readRootElement.

ts
interface ReadRootElementOptions {
	readonly maxDepth?: number;
	readonly allowOpaqueConstructedTags?: readonly number[];
}

Properties

  • readonly maxDepth?: number — Maximum nesting depth for the DER depth check. @default DEFAULT_MAX_DER_DEPTH.
  • readonly allowOpaqueConstructedTags?: readonly number``[] — Constructed tags whose inner bytes may not parse as valid TLV children (e.g. opaque extension values).

ReadSequenceChildrenOptions ​

Options for readSequenceChildren.

ts
interface ReadSequenceChildrenOptions {
	readonly maxDepth?: number;
	readonly allowOpaqueConstructedTags?: readonly number[];
}

Properties

  • readonly maxDepth?: number — Maximum nesting depth for the DER depth check. @default DEFAULT_MAX_DER_DEPTH.
  • readonly allowOpaqueConstructedTags?: readonly number``[] — Constructed tags whose inner bytes may not parse as valid TLV children (e.g. opaque extension values).

assertDerMaxDepth ​

Walks the full DER tree rooted in bytes.

Constructed tags with content that cannot be parsed as valid children are tolerated when listed in allowOpaqueConstructedTags.

ts
function assertDerMaxDepth(
	bytes: Uint8Array,
	maxDepth: number,
	options?: {
  readonly allowOpaqueConstructedTags?: readonly number[]
},
): void

Parameters

  • bytes: Uint8Array
  • maxDepth: number
  • options?: { readonly allowOpaqueConstructedTags?: readonly number``[] }

Throws

derBitString ​

Encodes a DER BIT STRING (tag 0x03).

The value is prefixed with a single octet indicating how many trailing bits in the last byte are unused.

ts
function derBitString(
	value: Uint8Array,
	unusedBits: number,
): Uint8Array

Parameters

  • value: Uint8Array
  • unusedBits: number — Number of unused trailing bits (0–7). Defaults to 0.

derBmpString ​

Encodes a DER BMPString (tag 0x1e) as big-endian UTF-16.

ts
function derBmpString(
	value: string,
): Uint8Array

Parameters

  • value: string

Throws

  • on lone surrogates and on code points above the Basic Multilingual Plane.

derBoolean ​

Encodes a DER BOOLEAN (tag 0x01): true → 0xff, false → 0x00.

ts
function derBoolean(
	value: boolean,
): Uint8Array

Parameters

  • value: boolean

concatBytes ​

Concatenates multiple byte arrays into a single Uint8Array.

ts
function concatBytes(
	parts: readonly Uint8Array[],
): Uint8Array

Parameters

  • parts: readonly Uint8Array``[]

DEFAULT_MAX_DER_DEPTH ​

Maximum nesting depth allowed when recursively walking a DER structure.

Guards against stack exhaustion from pathologically nested input.

ts
const DEFAULT_MAX_DER_DEPTH: 64

derExplicitContext ​

Wraps a value in an explicit context-specific constructed tag (0xa0 + tag).

Used for optional SEQUENCE fields tagged with [tag] EXPLICIT.

ts
function derExplicitContext(
	tag: number,
	value: Uint8Array,
): Uint8Array

Parameters

  • tag: number
  • value: Uint8Array

derGeneralizedTime ​

Encodes a Date as a DER GeneralizedTime (tag 0x18), format YYYYMMDDHHMMSSZ.

Uses a four-digit year; required for dates outside the 1950–2049 range.

ts
function derGeneralizedTime(
	date: Date,
): Uint8Array

Parameters

  • date: Date

derIa5String ​

Encodes a DER IA5String (tag 0x16).

ts
function derIa5String(
	value: string,
): Uint8Array

Parameters

  • value: string

Throws

  • if the input contains any non-ASCII character (code point > 0x7f).

derImplicitConstructedContext ​

Wraps a value in an implicit context-specific constructed tag (0xa0 + tag).

Used for [tag] IMPLICIT fields whose underlying type is constructed (e.g. SEQUENCE).

ts
function derImplicitConstructedContext(
	tag: number,
	value: Uint8Array,
): Uint8Array

Parameters

  • tag: number
  • value: Uint8Array

derImplicitPrimitiveContext ​

Wraps a value in an implicit context-specific primitive tag (0x80 + tag).

Used for [tag] IMPLICIT fields whose underlying type is primitive (e.g. OCTET STRING).

ts
function derImplicitPrimitiveContext(
	tag: number,
	value: Uint8Array,
): Uint8Array

Parameters

  • tag: number
  • value: Uint8Array

derInteger ​

Encodes raw big-endian bytes as a DER INTEGER (tag 0x02).

Strips leading zero bytes for minimal encoding and prepends a zero byte when the high bit is set to keep the value non-negative.

ts
function derInteger(
	bytes: Uint8Array,
): Uint8Array

Parameters

  • bytes: Uint8Array

derIntegerFromNumber ​

Encodes a non-negative JavaScript number as a DER INTEGER.

ts
function derIntegerFromNumber(
	value: number,
): Uint8Array

Parameters

  • value: number

Throws

  • if the value is not a non-negative safe integer.

derNull ​

Produces a DER NULL element (tag 0x05, zero-length value).

ts
function derNull(): Uint8Array

derOid ​

Encodes a dotted-decimal OID string as a DER OBJECT IDENTIFIER (tag 0x06).

Validates arc constraints per X.660 §7.6: the root arc must be 0–2, and under roots 0 and 1 the second arc must be 0–39. X.690 §8.19.4 defines the (X*40)+Y packing of the first two arcs into one subidentifier.
Sub-identifiers are encoded with base-128 continuation.

ts
function derOid(
	oid: string,
): Uint8Array

Parameters

  • oid: string

derOctetString ​

Wraps raw bytes in an OCTET STRING element (tag 0x04).

ts
function derOctetString(
	value: Uint8Array,
): Uint8Array

Parameters

  • value: Uint8Array

derPrintableString ​

Encodes a DER PrintableString (tag 0x13).

ts
function derPrintableString(
	value: string,
): Uint8Array

Parameters

  • value: string

Throws

  • if the input contains characters outside the ITU-T X.680 §41.4 Table 10 PrintableString set.

derSequence ​

Wraps concatenated children in a SEQUENCE (tag 0x30).

ts
function derSequence(
	parts: readonly Uint8Array[],
): Uint8Array

Parameters

  • parts: readonly Uint8Array``[]

derSet ​

Wraps children in a SET (tag 0x31) after DER-sorting them lexicographically by encoded bytes, as required by X.690 DER.

ts
function derSet(
	parts: readonly Uint8Array[],
): Uint8Array

Parameters

  • parts: readonly Uint8Array``[]

derTime ​

Encodes a Date as the appropriate DER time type per RFC 5280.

  • utcTime for 1950–2049
  • generalizedTime otherwise
ts
function derTime(
	date: Date,
): Uint8Array

Parameters

  • date: Date

derTlv ​

Builds a complete DER TLV (tag-length-value) element:

  • one tag octet,
  • the DER-encoded length, then
  • the raw value bytes.
ts
function derTlv(
	tag: number,
	value: Uint8Array,
): Uint8Array

Parameters

  • tag: number
  • value: Uint8Array

derUniversalString ​

Encodes a DER UniversalString (tag 0x1c) as big-endian UTF-32.

ts
function derUniversalString(
	value: string,
): Uint8Array

Parameters

  • value: string

Throws

  • on lone surrogates.

derUtcTime ​

Encodes a Date as a DER UTCTime (tag 0x17), format YYMMDDHHMMSSZ.

Only the two-digit year is stored; suitable for dates in 1950–2049.

ts
function derUtcTime(
	date: Date,
): Uint8Array

Parameters

  • date: Date

derUtf8String ​

Encodes a DER UTF8String (tag 0x0c).

ts
function derUtf8String(
	value: string,
): Uint8Array

Parameters

  • value: string

Released under the MIT License.