CML
    Preparing search index...

    Module @svta/cml-c2pa

    C2PA (Coalition for Content Provenance and Authenticity) validation for BMFF/MP4 live video streams.

    @svta/cml-c2pa

    C2PA (Coalition for Content Provenance and Authenticity) live video validation for BMFF/MP4 containers.

    Supports the segment validation methods defined in the C2PA specification:

    • §19.3 Per-segment C2PA Manifest Box: each segment embeds a full C2PA manifest with COSE signature
    • §19.4 Verifiable Segment Info (VSI/EMSG): the init segment carries the manifest and session keys; each media segment carries a lightweight signed EMSG box
    • §15.12.2 / §18.6 VOD Merkle: for on-demand fragmented MP4 assets, the init manifest stores one Merkle tree row per track, and each media segment carries its own leaf hash and proof
    npm i @svta/cml-c2pa
    

    Note: @svta/cml-iso-bmff, @svta/cml-utils, and cbor-x are peer dependencies. Most package managers install them automatically, but you may need to add them explicitly.

    Note: This library uses the Web Crypto API (crypto.subtle) for COSE signature verification and BMFF hash computation. In Node.js 20+ this is available globally. In browsers, crypto.subtle requires a secure context (HTTPS or localhost).

    import { validateC2paManifestBoxSegment } from '@svta/cml-c2pa'
    import type { ManifestBoxValidationState } from '@svta/cml-c2pa'

    let lastManifestId: string | null = null
    let state: ManifestBoxValidationState | undefined

    for (const segmentUrl of segmentUrls) {
    const bytes = new Uint8Array(await fetch(segmentUrl).then(r => r.arrayBuffer()))
    const { result, nextManifestId, nextState } = await validateC2paManifestBoxSegment(
    bytes,
    lastManifestId,
    state,
    )
    lastManifestId = nextManifestId
    state = nextState

    console.log(result.isValid, result.errorCodes)
    }
    import { validateC2paInitSegment, validateC2paSegment } from '@svta/cml-c2pa'

    const initBytes = new Uint8Array(await fetch(initUrl).then(r => r.arrayBuffer()))
    const init = await validateC2paInitSegment(initBytes)

    const segmentBytes = new Uint8Array(await fetch(segmentUrl).then(r => r.arrayBuffer()))
    const validated = await validateC2paSegment(segmentBytes, init.sessionKeys)
    import { validateC2paInitSegment, validateC2paMerkleSegment } from '@svta/cml-c2pa'

    const initBytes = new Uint8Array(await fetch(initUrl).then(r => r.arrayBuffer()))
    const init = await validateC2paInitSegment(initBytes)

    const segmentBytes = new Uint8Array(await fetch(segmentUrl).then(r => r.arrayBuffer()))
    const { result } = await validateC2paMerkleSegment(segmentBytes, init.merkleMaps)

    Documents

    Manifest Box Validation
    VOD Merkle Validation
    Results and Error Codes
    VSI/EMSG Validation

    Enumerations

    C2paStatusCode
    LiveVideoStatusCode
    SequenceValidationReason

    Type Aliases

    BmffHashConstraint
    BmffHashExclusion
    C2paAssertion
    C2paManifest
    C2paSignatureInfo
    CoseKeyJwk
    InitSegmentValidation
    ManifestBoxContinuityValidator
    ManifestBoxValidationOptions
    ManifestBoxValidationResult
    ManifestBoxValidationState
    MerkleMap
    MerkleSegmentState
    MerkleSegmentValidation
    SegmentValidationResult
    SequenceState
    SequenceValidationResult
    ValidatedSessionKey

    Functions

    validateC2paInitSegment
    validateC2paManifestBoxSegment
    validateC2paMerkleSegment
    validateC2paSegment