@sentropic/h2a 0.2.4 → 0.2.6

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,8 +1,26 @@
1
+ import { type SignOptions } from "./signature.js";
1
2
  import { type H2AEnvelope } from "./types.js";
2
3
  type CreateEnvelopeInput<TBody> = Omit<H2AEnvelope<TBody>, "protocol" | "version" | "createdAt"> & {
3
4
  createdAt?: string;
4
5
  };
5
6
  export declare function createEnvelope<TBody>(input: CreateEnvelopeInput<TBody>): H2AEnvelope<TBody>;
7
+ /**
8
+ * Sign an envelope's provenance (DEC-073). Returns a new envelope with the
9
+ * ed25519 signature appended to `signatures[]`; the original is not mutated.
10
+ * This is the "signed bearer" primitive underpinning authenticated transport
11
+ * (DEC-032): a recipient can verify *who* emitted an envelope independently of
12
+ * the channel it arrived on.
13
+ */
14
+ export declare function signEnvelope<TBody>(envelope: H2AEnvelope<TBody>, options: SignOptions): H2AEnvelope<TBody>;
15
+ /**
16
+ * Verify an envelope's signature(s) against a public key (DEC-073). With
17
+ * `options.by`, only that signer's signature(s) are checked; otherwise any
18
+ * signature that verifies against the key counts. Returns false when the
19
+ * envelope carries no (matching) signature.
20
+ */
21
+ export declare function verifyEnvelopeSignature<TBody>(envelope: H2AEnvelope<TBody>, publicKeyPem: string, options?: {
22
+ by?: string;
23
+ }): boolean;
6
24
  export declare function isH2AEnvelope<TBody = unknown>(value: unknown): value is H2AEnvelope<TBody>;
7
25
  export {};
8
26
  //# sourceMappingURL=envelope.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"envelope.d.ts","sourceRoot":"","sources":["../src/envelope.ts"],"names":[],"mappings":"AAAA,OAAO,EAML,KAAK,WAAW,EAEjB,MAAM,YAAY,CAAC;AAEpB,KAAK,mBAAmB,CAAC,KAAK,IAAI,IAAI,CACpC,WAAW,CAAC,KAAK,CAAC,EAClB,UAAU,GAAG,SAAS,GAAG,WAAW,CACrC,GAAG;IACF,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB,CAAC;AAwBF,wBAAgB,cAAc,CAAC,KAAK,EAClC,KAAK,EAAE,mBAAmB,CAAC,KAAK,CAAC,GAChC,WAAW,CAAC,KAAK,CAAC,CAOpB;AAED,wBAAgB,aAAa,CAAC,KAAK,GAAG,OAAO,EAC3C,KAAK,EAAE,OAAO,GACb,KAAK,IAAI,WAAW,CAAC,KAAK,CAAC,CAc7B"}
1
+ {"version":3,"file":"envelope.d.ts","sourceRoot":"","sources":["../src/envelope.ts"],"names":[],"mappings":"AAAA,OAAO,EAAkC,KAAK,WAAW,EAAE,MAAM,gBAAgB,CAAC;AAClF,OAAO,EAML,KAAK,WAAW,EAEjB,MAAM,YAAY,CAAC;AAEpB,KAAK,mBAAmB,CAAC,KAAK,IAAI,IAAI,CACpC,WAAW,CAAC,KAAK,CAAC,EAClB,UAAU,GAAG,SAAS,GAAG,WAAW,CACrC,GAAG;IACF,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB,CAAC;AAwBF,wBAAgB,cAAc,CAAC,KAAK,EAClC,KAAK,EAAE,mBAAmB,CAAC,KAAK,CAAC,GAChC,WAAW,CAAC,KAAK,CAAC,CAOpB;AAeD;;;;;;GAMG;AACH,wBAAgB,YAAY,CAAC,KAAK,EAChC,QAAQ,EAAE,WAAW,CAAC,KAAK,CAAC,EAC5B,OAAO,EAAE,WAAW,GACnB,WAAW,CAAC,KAAK,CAAC,CAMpB;AAED;;;;;GAKG;AACH,wBAAgB,uBAAuB,CAAC,KAAK,EAC3C,QAAQ,EAAE,WAAW,CAAC,KAAK,CAAC,EAC5B,YAAY,EAAE,MAAM,EACpB,OAAO,GAAE;IAAE,EAAE,CAAC,EAAE,MAAM,CAAA;CAAO,GAC5B,OAAO,CAUT;AAED,wBAAgB,aAAa,CAAC,KAAK,GAAG,OAAO,EAC3C,KAAK,EAAE,OAAO,GACb,KAAK,IAAI,WAAW,CAAC,KAAK,CAAC,CAc7B"}
package/dist/envelope.js CHANGED
@@ -1,3 +1,4 @@
1
+ import { signCanonical, verifyCanonical } from "./signature.js";
1
2
  import { H2A_ENVELOPE_TYPES, H2A_PROTOCOL, H2A_ROLES, H2A_VERSION } from "./types.js";
2
3
  function isRecord(value) {
3
4
  return typeof value === "object" && value !== null;
@@ -23,6 +24,47 @@ export function createEnvelope(input) {
23
24
  ...input
24
25
  };
25
26
  }
27
+ /**
28
+ * The portion of an envelope that a signature covers: everything except the
29
+ * `signatures` array itself. Excluding `signatures` makes the signed content
30
+ * stable, so multiple signers each sign the same provenance (DEC-073) — the
31
+ * same model as artifact signing (DEC-035).
32
+ */
33
+ function envelopeSigningView(envelope) {
34
+ const { signatures: _omit, ...rest } = envelope;
35
+ return rest;
36
+ }
37
+ /**
38
+ * Sign an envelope's provenance (DEC-073). Returns a new envelope with the
39
+ * ed25519 signature appended to `signatures[]`; the original is not mutated.
40
+ * This is the "signed bearer" primitive underpinning authenticated transport
41
+ * (DEC-032): a recipient can verify *who* emitted an envelope independently of
42
+ * the channel it arrived on.
43
+ */
44
+ export function signEnvelope(envelope, options) {
45
+ const signature = signCanonical(envelopeSigningView(envelope), options);
46
+ return {
47
+ ...envelope,
48
+ signatures: [...(envelope.signatures ?? []), signature]
49
+ };
50
+ }
51
+ /**
52
+ * Verify an envelope's signature(s) against a public key (DEC-073). With
53
+ * `options.by`, only that signer's signature(s) are checked; otherwise any
54
+ * signature that verifies against the key counts. Returns false when the
55
+ * envelope carries no (matching) signature.
56
+ */
57
+ export function verifyEnvelopeSignature(envelope, publicKeyPem, options = {}) {
58
+ const signatures = envelope.signatures ?? [];
59
+ const candidates = options.by
60
+ ? signatures.filter((s) => s.by === options.by)
61
+ : signatures;
62
+ if (candidates.length === 0) {
63
+ return false;
64
+ }
65
+ const view = envelopeSigningView(envelope);
66
+ return candidates.some((sig) => verifyCanonical(view, sig, publicKeyPem));
67
+ }
26
68
  export function isH2AEnvelope(value) {
27
69
  if (!isRecord(value)) {
28
70
  return false;
@@ -1 +1 @@
1
- {"version":3,"file":"envelope.js","sourceRoot":"","sources":["../src/envelope.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,kBAAkB,EAClB,YAAY,EACZ,SAAS,EACT,WAAW,EAIZ,MAAM,YAAY,CAAC;AASpB,SAAS,QAAQ,CAAC,KAAc;IAC9B,OAAO,OAAO,KAAK,KAAK,QAAQ,IAAI,KAAK,KAAK,IAAI,CAAC;AACrD,CAAC;AAED,SAAS,cAAc,CAAC,KAAc;IACpC,OAAO,OAAO,KAAK,KAAK,QAAQ,IAAI,kBAAkB,CAAC,QAAQ,CAAC,KAAwB,CAAC,CAAC;AAC5F,CAAC;AAED,SAAS,UAAU,CAAC,KAAc;IAChC,IAAI,CAAC,QAAQ,CAAC,KAAK,CAAC,EAAE,CAAC;QACrB,OAAO,KAAK,CAAC;IACf,CAAC;IAED,OAAO,CACL,OAAO,KAAK,CAAC,QAAQ,KAAK,QAAQ;QAClC,OAAO,KAAK,CAAC,KAAK,KAAK,QAAQ;QAC/B,OAAO,KAAK,CAAC,IAAI,KAAK,QAAQ;QAC9B,SAAS,CAAC,QAAQ,CAAC,KAAK,CAAC,IAA2B,CAAC;QACrD,CAAC,KAAK,CAAC,OAAO,KAAK,SAAS,IAAI,OAAO,KAAK,CAAC,OAAO,KAAK,QAAQ,CAAC,CACnE,CAAC;AACJ,CAAC;AAED,MAAM,UAAU,cAAc,CAC5B,KAAiC;IAEjC,OAAO;QACL,QAAQ,EAAE,YAAY;QACtB,OAAO,EAAE,WAAW;QACpB,SAAS,EAAE,KAAK,CAAC,SAAS,IAAI,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE;QACtD,GAAG,KAAK;KACT,CAAC;AACJ,CAAC;AAED,MAAM,UAAU,aAAa,CAC3B,KAAc;IAEd,IAAI,CAAC,QAAQ,CAAC,KAAK,CAAC,EAAE,CAAC;QACrB,OAAO,KAAK,CAAC;IACf,CAAC;IAED,OAAO,CACL,KAAK,CAAC,QAAQ,KAAK,YAAY;QAC/B,KAAK,CAAC,OAAO,KAAK,WAAW;QAC7B,OAAO,KAAK,CAAC,EAAE,KAAK,QAAQ;QAC5B,cAAc,CAAC,KAAK,CAAC,IAAI,CAAC;QAC1B,UAAU,CAAC,KAAK,CAAC,KAAK,CAAC;QACvB,MAAM,IAAI,KAAK;QACf,OAAO,KAAK,CAAC,SAAS,KAAK,QAAQ,CACpC,CAAC;AACJ,CAAC"}
1
+ {"version":3,"file":"envelope.js","sourceRoot":"","sources":["../src/envelope.ts"],"names":[],"mappings":"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"}
package/dist/index.d.ts CHANGED
@@ -14,7 +14,9 @@ export { H2A_OBLIGATION_CADENCES, H2A_RECURRING_OBLIGATION_CONFLICT_DISPOSITIONS
14
14
  export type { H2AObligationCadence, H2ARecurringObligationAuditResult, H2ARecurringObligationConflictDisposition, H2ARecurringObligationProfileDescriptor } from "./recurring-obligations.js";
15
15
  export { H2A_JURISDICTION_CONFLICT_DISPOSITIONS, H2A_JURISDICTION_KINDS, H2A_JURISDICTION_PROFILES, auditJurisdictionProfile, getJurisdictionProfile } from "./jurisdiction.js";
16
16
  export type { H2AJurisdictionAuditResult, H2AJurisdictionConflictDisposition, H2AJurisdictionKind, H2AJurisdictionProfileDescriptor } from "./jurisdiction.js";
17
- export { createEnvelope, isH2AEnvelope } from "./envelope.js";
17
+ export { createEnvelope, isH2AEnvelope, signEnvelope, verifyEnvelopeSignature } from "./envelope.js";
18
+ export { H2A_DEFAULT_MAX_AGE_MS, H2A_DEFAULT_MAX_SKEW_MS, checkEnvelopeFreshness, createReplayGuard } from "./replay.js";
19
+ export type { H2AFreshnessOptions, H2AReplayCheck, H2AReplayGuard, H2AReplayRejection } from "./replay.js";
18
20
  export { H2A_SESSION_DEFAULT_EXPIRY_MS, H2A_SESSION_DEFAULT_HEARTBEAT_INTERVAL_MS, H2A_SESSION_NOTIFICATION_TOPICS, H2A_SESSION_STATES, isH2ASession, isSessionExpired, pickFreshSessions } from "./session.js";
19
21
  export type { H2ASession, H2ASessionExpiryOptions, H2ASessionInterests, H2ASessionNotificationTopic, H2ASessionState } from "./session.js";
20
22
  export { H2A_HOST_BRIDGE_CLAUSES, H2A_HOST_BRIDGE_PROFILES, auditHostBridge, getHostBridgeProfile, listHostBridgeProfiles } from "./h2a-bridge.js";
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"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"}
package/dist/index.js CHANGED
@@ -6,7 +6,8 @@ export { H2A_DISCLOSURE_CONFLICT_DISPOSITIONS, H2A_DISCLOSURE_MODES, H2A_DISCLOS
6
6
  export { H2A_RECOURSE_CONFLICT_DISPOSITIONS, H2A_RECOURSE_PROFILES, H2A_RECOURSE_STATES, auditRecourseProfile, getRecourseProfile } from "./recourse.js";
7
7
  export { H2A_OBLIGATION_CADENCES, H2A_RECURRING_OBLIGATION_CONFLICT_DISPOSITIONS, H2A_RECURRING_OBLIGATION_PROFILES, auditRecurringObligationProfile, getRecurringObligationProfile } from "./recurring-obligations.js";
8
8
  export { H2A_JURISDICTION_CONFLICT_DISPOSITIONS, H2A_JURISDICTION_KINDS, H2A_JURISDICTION_PROFILES, auditJurisdictionProfile, getJurisdictionProfile } from "./jurisdiction.js";
9
- export { createEnvelope, isH2AEnvelope } from "./envelope.js";
9
+ export { createEnvelope, isH2AEnvelope, signEnvelope, verifyEnvelopeSignature } from "./envelope.js";
10
+ export { H2A_DEFAULT_MAX_AGE_MS, H2A_DEFAULT_MAX_SKEW_MS, checkEnvelopeFreshness, createReplayGuard } from "./replay.js";
10
11
  export { H2A_SESSION_DEFAULT_EXPIRY_MS, H2A_SESSION_DEFAULT_HEARTBEAT_INTERVAL_MS, H2A_SESSION_NOTIFICATION_TOPICS, H2A_SESSION_STATES, isH2ASession, isSessionExpired, pickFreshSessions } from "./session.js";
11
12
  export { H2A_HOST_BRIDGE_CLAUSES, H2A_HOST_BRIDGE_PROFILES, auditHostBridge, getHostBridgeProfile, listHostBridgeProfiles } from "./h2a-bridge.js";
12
13
  export { assertValidNegotiationState } from "./negotiation.js";
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,0BAA0B,EAC1B,iBAAiB,EACjB,sBAAsB,EACtB,0BAA0B,EAC1B,kBAAkB,EACnB,MAAM,UAAU,CAAC;AAWlB,OAAO,EACL,wBAAwB,EACxB,qBAAqB,EACrB,iBAAiB,EACjB,oBAAoB,EACrB,MAAM,kBAAkB,CAAC;AAU1B,OAAO,EACL,6BAA6B,EAC7B,8BAA8B,EAC9B,gCAAgC,EAChC,0BAA0B,EAC1B,2BAA2B,EAC5B,MAAM,0BAA0B,CAAC;AAOlC,OAAO,EACL,2CAA2C,EAC3C,8BAA8B,EAC9B,2BAA2B,EAC3B,4BAA4B,EAC5B,0BAA0B,EAC3B,MAAM,wBAAwB,CAAC;AAOhC,OAAO,EACL,oCAAoC,EACpC,oBAAoB,EACpB,uBAAuB,EACvB,sBAAsB,EACtB,oBAAoB,EACrB,MAAM,iBAAiB,CAAC;AAOzB,OAAO,EACL,kCAAkC,EAClC,qBAAqB,EACrB,mBAAmB,EACnB,oBAAoB,EACpB,kBAAkB,EACnB,MAAM,eAAe,CAAC;AAOvB,OAAO,EACL,uBAAuB,EACvB,8CAA8C,EAC9C,iCAAiC,EACjC,+BAA+B,EAC/B,6BAA6B,EAC9B,MAAM,4BAA4B,CAAC;AAOpC,OAAO,EACL,sCAAsC,EACtC,sBAAsB,EACtB,yBAAyB,EACzB,wBAAwB,EACxB,sBAAsB,EACvB,MAAM,mBAAmB,CAAC;AAO3B,OAAO,EACL,cAAc,EACd,aAAa,EACd,MAAM,eAAe,CAAC;AACvB,OAAO,EACL,6BAA6B,EAC7B,yCAAyC,EACzC,+BAA+B,EAC/B,kBAAkB,EAClB,YAAY,EACZ,gBAAgB,EAChB,iBAAiB,EAClB,MAAM,cAAc,CAAC;AAQtB,OAAO,EACL,uBAAuB,EACvB,wBAAwB,EACxB,eAAe,EACf,oBAAoB,EACpB,sBAAsB,EACvB,MAAM,iBAAiB,CAAC;AAYzB,OAAO,EAAE,2BAA2B,EAAE,MAAM,kBAAkB,CAAC;AAC/D,OAAO,EAAE,YAAY,EAAE,WAAW,EAAE,MAAM,gBAAgB,CAAC;AAC3D,OAAO,EAAE,aAAa,EAAE,eAAe,EAAE,MAAM,gBAAgB,CAAC;AAEhE,OAAO,EACL,kBAAkB,EAClB,kBAAkB,EAClB,6BAA6B,EAC7B,kBAAkB,EACnB,MAAM,cAAc,CAAC;AAMtB,OAAO,EACL,WAAW,EACX,WAAW,EACX,UAAU,EACV,iBAAiB,EACjB,YAAY,EACZ,SAAS,EACT,QAAQ,EACR,WAAW,EACZ,MAAM,gBAAgB,CAAC;AACxB,OAAO,EACL,oBAAoB,EACpB,yBAAyB,EACzB,mBAAmB,EACpB,MAAM,gBAAgB,CAAC;AACxB,OAAO,EACL,iCAAiC,EACjC,mCAAmC,EACnC,wBAAwB,EACxB,6BAA6B,EAC9B,MAAM,kBAAkB,CAAC;AAQ1B,OAAO,EACL,8BAA8B,EAC9B,uBAAuB,EACvB,8BAA8B,EAC9B,uBAAuB,EACxB,MAAM,iBAAiB,CAAC;AAUzB,OAAO,EAAE,sBAAsB,EAAE,MAAM,qBAAqB,CAAC;AAE7D,OAAO,EACL,0BAA0B,EAC1B,iBAAiB,EACjB,oBAAoB,EACpB,gBAAgB,EAChB,eAAe,EACf,uBAAuB,EACxB,MAAM,gBAAgB,CAAC;AAMxB,OAAO,EACL,kBAAkB,EAClB,mBAAmB,EACnB,kBAAkB,EAClB,sBAAsB,EACtB,yBAAyB,EACzB,YAAY,EACZ,SAAS,EACT,WAAW,EACZ,MAAM,YAAY,CAAC"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,56 @@
1
+ /**
2
+ * Anti-replay for signed envelopes (DEC-074), slice 2 of the signed-bearer
3
+ * transport-auth workstream (DEC-032 / DEC-073).
4
+ *
5
+ * A DEC-073 signature proves *who* emitted an envelope, but not that it is
6
+ * *fresh* — a validly signed envelope can be captured and re-sent. Replay
7
+ * protection adds two orthogonal checks:
8
+ *
9
+ * - **Freshness**: the envelope's `createdAt` must fall inside an accepted
10
+ * window `[now - maxAgeMs, now + maxSkewMs]` (skew tolerates clock drift on
11
+ * the emitter).
12
+ * - **Dedup**: the envelope's `id` must not have been accepted before. The
13
+ * `id` is part of the signed view (DEC-073), so a replayed envelope carries
14
+ * the same id and is rejected.
15
+ *
16
+ * Both are pure/in-memory — no I/O — so this lives in `@sentropic/h2a`. The
17
+ * channel that moves bytes is irrelevant; verification is end-to-end.
18
+ */
19
+ import type { H2AEnvelope } from "./types.js";
20
+ export declare const H2A_DEFAULT_MAX_AGE_MS = 300000;
21
+ export declare const H2A_DEFAULT_MAX_SKEW_MS = 60000;
22
+ export interface H2AFreshnessOptions {
23
+ /** Reference time (ms epoch). Defaults to `Date.now()`. */
24
+ now?: number;
25
+ /** How old an envelope may be before it is stale. Default 5 min. */
26
+ maxAgeMs?: number;
27
+ /** How far in the future `createdAt` may be (clock skew). Default 1 min. */
28
+ maxSkewMs?: number;
29
+ }
30
+ export type H2AReplayRejection = "invalid-timestamp" | "expired" | "future" | "replayed";
31
+ export interface H2AReplayCheck {
32
+ ok: boolean;
33
+ reason?: H2AReplayRejection;
34
+ }
35
+ /**
36
+ * Pure freshness check: is the envelope's `createdAt` within the accepted
37
+ * window? Does not consider dedup (that needs state — see {@link createReplayGuard}).
38
+ */
39
+ export declare function checkEnvelopeFreshness(envelope: H2AEnvelope, options?: H2AFreshnessOptions): H2AReplayCheck;
40
+ export interface H2AReplayGuard {
41
+ /**
42
+ * Accept an envelope iff it is fresh AND its id has not been seen before.
43
+ * On success the id is remembered for the rest of its freshness window.
44
+ */
45
+ accept(envelope: H2AEnvelope, now?: number): H2AReplayCheck;
46
+ /** Number of remembered ids (after pruning). Mostly for tests/observability. */
47
+ size(): number;
48
+ }
49
+ /**
50
+ * Create an in-memory replay guard. It remembers accepted envelope ids until
51
+ * they fall out of the freshness window, so the set stays bounded: an id that
52
+ * could only be replayed *after* it has expired would be rejected by the
53
+ * freshness check anyway, so it is safe to forget.
54
+ */
55
+ export declare function createReplayGuard(options?: Pick<H2AFreshnessOptions, "maxAgeMs" | "maxSkewMs">): H2AReplayGuard;
56
+ //# sourceMappingURL=replay.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"replay.d.ts","sourceRoot":"","sources":["../src/replay.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;GAiBG;AAEH,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,YAAY,CAAC;AAE9C,eAAO,MAAM,sBAAsB,SAAU,CAAC;AAC9C,eAAO,MAAM,uBAAuB,QAAS,CAAC;AAE9C,MAAM,WAAW,mBAAmB;IAClC,2DAA2D;IAC3D,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,oEAAoE;IACpE,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,4EAA4E;IAC5E,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB;AAED,MAAM,MAAM,kBAAkB,GAAG,mBAAmB,GAAG,SAAS,GAAG,QAAQ,GAAG,UAAU,CAAC;AAEzF,MAAM,WAAW,cAAc;IAC7B,EAAE,EAAE,OAAO,CAAC;IACZ,MAAM,CAAC,EAAE,kBAAkB,CAAC;CAC7B;AAED;;;GAGG;AACH,wBAAgB,sBAAsB,CACpC,QAAQ,EAAE,WAAW,EACrB,OAAO,GAAE,mBAAwB,GAChC,cAAc,CAgBhB;AAED,MAAM,WAAW,cAAc;IAC7B;;;OAGG;IACH,MAAM,CAAC,QAAQ,EAAE,WAAW,EAAE,GAAG,CAAC,EAAE,MAAM,GAAG,cAAc,CAAC;IAC5D,gFAAgF;IAChF,IAAI,IAAI,MAAM,CAAC;CAChB;AAED;;;;;GAKG;AACH,wBAAgB,iBAAiB,CAC/B,OAAO,GAAE,IAAI,CAAC,mBAAmB,EAAE,UAAU,GAAG,WAAW,CAAM,GAChE,cAAc,CAgChB"}
package/dist/replay.js ADDED
@@ -0,0 +1,79 @@
1
+ /**
2
+ * Anti-replay for signed envelopes (DEC-074), slice 2 of the signed-bearer
3
+ * transport-auth workstream (DEC-032 / DEC-073).
4
+ *
5
+ * A DEC-073 signature proves *who* emitted an envelope, but not that it is
6
+ * *fresh* — a validly signed envelope can be captured and re-sent. Replay
7
+ * protection adds two orthogonal checks:
8
+ *
9
+ * - **Freshness**: the envelope's `createdAt` must fall inside an accepted
10
+ * window `[now - maxAgeMs, now + maxSkewMs]` (skew tolerates clock drift on
11
+ * the emitter).
12
+ * - **Dedup**: the envelope's `id` must not have been accepted before. The
13
+ * `id` is part of the signed view (DEC-073), so a replayed envelope carries
14
+ * the same id and is rejected.
15
+ *
16
+ * Both are pure/in-memory — no I/O — so this lives in `@sentropic/h2a`. The
17
+ * channel that moves bytes is irrelevant; verification is end-to-end.
18
+ */
19
+ export const H2A_DEFAULT_MAX_AGE_MS = 300_000; // 5 minutes
20
+ export const H2A_DEFAULT_MAX_SKEW_MS = 60_000; // 1 minute clock skew
21
+ /**
22
+ * Pure freshness check: is the envelope's `createdAt` within the accepted
23
+ * window? Does not consider dedup (that needs state — see {@link createReplayGuard}).
24
+ */
25
+ export function checkEnvelopeFreshness(envelope, options = {}) {
26
+ const now = options.now ?? Date.now();
27
+ const maxAgeMs = options.maxAgeMs ?? H2A_DEFAULT_MAX_AGE_MS;
28
+ const maxSkewMs = options.maxSkewMs ?? H2A_DEFAULT_MAX_SKEW_MS;
29
+ const created = Date.parse(envelope.createdAt);
30
+ if (Number.isNaN(created)) {
31
+ return { ok: false, reason: "invalid-timestamp" };
32
+ }
33
+ if (created > now + maxSkewMs) {
34
+ return { ok: false, reason: "future" };
35
+ }
36
+ if (created < now - maxAgeMs) {
37
+ return { ok: false, reason: "expired" };
38
+ }
39
+ return { ok: true };
40
+ }
41
+ /**
42
+ * Create an in-memory replay guard. It remembers accepted envelope ids until
43
+ * they fall out of the freshness window, so the set stays bounded: an id that
44
+ * could only be replayed *after* it has expired would be rejected by the
45
+ * freshness check anyway, so it is safe to forget.
46
+ */
47
+ export function createReplayGuard(options = {}) {
48
+ const maxAgeMs = options.maxAgeMs ?? H2A_DEFAULT_MAX_AGE_MS;
49
+ const maxSkewMs = options.maxSkewMs ?? H2A_DEFAULT_MAX_SKEW_MS;
50
+ // id -> the createdAt (ms) we accepted it at, for window-based pruning.
51
+ const seen = new Map();
52
+ function prune(now) {
53
+ for (const [id, created] of seen) {
54
+ if (created < now - maxAgeMs)
55
+ seen.delete(id);
56
+ }
57
+ }
58
+ return {
59
+ accept(envelope, now = Date.now()) {
60
+ const freshness = checkEnvelopeFreshness(envelope, {
61
+ now,
62
+ maxAgeMs,
63
+ maxSkewMs
64
+ });
65
+ if (!freshness.ok)
66
+ return freshness;
67
+ prune(now);
68
+ if (seen.has(envelope.id)) {
69
+ return { ok: false, reason: "replayed" };
70
+ }
71
+ seen.set(envelope.id, Date.parse(envelope.createdAt));
72
+ return { ok: true };
73
+ },
74
+ size() {
75
+ return seen.size;
76
+ }
77
+ };
78
+ }
79
+ //# sourceMappingURL=replay.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"replay.js","sourceRoot":"","sources":["../src/replay.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;GAiBG;AAIH,MAAM,CAAC,MAAM,sBAAsB,GAAG,OAAO,CAAC,CAAC,YAAY;AAC3D,MAAM,CAAC,MAAM,uBAAuB,GAAG,MAAM,CAAC,CAAC,sBAAsB;AAkBrE;;;GAGG;AACH,MAAM,UAAU,sBAAsB,CACpC,QAAqB,EACrB,UAA+B,EAAE;IAEjC,MAAM,GAAG,GAAG,OAAO,CAAC,GAAG,IAAI,IAAI,CAAC,GAAG,EAAE,CAAC;IACtC,MAAM,QAAQ,GAAG,OAAO,CAAC,QAAQ,IAAI,sBAAsB,CAAC;IAC5D,MAAM,SAAS,GAAG,OAAO,CAAC,SAAS,IAAI,uBAAuB,CAAC;IAE/D,MAAM,OAAO,GAAG,IAAI,CAAC,KAAK,CAAC,QAAQ,CAAC,SAAS,CAAC,CAAC;IAC/C,IAAI,MAAM,CAAC,KAAK,CAAC,OAAO,CAAC,EAAE,CAAC;QAC1B,OAAO,EAAE,EAAE,EAAE,KAAK,EAAE,MAAM,EAAE,mBAAmB,EAAE,CAAC;IACpD,CAAC;IACD,IAAI,OAAO,GAAG,GAAG,GAAG,SAAS,EAAE,CAAC;QAC9B,OAAO,EAAE,EAAE,EAAE,KAAK,EAAE,MAAM,EAAE,QAAQ,EAAE,CAAC;IACzC,CAAC;IACD,IAAI,OAAO,GAAG,GAAG,GAAG,QAAQ,EAAE,CAAC;QAC7B,OAAO,EAAE,EAAE,EAAE,KAAK,EAAE,MAAM,EAAE,SAAS,EAAE,CAAC;IAC1C,CAAC;IACD,OAAO,EAAE,EAAE,EAAE,IAAI,EAAE,CAAC;AACtB,CAAC;AAYD;;;;;GAKG;AACH,MAAM,UAAU,iBAAiB,CAC/B,UAA+D,EAAE;IAEjE,MAAM,QAAQ,GAAG,OAAO,CAAC,QAAQ,IAAI,sBAAsB,CAAC;IAC5D,MAAM,SAAS,GAAG,OAAO,CAAC,SAAS,IAAI,uBAAuB,CAAC;IAC/D,wEAAwE;IACxE,MAAM,IAAI,GAAG,IAAI,GAAG,EAAkB,CAAC;IAEvC,SAAS,KAAK,CAAC,GAAW;QACxB,KAAK,MAAM,CAAC,EAAE,EAAE,OAAO,CAAC,IAAI,IAAI,EAAE,CAAC;YACjC,IAAI,OAAO,GAAG,GAAG,GAAG,QAAQ;gBAAE,IAAI,CAAC,MAAM,CAAC,EAAE,CAAC,CAAC;QAChD,CAAC;IACH,CAAC;IAED,OAAO;QACL,MAAM,CAAC,QAAqB,EAAE,GAAG,GAAG,IAAI,CAAC,GAAG,EAAE;YAC5C,MAAM,SAAS,GAAG,sBAAsB,CAAC,QAAQ,EAAE;gBACjD,GAAG;gBACH,QAAQ;gBACR,SAAS;aACV,CAAC,CAAC;YACH,IAAI,CAAC,SAAS,CAAC,EAAE;gBAAE,OAAO,SAAS,CAAC;YAEpC,KAAK,CAAC,GAAG,CAAC,CAAC;YACX,IAAI,IAAI,CAAC,GAAG,CAAC,QAAQ,CAAC,EAAE,CAAC,EAAE,CAAC;gBAC1B,OAAO,EAAE,EAAE,EAAE,KAAK,EAAE,MAAM,EAAE,UAAU,EAAE,CAAC;YAC3C,CAAC;YACD,IAAI,CAAC,GAAG,CAAC,QAAQ,CAAC,EAAE,EAAE,IAAI,CAAC,KAAK,CAAC,QAAQ,CAAC,SAAS,CAAC,CAAC,CAAC;YACtD,OAAO,EAAE,EAAE,EAAE,IAAI,EAAE,CAAC;QACtB,CAAC;QACD,IAAI;YACF,OAAO,IAAI,CAAC,IAAI,CAAC;QACnB,CAAC;KACF,CAAC;AACJ,CAAC"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@sentropic/h2a",
3
- "version": "0.2.4",
3
+ "version": "0.2.6",
4
4
  "description": "Core contracts and runtime primitives for human-to-agent coordination.",
5
5
  "license": "MIT",
6
6
  "type": "module",