import { AsyncSessionManager, PeerSession } from '@bsv/sdk'; import { Knex } from 'knex'; export declare const AUTH_SESSION_TABLE = "auth_sessions"; export declare const AUTH_MESSAGE_NONCE_TABLE = "auth_message_nonces"; export declare const DEFAULT_AUTH_SESSION_TTL_MS: number; export declare const DEFAULT_AUTH_SESSION_TOUCH_INTERVAL_MS: number; export declare const DEFAULT_MAX_AUTH_MESSAGE_NONCES_PER_SESSION = 100000; export declare const DEFAULT_MAX_INITIAL_REQUEST_NONCES = 100000; export declare const DEFAULT_MAX_INITIAL_REQUEST_NONCES_PER_IDENTITY = 100000; export interface KnexSessionManagerOptions { /** Session lifetime since its most recent authenticated use. Default: 24 hours. */ ttlMs?: number; /** * Maximum time that an authenticated, timestamp-only session update may be * coalesced. Authentication and certificate state changes are always written * immediately. Default: 1 minute (or one quarter of ttlMs when shorter). */ touchIntervalMs?: number; /** Maximum one-time signed message nonces retained per active session. */ maxMessageNoncesPerSession?: number; /** Maximum unsigned initial-request replay claims retained across all identities. */ maxInitialRequestNonces?: number; /** * Maximum unsigned initial-request replay claims retained per identity. * The oldest claim is evicted at capacity so unauthenticated traffic cannot * permanently disable new handshakes. Default: 100,000. */ maxInitialRequestNoncesPerIdentity?: number; /** Testable clock source. Defaults to `Date.now`. */ now?: () => number; } /** * Shared BRC-103 session storage for horizontally scaled StorageServer nodes. * * Every instance must use the same Knex database. The wallet-toolbox migration * creates the required `auth_sessions` and `auth_message_nonces` tables. The * nonce table atomically rejects replay across replicas. Writes are monotonic * by `PeerSession.lastUpdate`, preventing a delayed request on one replica from * replacing newer session state written by another replica. */ export declare class KnexSessionManager implements AsyncSessionManager { private readonly knex; private readonly ttlMs; private readonly touchIntervalMs; private readonly maxMessageNoncesPerSession; private readonly maxInitialRequestNonces; private readonly maxInitialRequestNoncesPerIdentity; private readonly now; /** Rows associated with session objects returned by this manager. */ private readonly persistedRows; constructor(knex: Knex, options?: KnexSessionManagerOptions); addSession(session: PeerSession): Promise; updateSession(session: PeerSession): Promise; getSession(identifier: string): Promise; removeSession(session: PeerSession): Promise; hasSession(identifier: string): Promise; /** Atomically reject reuse of a signed BRC-103 message nonce across replicas. */ claimMessageNonce(sessionNonce: string, messageNonce: string): Promise; /** Atomically reject replayed unsigned initial requests across replicas. */ claimInitialRequestNonce(identityKey: string, initialNonce: string): Promise; /** Delete expired rows. Call from an operator-controlled maintenance task. */ pruneExpiredSessions(): Promise; private activeSessions; private evictOldestInitialRequestClaims; private persistSession; private validatePersistentSession; /** * Coalesce only the routine last-used write performed after an authenticated * general message. The WeakMap proves that this exact session object came * from a durable row read (or successful write) by this manager. Every * authentication/certificate transition and every unrecognized object still * takes the monotonic database path. */ private canCoalesceTouch; private sessionForRow; private updateIfCurrentOrNewer; private mergeNullableBoolean; private toTableAuthSession; private currentTime; } //# sourceMappingURL=KnexSessionManager.d.ts.map