@enbox/dwn-sdk-js 0.3.3 → 0.3.5
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.
- package/dist/browser.mjs +8 -8
- package/dist/browser.mjs.map +3 -3
- package/dist/esm/generated/precompiled-validators.js +766 -1224
- package/dist/esm/generated/precompiled-validators.js.map +1 -1
- package/dist/esm/src/core/abstract-message.js +3 -3
- package/dist/esm/src/core/abstract-message.js.map +1 -1
- package/dist/esm/src/core/grant-authorization.js +6 -2
- package/dist/esm/src/core/grant-authorization.js.map +1 -1
- package/dist/esm/src/core/message.js +3 -3
- package/dist/esm/src/core/message.js.map +1 -1
- package/dist/esm/src/core/protocol-authorization-action.js +3 -3
- package/dist/esm/src/core/protocol-authorization-action.js.map +1 -1
- package/dist/esm/src/core/protocol-authorization-validation.js +1 -1
- package/dist/esm/src/core/protocol-authorization-validation.js.map +1 -1
- package/dist/esm/src/core/protocol-authorization.js +11 -11
- package/dist/esm/src/core/protocol-authorization.js.map +1 -1
- package/dist/esm/src/core/records-grant-authorization.js +1 -1
- package/dist/esm/src/core/records-grant-authorization.js.map +1 -1
- package/dist/esm/src/core/resumable-task-manager.js.map +1 -1
- package/dist/esm/src/dwn.js.map +1 -1
- package/dist/esm/src/event-stream/event-emitter-event-log.js +12 -12
- package/dist/esm/src/event-stream/event-emitter-event-log.js.map +1 -1
- package/dist/esm/src/handlers/messages-read.js +7 -7
- package/dist/esm/src/handlers/messages-read.js.map +1 -1
- package/dist/esm/src/handlers/messages-subscribe.js +1 -1
- package/dist/esm/src/handlers/messages-subscribe.js.map +1 -1
- package/dist/esm/src/handlers/messages-sync.js +18 -18
- package/dist/esm/src/handlers/messages-sync.js.map +1 -1
- package/dist/esm/src/handlers/protocols-configure.js +1 -1
- package/dist/esm/src/handlers/protocols-configure.js.map +1 -1
- package/dist/esm/src/handlers/protocols-query.js.map +1 -1
- package/dist/esm/src/handlers/records-count.js.map +1 -1
- package/dist/esm/src/handlers/records-delete.js.map +1 -1
- package/dist/esm/src/handlers/records-query.js.map +1 -1
- package/dist/esm/src/handlers/records-read.js +6 -6
- package/dist/esm/src/handlers/records-read.js.map +1 -1
- package/dist/esm/src/handlers/records-subscribe.js +1 -1
- package/dist/esm/src/handlers/records-subscribe.js.map +1 -1
- package/dist/esm/src/handlers/records-write.js +16 -16
- package/dist/esm/src/handlers/records-write.js.map +1 -1
- package/dist/esm/src/index.js +2 -2
- package/dist/esm/src/index.js.map +1 -1
- package/dist/esm/src/interfaces/protocols-configure.js +9 -9
- package/dist/esm/src/interfaces/protocols-configure.js.map +1 -1
- package/dist/esm/src/interfaces/records-delete.js.map +1 -1
- package/dist/esm/src/interfaces/records-write.js +8 -8
- package/dist/esm/src/interfaces/records-write.js.map +1 -1
- package/dist/esm/src/jose/jws/general/builder.js.map +1 -1
- package/dist/esm/src/jose/jws/general/verifier.js +30 -2
- package/dist/esm/src/jose/jws/general/verifier.js.map +1 -1
- package/dist/esm/src/protocols/permissions.js +1 -1
- package/dist/esm/src/protocols/permissions.js.map +1 -1
- package/dist/esm/src/smt/smt-store-level.js.map +1 -1
- package/dist/esm/src/smt/smt-store-memory.js.map +1 -1
- package/dist/esm/src/smt/sparse-merkle-tree.js +2 -2
- package/dist/esm/src/smt/sparse-merkle-tree.js.map +1 -1
- package/dist/esm/src/state-index/state-index-level.js.map +1 -1
- package/dist/esm/src/store/index-level-compound.js +10 -10
- package/dist/esm/src/store/index-level-compound.js.map +1 -1
- package/dist/esm/src/store/index-level.js +2 -2
- package/dist/esm/src/store/index-level.js.map +1 -1
- package/dist/esm/src/store/level-wrapper.js +1 -1
- package/dist/esm/src/store/level-wrapper.js.map +1 -1
- package/dist/esm/src/store/storage-controller.js +23 -10
- package/dist/esm/src/store/storage-controller.js.map +1 -1
- package/dist/esm/src/types/permission-types.js.map +1 -1
- package/dist/esm/src/utils/memory-cache.js.map +1 -1
- package/dist/esm/src/utils/messages.js +1 -1
- package/dist/esm/src/utils/messages.js.map +1 -1
- package/dist/esm/src/utils/object.js +1 -4
- package/dist/esm/src/utils/object.js.map +1 -1
- package/dist/esm/src/utils/private-key-signer.js.map +1 -1
- package/dist/esm/src/utils/records.js.map +1 -1
- package/dist/esm/tests/core/grant-authorization.spec.js +38 -0
- package/dist/esm/tests/core/grant-authorization.spec.js.map +1 -0
- package/dist/esm/tests/features/permissions.spec.js +1 -1
- package/dist/esm/tests/features/permissions.spec.js.map +1 -1
- package/dist/esm/tests/features/records-prune-cross-protocol.spec.js +422 -0
- package/dist/esm/tests/features/records-prune-cross-protocol.spec.js.map +1 -0
- package/dist/esm/tests/handlers/messages-subscribe.spec.js +3 -26
- package/dist/esm/tests/handlers/messages-subscribe.spec.js.map +1 -1
- package/dist/esm/tests/handlers/messages-sync.spec.js +3 -26
- package/dist/esm/tests/handlers/messages-sync.spec.js.map +1 -1
- package/dist/esm/tests/handlers/protocols-query.spec.js +4 -3
- package/dist/esm/tests/handlers/protocols-query.spec.js.map +1 -1
- package/dist/esm/tests/jose/jws/general.spec.js +115 -0
- package/dist/esm/tests/jose/jws/general.spec.js.map +1 -1
- package/dist/esm/tests/store/message-store.spec.js +15 -0
- package/dist/esm/tests/store/message-store.spec.js.map +1 -1
- package/dist/esm/tests/test-suite.js +2 -0
- package/dist/esm/tests/test-suite.js.map +1 -1
- package/dist/types/generated/precompiled-validators.d.ts.map +1 -1
- package/dist/types/src/core/abstract-message.d.ts +4 -4
- package/dist/types/src/core/abstract-message.d.ts.map +1 -1
- package/dist/types/src/core/grant-authorization.d.ts.map +1 -1
- package/dist/types/src/core/resumable-task-manager.d.ts +2 -2
- package/dist/types/src/core/resumable-task-manager.d.ts.map +1 -1
- package/dist/types/src/dwn.d.ts +12 -12
- package/dist/types/src/dwn.d.ts.map +1 -1
- package/dist/types/src/event-stream/event-emitter-event-log.d.ts +5 -5
- package/dist/types/src/event-stream/event-emitter-event-log.d.ts.map +1 -1
- package/dist/types/src/handlers/messages-read.d.ts +1 -1
- package/dist/types/src/handlers/messages-read.d.ts.map +1 -1
- package/dist/types/src/handlers/messages-subscribe.d.ts +1 -1
- package/dist/types/src/handlers/messages-subscribe.d.ts.map +1 -1
- package/dist/types/src/handlers/messages-sync.d.ts +1 -1
- package/dist/types/src/handlers/messages-sync.d.ts.map +1 -1
- package/dist/types/src/handlers/protocols-configure.d.ts +1 -1
- package/dist/types/src/handlers/protocols-configure.d.ts.map +1 -1
- package/dist/types/src/handlers/protocols-query.d.ts +1 -1
- package/dist/types/src/handlers/protocols-query.d.ts.map +1 -1
- package/dist/types/src/handlers/records-count.d.ts +1 -1
- package/dist/types/src/handlers/records-count.d.ts.map +1 -1
- package/dist/types/src/handlers/records-delete.d.ts +1 -1
- package/dist/types/src/handlers/records-delete.d.ts.map +1 -1
- package/dist/types/src/handlers/records-query.d.ts +1 -1
- package/dist/types/src/handlers/records-query.d.ts.map +1 -1
- package/dist/types/src/handlers/records-read.d.ts +1 -1
- package/dist/types/src/handlers/records-read.d.ts.map +1 -1
- package/dist/types/src/handlers/records-subscribe.d.ts +1 -1
- package/dist/types/src/handlers/records-subscribe.d.ts.map +1 -1
- package/dist/types/src/handlers/records-write.d.ts +1 -1
- package/dist/types/src/handlers/records-write.d.ts.map +1 -1
- package/dist/types/src/index.d.ts +5 -5
- package/dist/types/src/index.d.ts.map +1 -1
- package/dist/types/src/interfaces/records-write.d.ts +2 -2
- package/dist/types/src/interfaces/records-write.d.ts.map +1 -1
- package/dist/types/src/jose/jws/general/builder.d.ts +1 -1
- package/dist/types/src/jose/jws/general/builder.d.ts.map +1 -1
- package/dist/types/src/jose/jws/general/verifier.d.ts +13 -0
- package/dist/types/src/jose/jws/general/verifier.d.ts.map +1 -1
- package/dist/types/src/smt/smt-store-level.d.ts +1 -1
- package/dist/types/src/smt/smt-store-level.d.ts.map +1 -1
- package/dist/types/src/smt/smt-store-memory.d.ts +1 -1
- package/dist/types/src/smt/smt-store-memory.d.ts.map +1 -1
- package/dist/types/src/smt/sparse-merkle-tree.d.ts +1 -1
- package/dist/types/src/smt/sparse-merkle-tree.d.ts.map +1 -1
- package/dist/types/src/state-index/state-index-level.d.ts +3 -3
- package/dist/types/src/state-index/state-index-level.d.ts.map +1 -1
- package/dist/types/src/store/index-level.d.ts +2 -2
- package/dist/types/src/store/index-level.d.ts.map +1 -1
- package/dist/types/src/store/storage-controller.d.ts +19 -5
- package/dist/types/src/store/storage-controller.d.ts.map +1 -1
- package/dist/types/src/types/permission-types.d.ts +3 -4
- package/dist/types/src/types/permission-types.d.ts.map +1 -1
- package/dist/types/src/utils/memory-cache.d.ts +2 -2
- package/dist/types/src/utils/memory-cache.d.ts.map +1 -1
- package/dist/types/src/utils/object.d.ts.map +1 -1
- package/dist/types/src/utils/private-key-signer.d.ts +2 -2
- package/dist/types/src/utils/private-key-signer.d.ts.map +1 -1
- package/dist/types/tests/core/grant-authorization.spec.d.ts +2 -0
- package/dist/types/tests/core/grant-authorization.spec.d.ts.map +1 -0
- package/dist/types/tests/features/records-prune-cross-protocol.spec.d.ts +29 -0
- package/dist/types/tests/features/records-prune-cross-protocol.spec.d.ts.map +1 -0
- package/dist/types/tests/handlers/messages-subscribe.spec.d.ts.map +1 -1
- package/dist/types/tests/handlers/messages-sync.spec.d.ts.map +1 -1
- package/dist/types/tests/handlers/protocols-query.spec.d.ts.map +1 -1
- package/dist/types/tests/store/message-store.spec.d.ts.map +1 -1
- package/dist/types/tests/test-suite.d.ts.map +1 -1
- package/package.json +1 -1
- package/src/core/abstract-message.ts +8 -8
- package/src/core/grant-authorization.ts +9 -2
- package/src/core/message.ts +3 -3
- package/src/core/protocol-authorization-action.ts +3 -3
- package/src/core/protocol-authorization-validation.ts +9 -9
- package/src/core/protocol-authorization.ts +24 -24
- package/src/core/records-grant-authorization.ts +1 -1
- package/src/core/resumable-task-manager.ts +2 -2
- package/src/dwn.ts +13 -13
- package/src/event-stream/event-emitter-event-log.ts +15 -15
- package/src/handlers/messages-read.ts +7 -7
- package/src/handlers/messages-subscribe.ts +2 -2
- package/src/handlers/messages-sync.ts +19 -19
- package/src/handlers/protocols-configure.ts +2 -2
- package/src/handlers/protocols-query.ts +1 -1
- package/src/handlers/records-count.ts +1 -1
- package/src/handlers/records-delete.ts +1 -1
- package/src/handlers/records-query.ts +1 -1
- package/src/handlers/records-read.ts +6 -6
- package/src/handlers/records-subscribe.ts +2 -2
- package/src/handlers/records-write.ts +18 -18
- package/src/index.ts +5 -5
- package/src/interfaces/protocols-configure.ts +12 -12
- package/src/interfaces/records-delete.ts +1 -1
- package/src/interfaces/records-write.ts +11 -11
- package/src/jose/jws/general/builder.ts +1 -1
- package/src/jose/jws/general/verifier.ts +44 -3
- package/src/protocols/permissions.ts +1 -1
- package/src/smt/smt-store-level.ts +1 -1
- package/src/smt/smt-store-memory.ts +1 -1
- package/src/smt/sparse-merkle-tree.ts +10 -10
- package/src/state-index/state-index-level.ts +3 -3
- package/src/store/index-level-compound.ts +11 -11
- package/src/store/index-level.ts +4 -4
- package/src/store/level-wrapper.ts +1 -1
- package/src/store/storage-controller.ts +31 -16
- package/src/types/permission-types.ts +3 -4
- package/src/utils/memory-cache.ts +2 -2
- package/src/utils/messages.ts +2 -2
- package/src/utils/object.ts +1 -5
- package/src/utils/private-key-signer.ts +2 -2
- package/src/utils/records.ts +1 -1
|
@@ -3,8 +3,8 @@ import type { Cache } from '../types/cache.js';
|
|
|
3
3
|
* A cache using local memory.
|
|
4
4
|
*/
|
|
5
5
|
export declare class MemoryCache implements Cache {
|
|
6
|
-
private timeToLiveInSeconds;
|
|
7
|
-
private cache;
|
|
6
|
+
private readonly timeToLiveInSeconds;
|
|
7
|
+
private readonly cache;
|
|
8
8
|
/**
|
|
9
9
|
* @param timeToLiveInSeconds time-to-live for every key-value pair set in the cache
|
|
10
10
|
*/
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"memory-cache.d.ts","sourceRoot":"","sources":["../../../../src/utils/memory-cache.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,mBAAmB,CAAC;AAG/C;;GAEG;AACH,qBAAa,WAAY,YAAW,KAAK;IAMnB,OAAO,CAAC,mBAAmB;
|
|
1
|
+
{"version":3,"file":"memory-cache.d.ts","sourceRoot":"","sources":["../../../../src/utils/memory-cache.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,mBAAmB,CAAC;AAG/C;;GAEG;AACH,qBAAa,WAAY,YAAW,KAAK;IAMnB,OAAO,CAAC,QAAQ,CAAC,mBAAmB;IALxD,OAAO,CAAC,QAAQ,CAAC,KAAK,CAAwB;IAE9C;;OAEG;gBACkC,mBAAmB,EAAE,MAAM;IAO1D,GAAG,CAAC,GAAG,EAAE,MAAM,EAAE,KAAK,EAAE,GAAG,GAAG,OAAO,CAAC,IAAI,CAAC;IAQ3C,GAAG,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,GAAG,GAAG,SAAS,CAAC;CAGjD"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"object.d.ts","sourceRoot":"","sources":["../../../../src/utils/object.ts"],"names":[],"mappings":"AAAA;;GAEG;AACH,wBAAgB,aAAa,CAAC,GAAG,EAAE,OAAO,GAAG,OAAO,
|
|
1
|
+
{"version":3,"file":"object.d.ts","sourceRoot":"","sources":["../../../../src/utils/object.ts"],"names":[],"mappings":"AAAA;;GAEG;AACH,wBAAgB,aAAa,CAAC,GAAG,EAAE,OAAO,GAAG,OAAO,CAMnD;AAED;;GAEG;AACH,wBAAgB,kBAAkB,CAAC,GAAG,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,IAAI,CAWrE;AAED;;GAEG;AACH,wBAAgB,yBAAyB,CAAC,GAAG,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,IAAI,CAQ5E"}
|
|
@@ -23,8 +23,8 @@ export type PrivateKeySignerOptions = {
|
|
|
23
23
|
export declare class PrivateKeySigner implements MessageSigner {
|
|
24
24
|
keyId: string;
|
|
25
25
|
algorithm: string;
|
|
26
|
-
private privateJwk;
|
|
27
|
-
private signatureAlgorithm;
|
|
26
|
+
private readonly privateJwk;
|
|
27
|
+
private readonly signatureAlgorithm;
|
|
28
28
|
constructor(options: PrivateKeySignerOptions);
|
|
29
29
|
/**
|
|
30
30
|
* Signs the given content and returns the signature as bytes.
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"private-key-signer.d.ts","sourceRoot":"","sources":["../../../../src/utils/private-key-signer.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,oBAAoB,CAAC;AACxD,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,wBAAwB,CAAC;AAK5D;;GAEG;AACH,MAAM,MAAM,uBAAuB,GAAG;IACpC;;OAEG;IACH,UAAU,EAAE,aAAa,CAAC;IAE1B;;OAEG;IACH,KAAK,CAAC,EAAE,MAAM,CAAC;IAEf;;OAEG;IACH,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB,CAAC;AAEF;;GAEG;AACH,qBAAa,gBAAiB,YAAW,aAAa;IAC7C,KAAK,SAAC;IACN,SAAS,SAAC;IACjB,OAAO,CAAC,UAAU,CAAgB;
|
|
1
|
+
{"version":3,"file":"private-key-signer.d.ts","sourceRoot":"","sources":["../../../../src/utils/private-key-signer.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,oBAAoB,CAAC;AACxD,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,wBAAwB,CAAC;AAK5D;;GAEG;AACH,MAAM,MAAM,uBAAuB,GAAG;IACpC;;OAEG;IACH,UAAU,EAAE,aAAa,CAAC;IAE1B;;OAEG;IACH,KAAK,CAAC,EAAE,MAAM,CAAC;IAEf;;OAEG;IACH,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB,CAAC;AAEF;;GAEG;AACH,qBAAa,gBAAiB,YAAW,aAAa;IAC7C,KAAK,SAAC;IACN,SAAS,SAAC;IACjB,OAAO,CAAC,QAAQ,CAAC,UAAU,CAAgB;IAC3C,OAAO,CAAC,QAAQ,CAAC,kBAAkB,CAAC;gBAEjB,OAAO,EAAE,uBAAuB;IA8BnD;;OAEG;IACU,IAAI,CAAE,OAAO,EAAE,UAAU,GAAG,OAAO,CAAC,UAAU,CAAC;CAI7D"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"grant-authorization.spec.d.ts","sourceRoot":"","sources":["../../../../tests/core/grant-authorization.spec.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Regression tests for cross-protocol prune cascade — closes #298.
|
|
3
|
+
*
|
|
4
|
+
* Semantics (decision under #298):
|
|
5
|
+
* A `RecordsDelete` with `prune: true` cascades to every descendant of the
|
|
6
|
+
* pruned record, regardless of which protocol a descendant declares itself
|
|
7
|
+
* under. `parentContextId` is a structural link — pruning a parent removes
|
|
8
|
+
* the entire subtree it rooted. Cross-protocol composing children (records
|
|
9
|
+
* in a different protocol that reference the parent via `$ref` / `uses`)
|
|
10
|
+
* participate in the cascade on equal footing with same-protocol children.
|
|
11
|
+
*
|
|
12
|
+
* Rationale:
|
|
13
|
+
* - A DWN is tenant-owned storage. The tenant's prune authority extends
|
|
14
|
+
* across the whole subtree they rooted, so walking the `parentId` chain
|
|
15
|
+
* unconditionally is the correct semantic.
|
|
16
|
+
* - Preserving cross-protocol orphans creates a half-alive state — readable
|
|
17
|
+
* but not updatable, since `validateReferentialIntegrity` in the
|
|
18
|
+
* `RecordsWrite` handler rejects any write whose parent is missing —
|
|
19
|
+
* which is worse for callers than cascading.
|
|
20
|
+
* - Same-protocol descendants at arbitrary depth already cascade via
|
|
21
|
+
* `parentId` with no protocol filter; treating a cross-protocol hop
|
|
22
|
+
* specially was inconsistent.
|
|
23
|
+
*
|
|
24
|
+
* These tests install multiple protocols linked via `uses` + `$ref`, write
|
|
25
|
+
* records across protocol boundaries, and assert that the entire subtree —
|
|
26
|
+
* same protocol or cross protocol, at any depth — is fully purged on prune.
|
|
27
|
+
*/
|
|
28
|
+
export declare function testRecordsPruneCrossProtocol(): void;
|
|
29
|
+
//# sourceMappingURL=records-prune-cross-protocol.spec.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"records-prune-cross-protocol.spec.d.ts","sourceRoot":"","sources":["../../../../tests/features/records-prune-cross-protocol.spec.ts"],"names":[],"mappings":"AA8BA;;;;;;;;;;;;;;;;;;;;;;;;;;GA0BG;AACH,wBAAgB,6BAA6B,IAAI,IAAI,CAyfpD"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"messages-subscribe.spec.d.ts","sourceRoot":"","sources":["../../../../tests/handlers/messages-subscribe.spec.ts"],"names":[],"mappings":"AAsBA,wBAAgB,4BAA4B,IAAI,IAAI,
|
|
1
|
+
{"version":3,"file":"messages-subscribe.spec.d.ts","sourceRoot":"","sources":["../../../../tests/handlers/messages-subscribe.spec.ts"],"names":[],"mappings":"AAsBA,wBAAgB,4BAA4B,IAAI,IAAI,CAu6BnD"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"messages-sync.spec.d.ts","sourceRoot":"","sources":["../../../../tests/handlers/messages-sync.spec.ts"],"names":[],"mappings":"AAwBA,wBAAgB,uBAAuB,IAAI,IAAI,
|
|
1
|
+
{"version":3,"file":"messages-sync.spec.d.ts","sourceRoot":"","sources":["../../../../tests/handlers/messages-sync.spec.ts"],"names":[],"mappings":"AAwBA,wBAAgB,uBAAuB,IAAI,IAAI,CA8zB9C"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"protocols-query.spec.d.ts","sourceRoot":"","sources":["../../../../tests/handlers/protocols-query.spec.ts"],"names":[],"mappings":"AAwBA,wBAAgB,yBAAyB,IAAI,IAAI,
|
|
1
|
+
{"version":3,"file":"protocols-query.spec.d.ts","sourceRoot":"","sources":["../../../../tests/handlers/protocols-query.spec.ts"],"names":[],"mappings":"AAwBA,wBAAgB,yBAAyB,IAAI,IAAI,CA+gBhD"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"message-store.spec.d.ts","sourceRoot":"","sources":["../../../../tests/store/message-store.spec.ts"],"names":[],"mappings":"AAcA,wBAAgB,gBAAgB,IAAI,IAAI,
|
|
1
|
+
{"version":3,"file":"message-store.spec.d.ts","sourceRoot":"","sources":["../../../../tests/store/message-store.spec.ts"],"names":[],"mappings":"AAcA,wBAAgB,gBAAgB,IAAI,IAAI,CA8lBvC"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"test-suite.d.ts","sourceRoot":"","sources":["../../../tests/test-suite.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,SAAS,EAAE,QAAQ,EAAE,YAAY,EAAE,kBAAkB,EAAE,UAAU,EAAE,MAAM,iBAAiB,CAAC;
|
|
1
|
+
{"version":3,"file":"test-suite.d.ts","sourceRoot":"","sources":["../../../tests/test-suite.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,SAAS,EAAE,QAAQ,EAAE,YAAY,EAAE,kBAAkB,EAAE,UAAU,EAAE,MAAM,iBAAiB,CAAC;AAwCzG;;GAEG;AACH,qBAAa,SAAS;IAEpB;;;OAGG;WACW,2BAA2B,CAAC,SAAS,CAAC,EAAE;QACpD,YAAY,CAAC,EAAE,YAAY,CAAC;QAC5B,SAAS,CAAC,EAAE,SAAS,CAAC;QACtB,UAAU,CAAC,EAAE,UAAU,CAAC;QACxB,QAAQ,CAAC,EAAE,QAAQ,CAAC;QACpB,kBAAkB,CAAC,EAAE,kBAAkB,CAAC;KACzC,GAAG,IAAI;CA+CT"}
|
package/package.json
CHANGED
|
@@ -8,22 +8,22 @@ import { Message } from './message.js';
|
|
|
8
8
|
* An abstract implementation of the `MessageInterface` interface.
|
|
9
9
|
*/
|
|
10
10
|
export abstract class AbstractMessage<M extends GenericMessage> implements MessageInterface<M> {
|
|
11
|
-
private _message: M;
|
|
11
|
+
private readonly _message: M;
|
|
12
12
|
public get message(): M {
|
|
13
|
-
return this._message
|
|
13
|
+
return this._message;
|
|
14
14
|
}
|
|
15
15
|
|
|
16
|
-
private _signer: string | undefined;
|
|
16
|
+
private readonly _signer: string | undefined;
|
|
17
17
|
public get signer(): string | undefined {
|
|
18
18
|
return this._signer;
|
|
19
19
|
}
|
|
20
20
|
|
|
21
|
-
private _author: string | undefined;
|
|
21
|
+
private readonly _author: string | undefined;
|
|
22
22
|
public get author(): string | undefined {
|
|
23
23
|
return this._author;
|
|
24
24
|
}
|
|
25
25
|
|
|
26
|
-
private _signaturePayload: GenericSignaturePayload | undefined;
|
|
26
|
+
private readonly _signaturePayload: GenericSignaturePayload | undefined;
|
|
27
27
|
public get signaturePayload(): GenericSignaturePayload | undefined {
|
|
28
28
|
return this._signaturePayload;
|
|
29
29
|
}
|
|
@@ -43,10 +43,10 @@ export abstract class AbstractMessage<M extends GenericMessage> implements Messa
|
|
|
43
43
|
|
|
44
44
|
// if the message authorization contains author delegated grant, the author would be the grantor of the grant
|
|
45
45
|
// else the author would be the signer of the message
|
|
46
|
-
if (message.authorization.authorDelegatedGrant
|
|
47
|
-
this._author = Message.getSigner(message.authorization.authorDelegatedGrant);
|
|
48
|
-
} else {
|
|
46
|
+
if (message.authorization.authorDelegatedGrant === undefined) {
|
|
49
47
|
this._author = this._signer;
|
|
48
|
+
} else {
|
|
49
|
+
this._author = Message.getSigner(message.authorization.authorDelegatedGrant);
|
|
50
50
|
}
|
|
51
51
|
|
|
52
52
|
this._signaturePayload = Jws.decodePlainObjectPayload(message.authorization.signature);
|
|
@@ -146,8 +146,15 @@ export class GrantAuthorization {
|
|
|
146
146
|
);
|
|
147
147
|
}
|
|
148
148
|
|
|
149
|
-
//
|
|
150
|
-
|
|
149
|
+
// Messages.Read is the only valid Messages scope and covers Read, Subscribe, and Sync operations.
|
|
150
|
+
// Reject any Messages grant with method !== Read (malformed or legacy stored data).
|
|
151
|
+
if (dwnInterface === DwnInterfaceName.Messages) {
|
|
152
|
+
if (permissionGrant.scope.method !== DwnMethodName.Read) {
|
|
153
|
+
throw new DwnError(
|
|
154
|
+
DwnErrorCode.GrantAuthorizationMethodMismatch,
|
|
155
|
+
`messages permission grant must have method 'Read', got '${permissionGrant.scope.method}' for grant ${permissionGrant.id}`
|
|
156
|
+
);
|
|
157
|
+
}
|
|
151
158
|
const allowedMethods = [DwnMethodName.Read, DwnMethodName.Subscribe, DwnMethodName.Sync];
|
|
152
159
|
if (!allowedMethods.includes(dwnMethod as DwnMethodName)) {
|
|
153
160
|
throw new DwnError(
|
package/src/core/message.ts
CHANGED
|
@@ -26,10 +26,10 @@ export class Message {
|
|
|
26
26
|
}
|
|
27
27
|
|
|
28
28
|
let author;
|
|
29
|
-
if (message.authorization.authorDelegatedGrant
|
|
30
|
-
author = Message.getSigner(message.authorization.authorDelegatedGrant);
|
|
31
|
-
} else {
|
|
29
|
+
if (message.authorization.authorDelegatedGrant === undefined) {
|
|
32
30
|
author = Message.getSigner(message);
|
|
31
|
+
} else {
|
|
32
|
+
author = Message.getSigner(message.authorization.authorDelegatedGrant);
|
|
33
33
|
}
|
|
34
34
|
|
|
35
35
|
return author;
|
|
@@ -53,7 +53,7 @@ export async function verifyInvokedRole(
|
|
|
53
53
|
);
|
|
54
54
|
}
|
|
55
55
|
|
|
56
|
-
if (protocolDefinition.uses
|
|
56
|
+
if (protocolDefinition.uses?.[parsed.alias] === undefined) {
|
|
57
57
|
throw new DwnError(
|
|
58
58
|
DwnErrorCode.ProtocolAuthorizationNotARole,
|
|
59
59
|
`Cross-protocol role alias '${parsed.alias}' in '${protocolRole}' does not exist in the protocol's 'uses' map.`
|
|
@@ -68,7 +68,7 @@ export async function verifyInvokedRole(
|
|
|
68
68
|
tenant, roleProtocolUri, messageStore, governingTimestamp
|
|
69
69
|
);
|
|
70
70
|
const roleRuleSet = getRuleSetAtPath(roleProtocolPath, refDefinition.structure);
|
|
71
|
-
if (
|
|
71
|
+
if (!roleRuleSet?.$role) {
|
|
72
72
|
throw new DwnError(
|
|
73
73
|
DwnErrorCode.ProtocolAuthorizationNotARole,
|
|
74
74
|
`Cross-protocol role path ${protocolRole} does not match role record type.`
|
|
@@ -77,7 +77,7 @@ export async function verifyInvokedRole(
|
|
|
77
77
|
} else {
|
|
78
78
|
// Local role: validate in the composing protocol's definition
|
|
79
79
|
const roleRuleSet = getRuleSetAtPath(protocolRole, protocolDefinition.structure);
|
|
80
|
-
if (
|
|
80
|
+
if (!roleRuleSet?.$role) {
|
|
81
81
|
throw new DwnError(
|
|
82
82
|
DwnErrorCode.ProtocolAuthorizationNotARole,
|
|
83
83
|
`Protocol path ${protocolRole} does not match role record type.`
|
|
@@ -28,7 +28,7 @@ export async function verifyProtocolPathAndContextId(
|
|
|
28
28
|
fetchProtocolDefinition: FetchProtocolDefinitionFn,
|
|
29
29
|
governingTimestamp?: string,
|
|
30
30
|
): Promise<void> {
|
|
31
|
-
const declaredProtocolPath = inboundMessage.message.descriptor.protocolPath
|
|
31
|
+
const declaredProtocolPath = inboundMessage.message.descriptor.protocolPath;
|
|
32
32
|
const declaredTypeName = getTypeName(declaredProtocolPath);
|
|
33
33
|
|
|
34
34
|
const parentId = inboundMessage.message.descriptor.parentId;
|
|
@@ -47,7 +47,7 @@ export async function verifyProtocolPathAndContextId(
|
|
|
47
47
|
|
|
48
48
|
// Determine the protocol URI for the parent query.
|
|
49
49
|
// If the parent path segment has a `$ref` in the composing protocol, the parent lives in a different protocol.
|
|
50
|
-
const childProtocol = inboundMessage.message.descriptor.protocol
|
|
50
|
+
const childProtocol = inboundMessage.message.descriptor.protocol;
|
|
51
51
|
const parentProtocolUri = await resolveParentProtocolUri(
|
|
52
52
|
tenant, childProtocol, declaredProtocolPath, messageStore, fetchProtocolDefinition, governingTimestamp
|
|
53
53
|
);
|
|
@@ -174,7 +174,7 @@ export async function verifyTypeWithComposition(
|
|
|
174
174
|
fetchProtocolDefinition: FetchProtocolDefinitionFn,
|
|
175
175
|
governingTimestamp?: string,
|
|
176
176
|
): Promise<void> {
|
|
177
|
-
const declaredProtocolPath = inboundMessage.descriptor.protocolPath
|
|
177
|
+
const declaredProtocolPath = inboundMessage.descriptor.protocolPath;
|
|
178
178
|
const declaredTypeName = getTypeName(declaredProtocolPath);
|
|
179
179
|
|
|
180
180
|
// Resolve which protocol types map to use.
|
|
@@ -231,7 +231,7 @@ export function verifyType(
|
|
|
231
231
|
protocolTypes: ProtocolTypes,
|
|
232
232
|
typeName?: string,
|
|
233
233
|
): void {
|
|
234
|
-
const declaredTypeName = typeName ?? getTypeName(inboundMessage.descriptor.protocolPath
|
|
234
|
+
const declaredTypeName = typeName ?? getTypeName(inboundMessage.descriptor.protocolPath);
|
|
235
235
|
const typeNames = Object.keys(protocolTypes);
|
|
236
236
|
|
|
237
237
|
if (!typeNames.includes(declaredTypeName)) {
|
|
@@ -361,12 +361,12 @@ export async function verifyAsRoleRecordIfNeeded(
|
|
|
361
361
|
);
|
|
362
362
|
}
|
|
363
363
|
|
|
364
|
-
const protocolPath = incomingRecordsWrite.message.descriptor.protocolPath
|
|
364
|
+
const protocolPath = incomingRecordsWrite.message.descriptor.protocolPath;
|
|
365
365
|
const filter: Filter = {
|
|
366
366
|
interface : DwnInterfaceName.Records,
|
|
367
367
|
method : DwnMethodName.Write,
|
|
368
368
|
isLatestBaseState : true,
|
|
369
|
-
protocol : incomingRecordsWrite.message.descriptor.protocol
|
|
369
|
+
protocol : incomingRecordsWrite.message.descriptor.protocol,
|
|
370
370
|
protocolPath,
|
|
371
371
|
recipient,
|
|
372
372
|
};
|
|
@@ -422,12 +422,12 @@ export async function verifyRecordLimit(
|
|
|
422
422
|
const { max, strategy } = ruleSet.$recordLimit;
|
|
423
423
|
|
|
424
424
|
// Build a filter to count existing records at the same protocol path and parent context.
|
|
425
|
-
const protocolPath = incomingMessage.message.descriptor.protocolPath
|
|
425
|
+
const protocolPath = incomingMessage.message.descriptor.protocolPath;
|
|
426
426
|
const filter: Filter = {
|
|
427
427
|
interface : DwnInterfaceName.Records,
|
|
428
428
|
method : DwnMethodName.Write,
|
|
429
429
|
isLatestBaseState : true,
|
|
430
|
-
protocol : incomingMessage.message.descriptor.protocol
|
|
430
|
+
protocol : incomingMessage.message.descriptor.protocol,
|
|
431
431
|
protocolPath,
|
|
432
432
|
};
|
|
433
433
|
|
|
@@ -445,7 +445,7 @@ export async function verifyRecordLimit(
|
|
|
445
445
|
throw new DwnError(
|
|
446
446
|
DwnErrorCode.ProtocolAuthorizationRecordLimitExceeded,
|
|
447
447
|
`record limit of ${max} reached at protocol path '${protocolPath}'` +
|
|
448
|
-
`${parentContextId
|
|
448
|
+
`${parentContextId === '' ? '' : ` under parent context '${parentContextId}'`}` +
|
|
449
449
|
`: new records are rejected until existing records are deleted.`
|
|
450
450
|
);
|
|
451
451
|
}
|
|
@@ -61,7 +61,7 @@ export class ProtocolAuthorization {
|
|
|
61
61
|
// fetch the protocol definition that was active at the governing timestamp
|
|
62
62
|
const protocolDefinition = await ProtocolAuthorization.fetchProtocolDefinition(
|
|
63
63
|
tenant,
|
|
64
|
-
incomingMessage.message.descriptor.protocol
|
|
64
|
+
incomingMessage.message.descriptor.protocol,
|
|
65
65
|
messageStore,
|
|
66
66
|
governingTimestamp,
|
|
67
67
|
coreProtocols,
|
|
@@ -85,7 +85,7 @@ export class ProtocolAuthorization {
|
|
|
85
85
|
|
|
86
86
|
// get the rule set for the inbound message
|
|
87
87
|
const ruleSet = ProtocolAuthorization.getRuleSet(
|
|
88
|
-
incomingMessage.message.descriptor.protocolPath
|
|
88
|
+
incomingMessage.message.descriptor.protocolPath,
|
|
89
89
|
protocolDefinition,
|
|
90
90
|
);
|
|
91
91
|
|
|
@@ -143,7 +143,7 @@ export class ProtocolAuthorization {
|
|
|
143
143
|
// fetch the protocol definition that was active at the governing timestamp
|
|
144
144
|
const protocolDefinition = await ProtocolAuthorization.fetchProtocolDefinition(
|
|
145
145
|
tenant,
|
|
146
|
-
incomingMessage.message.descriptor.protocol
|
|
146
|
+
incomingMessage.message.descriptor.protocol,
|
|
147
147
|
messageStore,
|
|
148
148
|
governingTimestamp,
|
|
149
149
|
coreProtocols,
|
|
@@ -151,7 +151,7 @@ export class ProtocolAuthorization {
|
|
|
151
151
|
|
|
152
152
|
// get the rule set for the inbound message
|
|
153
153
|
const ruleSet = ProtocolAuthorization.getRuleSet(
|
|
154
|
-
incomingMessage.message.descriptor.protocolPath
|
|
154
|
+
incomingMessage.message.descriptor.protocolPath,
|
|
155
155
|
protocolDefinition,
|
|
156
156
|
);
|
|
157
157
|
|
|
@@ -161,8 +161,8 @@ export class ProtocolAuthorization {
|
|
|
161
161
|
await verifyInvokedRole(
|
|
162
162
|
tenant,
|
|
163
163
|
incomingMessage,
|
|
164
|
-
incomingMessage.message.descriptor.protocol
|
|
165
|
-
incomingMessage.message.contextId
|
|
164
|
+
incomingMessage.message.descriptor.protocol,
|
|
165
|
+
incomingMessage.message.contextId,
|
|
166
166
|
protocolDefinition,
|
|
167
167
|
messageStore,
|
|
168
168
|
boundFetchDefinition,
|
|
@@ -201,14 +201,14 @@ export class ProtocolAuthorization {
|
|
|
201
201
|
const initialWrite = await fetchInitialWrite(
|
|
202
202
|
tenant, newestRecordsWrite.message.recordId, messageStore
|
|
203
203
|
);
|
|
204
|
-
const governingTimestamp = initialWrite
|
|
205
|
-
?
|
|
206
|
-
:
|
|
204
|
+
const governingTimestamp = initialWrite === undefined
|
|
205
|
+
? newestRecordsWrite.message.descriptor.messageTimestamp
|
|
206
|
+
: initialWrite.descriptor.messageTimestamp;
|
|
207
207
|
|
|
208
208
|
// fetch the protocol definition that was active when the record was created
|
|
209
209
|
const protocolDefinition = await ProtocolAuthorization.fetchProtocolDefinition(
|
|
210
210
|
tenant,
|
|
211
|
-
newestRecordsWrite.message.descriptor.protocol
|
|
211
|
+
newestRecordsWrite.message.descriptor.protocol,
|
|
212
212
|
messageStore,
|
|
213
213
|
governingTimestamp,
|
|
214
214
|
coreProtocols,
|
|
@@ -216,7 +216,7 @@ export class ProtocolAuthorization {
|
|
|
216
216
|
|
|
217
217
|
// get the rule set for the inbound message
|
|
218
218
|
const ruleSet = ProtocolAuthorization.getRuleSet(
|
|
219
|
-
newestRecordsWrite.message.descriptor.protocolPath
|
|
219
|
+
newestRecordsWrite.message.descriptor.protocolPath,
|
|
220
220
|
protocolDefinition,
|
|
221
221
|
);
|
|
222
222
|
|
|
@@ -226,8 +226,8 @@ export class ProtocolAuthorization {
|
|
|
226
226
|
await verifyInvokedRole(
|
|
227
227
|
tenant,
|
|
228
228
|
incomingMessage,
|
|
229
|
-
newestRecordsWrite.message.descriptor.protocol
|
|
230
|
-
newestRecordsWrite.message.contextId
|
|
229
|
+
newestRecordsWrite.message.descriptor.protocol,
|
|
230
|
+
newestRecordsWrite.message.contextId,
|
|
231
231
|
protocolDefinition,
|
|
232
232
|
messageStore,
|
|
233
233
|
boundFetchDefinition,
|
|
@@ -312,14 +312,14 @@ export class ProtocolAuthorization {
|
|
|
312
312
|
const initialWrite = await fetchInitialWrite(
|
|
313
313
|
tenant, incomingMessage.message.descriptor.recordId, messageStore
|
|
314
314
|
);
|
|
315
|
-
const governingTimestamp = initialWrite
|
|
316
|
-
?
|
|
317
|
-
:
|
|
315
|
+
const governingTimestamp = initialWrite === undefined
|
|
316
|
+
? recordsWrite.message.descriptor.messageTimestamp
|
|
317
|
+
: initialWrite.descriptor.messageTimestamp;
|
|
318
318
|
|
|
319
319
|
// fetch the protocol definition that was active when the record was created
|
|
320
320
|
const protocolDefinition = await ProtocolAuthorization.fetchProtocolDefinition(
|
|
321
321
|
tenant,
|
|
322
|
-
recordsWrite.message.descriptor.protocol
|
|
322
|
+
recordsWrite.message.descriptor.protocol,
|
|
323
323
|
messageStore,
|
|
324
324
|
governingTimestamp,
|
|
325
325
|
coreProtocols,
|
|
@@ -327,7 +327,7 @@ export class ProtocolAuthorization {
|
|
|
327
327
|
|
|
328
328
|
// get the rule set for the inbound message
|
|
329
329
|
const ruleSet = ProtocolAuthorization.getRuleSet(
|
|
330
|
-
recordsWrite.message.descriptor.protocolPath
|
|
330
|
+
recordsWrite.message.descriptor.protocolPath,
|
|
331
331
|
protocolDefinition,
|
|
332
332
|
);
|
|
333
333
|
|
|
@@ -337,8 +337,8 @@ export class ProtocolAuthorization {
|
|
|
337
337
|
await verifyInvokedRole(
|
|
338
338
|
tenant,
|
|
339
339
|
incomingMessage,
|
|
340
|
-
recordsWrite.message.descriptor.protocol
|
|
341
|
-
recordsWrite.message.contextId
|
|
340
|
+
recordsWrite.message.descriptor.protocol,
|
|
341
|
+
recordsWrite.message.contextId,
|
|
342
342
|
protocolDefinition,
|
|
343
343
|
messageStore,
|
|
344
344
|
boundFetchDefinition,
|
|
@@ -389,12 +389,12 @@ export class ProtocolAuthorization {
|
|
|
389
389
|
protocol : protocolUri,
|
|
390
390
|
};
|
|
391
391
|
|
|
392
|
-
if (messageTimestamp
|
|
393
|
-
// temporal lookup: find the protocol definition active at the given timestamp
|
|
394
|
-
query.messageTimestamp = { lte: messageTimestamp };
|
|
395
|
-
} else {
|
|
392
|
+
if (messageTimestamp === undefined) {
|
|
396
393
|
// default: return only the latest protocol definition
|
|
397
394
|
query.isLatestBaseState = true;
|
|
395
|
+
} else {
|
|
396
|
+
// temporal lookup: find the protocol definition active at the given timestamp
|
|
397
|
+
query.messageTimestamp = { lte: messageTimestamp };
|
|
398
398
|
}
|
|
399
399
|
|
|
400
400
|
const { messages: protocols } = await messageStore.query(
|
|
@@ -153,7 +153,7 @@ export class RecordsGrantAuthorization {
|
|
|
153
153
|
|
|
154
154
|
// If grant specifies a contextId, check that record falls under that contextId
|
|
155
155
|
if (grantScope.contextId !== undefined) {
|
|
156
|
-
if (
|
|
156
|
+
if (!recordsWriteMessage.contextId?.startsWith(grantScope.contextId)) {
|
|
157
157
|
throw new DwnError(
|
|
158
158
|
DwnErrorCode.RecordsGrantAuthorizationScopeContextIdMismatch,
|
|
159
159
|
`Grant scope specifies different contextId than what appears in the record`
|
|
@@ -20,9 +20,9 @@ export class ResumableTaskManager {
|
|
|
20
20
|
public static readonly timeoutExtensionFrequencyInSeconds = 30;
|
|
21
21
|
|
|
22
22
|
private resumableTaskBatchSize = 100;
|
|
23
|
-
private resumableTaskHandlers: { [key:string]: (taskData: any) => Promise<void> };
|
|
23
|
+
private readonly resumableTaskHandlers: { [key:string]: (taskData: any) => Promise<void> };
|
|
24
24
|
|
|
25
|
-
public constructor(private resumableTaskStore: ResumableTaskStore, storageController: StorageController) {
|
|
25
|
+
public constructor(private readonly resumableTaskStore: ResumableTaskStore, storageController: StorageController) {
|
|
26
26
|
// assign resumable task handlers
|
|
27
27
|
this.resumableTaskHandlers = {
|
|
28
28
|
// NOTE: The arrow function is IMPORTANT here, else the `this` context will be lost within the invoked method.
|
package/src/dwn.ts
CHANGED
|
@@ -34,20 +34,20 @@ import { DidDht, DidJwk, DidKey, DidResolverCacheMemory, DidWeb, UniversalResolv
|
|
|
34
34
|
import { DwnInterfaceName, DwnMethodName } from './enums/dwn-interface-method.js';
|
|
35
35
|
|
|
36
36
|
export class Dwn {
|
|
37
|
-
private methodHandlers: { [key:string]: MethodHandler };
|
|
38
|
-
private didResolver: DidResolver;
|
|
39
|
-
private messageStore: MessageStore;
|
|
40
|
-
private dataStore: DataStore;
|
|
41
|
-
private resumableTaskStore: ResumableTaskStore;
|
|
42
|
-
private stateIndex: StateIndex;
|
|
43
|
-
private tenantGate: TenantGate;
|
|
44
|
-
private eventLog?: EventLog;
|
|
45
|
-
private storageController: StorageController;
|
|
46
|
-
private resumableTaskManager: ResumableTaskManager;
|
|
47
|
-
private _coreProtocols: CoreProtocolRegistry;
|
|
37
|
+
private readonly methodHandlers: { [key:string]: MethodHandler };
|
|
38
|
+
private readonly didResolver: DidResolver;
|
|
39
|
+
private readonly messageStore: MessageStore;
|
|
40
|
+
private readonly dataStore: DataStore;
|
|
41
|
+
private readonly resumableTaskStore: ResumableTaskStore;
|
|
42
|
+
private readonly stateIndex: StateIndex;
|
|
43
|
+
private readonly tenantGate: TenantGate;
|
|
44
|
+
private readonly eventLog?: EventLog;
|
|
45
|
+
private readonly storageController: StorageController;
|
|
46
|
+
private readonly resumableTaskManager: ResumableTaskManager;
|
|
47
|
+
private readonly _coreProtocols: CoreProtocolRegistry;
|
|
48
48
|
|
|
49
49
|
/** Whether the DWN owns the resolver's lifecycle (i.e., created it via defaults). */
|
|
50
|
-
private ownsResolver: boolean;
|
|
50
|
+
private readonly ownsResolver: boolean;
|
|
51
51
|
|
|
52
52
|
private constructor(config: DwnConfig) {
|
|
53
53
|
this.didResolver = config.didResolver!;
|
|
@@ -204,7 +204,7 @@ export class Dwn {
|
|
|
204
204
|
const handlerKey = rawMessage.descriptor.interface + rawMessage.descriptor.method;
|
|
205
205
|
const methodHandlerReply = await this.methodHandlers[handlerKey].handle({
|
|
206
206
|
tenant,
|
|
207
|
-
message: rawMessage
|
|
207
|
+
message: rawMessage,
|
|
208
208
|
dataStream,
|
|
209
209
|
subscriptionHandler
|
|
210
210
|
});
|
|
@@ -65,21 +65,21 @@ export interface EventEmitterEventLogConfig {
|
|
|
65
65
|
* For multi-node deployments, use a distributed implementation (NATS, Redis, etc.).
|
|
66
66
|
*/
|
|
67
67
|
export class EventEmitterEventLog implements EventLog {
|
|
68
|
-
private emitter = mitt<EmitterEvents>();
|
|
68
|
+
private readonly emitter = mitt<EmitterEvents>();
|
|
69
69
|
private isOpen: boolean = false;
|
|
70
|
-
private errorHandler: (error: any) => void = (error): void => { console.error('event log error', error); };
|
|
71
|
-
private maxEventsPerTenant: number;
|
|
70
|
+
private readonly errorHandler: (error: any) => void = (error): void => { console.error('event log error', error); };
|
|
71
|
+
private readonly maxEventsPerTenant: number;
|
|
72
72
|
|
|
73
73
|
/**
|
|
74
74
|
* Per-tenant ordered event storage.
|
|
75
75
|
* Key: tenant DID → Map of seq → StoredEntry.
|
|
76
76
|
*/
|
|
77
|
-
private tenantLogs: Map<string, Map<number, StoredEntry>> = new Map();
|
|
77
|
+
private readonly tenantLogs: Map<string, Map<number, StoredEntry>> = new Map();
|
|
78
78
|
|
|
79
79
|
/**
|
|
80
80
|
* Per-tenant monotonic sequence counter.
|
|
81
81
|
*/
|
|
82
|
-
private tenantSeqs: Map<string, number> = new Map();
|
|
82
|
+
private readonly tenantSeqs: Map<string, number> = new Map();
|
|
83
83
|
|
|
84
84
|
/**
|
|
85
85
|
* Epoch for this EventLog instance. Generated once at construction as a
|
|
@@ -131,9 +131,7 @@ export class EventEmitterEventLog implements EventLog {
|
|
|
131
131
|
let reason: ProgressGapReason;
|
|
132
132
|
if (cursor.streamId !== expectedStreamId) {
|
|
133
133
|
reason = 'stream_mismatch';
|
|
134
|
-
} else if (cursor.epoch
|
|
135
|
-
reason = 'epoch_mismatch';
|
|
136
|
-
} else {
|
|
134
|
+
} else if (cursor.epoch === this.epoch) {
|
|
137
135
|
// Check if position is still within replay bounds.
|
|
138
136
|
const log = this.tenantLogs.get(tenant);
|
|
139
137
|
if (log !== undefined && log.size > 0) {
|
|
@@ -148,6 +146,8 @@ export class EventEmitterEventLog implements EventLog {
|
|
|
148
146
|
} else {
|
|
149
147
|
return; // No events for tenant — cursor is vacuously valid (will get empty catch-up + EOSE).
|
|
150
148
|
}
|
|
149
|
+
} else {
|
|
150
|
+
reason = 'epoch_mismatch';
|
|
151
151
|
}
|
|
152
152
|
|
|
153
153
|
// Build gap metadata.
|
|
@@ -226,7 +226,7 @@ export class EventEmitterEventLog implements EventLog {
|
|
|
226
226
|
await this.validateCursor(tenant, cursor);
|
|
227
227
|
}
|
|
228
228
|
|
|
229
|
-
const cursorSeq = cursor
|
|
229
|
+
const cursorSeq = cursor === undefined ? undefined : EventEmitterEventLog.parsePosition(cursor.position);
|
|
230
230
|
const log = this.tenantLogs.get(tenant);
|
|
231
231
|
|
|
232
232
|
if (log === undefined || log.size === 0) {
|
|
@@ -319,12 +319,12 @@ export class EventEmitterEventLog implements EventLog {
|
|
|
319
319
|
if (filters !== undefined && filters.length > 0) {
|
|
320
320
|
if (!FilterUtility.matchAnyFilter(payload.indexes, filters)) { return; }
|
|
321
321
|
}
|
|
322
|
-
if (
|
|
323
|
-
pendingLiveEvents.push({ event: payload.event, seq: payload.seq, messageCid: payload.messageCid });
|
|
324
|
-
} else {
|
|
322
|
+
if (catchUpComplete) {
|
|
325
323
|
void tokenFromPayload(payload).then((token) => {
|
|
326
324
|
listener({ type: 'event', cursor: token, event: payload.event });
|
|
327
325
|
});
|
|
326
|
+
} else {
|
|
327
|
+
pendingLiveEvents.push({ event: payload.event, seq: payload.seq, messageCid: payload.messageCid });
|
|
328
328
|
}
|
|
329
329
|
};
|
|
330
330
|
|
|
@@ -334,9 +334,9 @@ export class EventEmitterEventLog implements EventLog {
|
|
|
334
334
|
const readResult = await this.read(tenant, { cursor, filters });
|
|
335
335
|
// The read cursor is the token of the last read event, or the input cursor if nothing new.
|
|
336
336
|
const eoseCursor = readResult.cursor ?? cursor;
|
|
337
|
-
const lastCatchUpSeq = readResult.cursor
|
|
338
|
-
?
|
|
339
|
-
:
|
|
337
|
+
const lastCatchUpSeq = readResult.cursor === undefined
|
|
338
|
+
? cursorSeq
|
|
339
|
+
: EventEmitterEventLog.parsePosition(readResult.cursor.position);
|
|
340
340
|
|
|
341
341
|
// Use the messageCid captured by read() during its synchronous iteration.
|
|
342
342
|
// This eliminates re-lookup races: read() populates entry.messageCid before
|
|
@@ -18,7 +18,7 @@ type HandleArgs = { tenant: string, message: MessagesReadMessage };
|
|
|
18
18
|
|
|
19
19
|
export class MessagesReadHandler implements MethodHandler {
|
|
20
20
|
|
|
21
|
-
constructor(private deps: HandlerDependencies) {}
|
|
21
|
+
constructor(private readonly deps: HandlerDependencies) {}
|
|
22
22
|
|
|
23
23
|
public async handle({ tenant, message }: HandleArgs): Promise<MessagesReadReply> {
|
|
24
24
|
let messagesRead: MessagesRead;
|
|
@@ -52,16 +52,16 @@ export class MessagesReadHandler implements MethodHandler {
|
|
|
52
52
|
const recordsWrite = entry.message as RecordsQueryReplyEntry;
|
|
53
53
|
// RecordsWrite specific handling, if MessageStore has embedded `encodedData` return it with the entry.
|
|
54
54
|
// we store `encodedData` along with the message if the data is below a certain threshold.
|
|
55
|
-
if (recordsWrite.encodedData
|
|
56
|
-
|
|
57
|
-
entry.data = DataStream.fromBytes(dataBytes);
|
|
58
|
-
delete recordsWrite.encodedData;
|
|
59
|
-
} else {
|
|
60
|
-
// otherwise check the data store for the associated data
|
|
55
|
+
if (recordsWrite.encodedData === undefined) {
|
|
56
|
+
// check the data store for the associated data
|
|
61
57
|
const result = await this.deps.dataStore!.get(tenant, recordsWrite.recordId, recordsWrite.descriptor.dataCid);
|
|
62
58
|
if (result?.dataStream !== undefined) {
|
|
63
59
|
entry.data = result.dataStream;
|
|
64
60
|
}
|
|
61
|
+
} else {
|
|
62
|
+
const dataBytes = Encoder.base64UrlToBytes(recordsWrite.encodedData);
|
|
63
|
+
entry.data = DataStream.fromBytes(dataBytes);
|
|
64
|
+
delete recordsWrite.encodedData;
|
|
65
65
|
}
|
|
66
66
|
}
|
|
67
67
|
|
|
@@ -14,7 +14,7 @@ import { DwnError, DwnErrorCode } from '../core/dwn-error.js';
|
|
|
14
14
|
|
|
15
15
|
export class MessagesSubscribeHandler implements MethodHandler {
|
|
16
16
|
|
|
17
|
-
constructor(private deps: HandlerDependencies) {}
|
|
17
|
+
constructor(private readonly deps: HandlerDependencies) {}
|
|
18
18
|
|
|
19
19
|
public async handle({
|
|
20
20
|
tenant,
|
|
@@ -65,7 +65,7 @@ export class MessagesSubscribeHandler implements MethodHandler {
|
|
|
65
65
|
const gapInfo = (error as any).gapInfo as ProgressGapInfo | undefined;
|
|
66
66
|
return {
|
|
67
67
|
status : { code: 410, detail: 'Progress token gap' },
|
|
68
|
-
error : gapInfo
|
|
68
|
+
error : gapInfo === undefined ? undefined : { code: 'ProgressGap' as const, ...gapInfo },
|
|
69
69
|
};
|
|
70
70
|
}
|
|
71
71
|
return messageReplyFromError(error, 500);
|