@adcp/sdk API Reference - v7.9.0
    Preparing search index...

    Interface IdempotencyBackend

    Storage backend interface. Swap implementations for memory, Postgres, Redis, etc.

    Keys are already composed as {principal}\u001f{key} (or with extra scope segments for per-session tools) before reaching the backend — backends don't need to know about scoping. The separator is U+001F (unit separator) rather than NUL because Postgres TEXT columns reject NUL bytes; either way the middleware's key-pattern validation (^[A-Za-z0-9_.:-]{16,255}$) guarantees the separator cannot appear in a legitimate key.

    Object-identity contract. Implementations MUST NOT return the same object reference on subsequent get calls — the middleware injects envelope fields (replayed: true, echo-back context) onto the returned value, and a shared reference would leak those mutations across requests. Implementations that store values by reference (e.g., memoryBackend) MUST deep-clone on read; implementations that serialize (e.g., pgBackend via JSON) get this for free.

    interface IdempotencyBackend {
        get(scopedKey: string): Promise<IdempotencyCacheEntry | null>;
        putIfAbsent(
            scopedKey: string,
            entry: IdempotencyCacheEntry,
        ): Promise<boolean>;
        put(scopedKey: string, entry: IdempotencyCacheEntry): Promise<void>;
        delete(scopedKey: string): Promise<void>;
        probe?(): Promise<void>;
        close?(): Promise<void>;
        clearAll?(): Promise<void>;
    }
    Index

    Methods

    • Atomically insert an entry only if no entry exists for scopedKey. Used as a claim step by the middleware to close the concurrent-miss race (two parallel requests with the same fresh key both seeing miss and both executing side effects). Returns true if the caller "won" the claim and should proceed to run the handler; false if another request claimed first (the caller should treat the result as a replay or conflict on re-check).

      Parameters

      Returns Promise<boolean>

    • Store an entry, overwriting any existing entry with the same scopedKey. Used by the middleware to replace the in-flight placeholder (written via putIfAbsent at claim time) with the final response after the handler completes.

      Parameters

      Returns Promise<void>

    • Delete an entry. Used by the middleware to release the claim when the handler fails — errors MUST NOT be cached, so the placeholder is rolled back on error so a retry can re-execute.

      Parameters

      • scopedKey: string

      Returns Promise<void>

    • Optional startup probe. Implementations that wrap an external store (e.g., pgBackend) should implement this to eagerly validate the connection before the server starts accepting traffic. Called by probeIdempotencyStore() and by serve() when readinessCheck is wired. Throws a descriptive error when the backend is unreachable or the required schema is missing.

      Returns Promise<void>

    • Optional hook for implementations that need to release resources (close pools, clear timers). Called by store.close().

      Returns Promise<void>

    • Optional test-harness hook that drops every cached entry without releasing backend resources. Used by AdcpServer.compliance.reset() between storyboards so idempotency cache hits from one storyboard don't replay into the next (shared brand domain, same key prefix).

      Production backends that can't cheaply flush everything (e.g., a shared Postgres cluster) should leave this undefined — the reset hook refuses to run when this method is missing unless the caller explicitly opts in with { force: true }.

      Returns Promise<void>