@openvtc/pnm-core 0.1.0

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.
Files changed (250) hide show
  1. package/README.md +129 -0
  2. package/dist/did/derive-signing-key.d.ts +19 -0
  3. package/dist/did/derive-signing-key.d.ts.map +1 -0
  4. package/dist/did/derive-signing-key.js +96 -0
  5. package/dist/did/derive-signing-key.js.map +1 -0
  6. package/dist/did/index.d.ts +5 -0
  7. package/dist/did/index.d.ts.map +1 -0
  8. package/dist/did/index.js +5 -0
  9. package/dist/did/index.js.map +1 -0
  10. package/dist/did/peer.d.ts +37 -0
  11. package/dist/did/peer.d.ts.map +1 -0
  12. package/dist/did/peer.js +49 -0
  13. package/dist/did/peer.js.map +1 -0
  14. package/dist/did/verification-method.d.ts +43 -0
  15. package/dist/did/verification-method.d.ts.map +1 -0
  16. package/dist/did/verification-method.js +32 -0
  17. package/dist/did/verification-method.js.map +1 -0
  18. package/dist/did/verify.d.ts +49 -0
  19. package/dist/did/verify.d.ts.map +1 -0
  20. package/dist/did/verify.js +89 -0
  21. package/dist/did/verify.js.map +1 -0
  22. package/dist/didcomm/index.d.ts +235 -0
  23. package/dist/didcomm/index.d.ts.map +1 -0
  24. package/dist/didcomm/index.js +415 -0
  25. package/dist/didcomm/index.js.map +1 -0
  26. package/dist/inbound/confirm.d.ts +50 -0
  27. package/dist/inbound/confirm.d.ts.map +1 -0
  28. package/dist/inbound/confirm.js +64 -0
  29. package/dist/inbound/confirm.js.map +1 -0
  30. package/dist/inbound/dedup.d.ts +9 -0
  31. package/dist/inbound/dedup.d.ts.map +1 -0
  32. package/dist/inbound/dedup.js +31 -0
  33. package/dist/inbound/dedup.js.map +1 -0
  34. package/dist/inbound/index.d.ts +3 -0
  35. package/dist/inbound/index.d.ts.map +1 -0
  36. package/dist/inbound/index.js +3 -0
  37. package/dist/inbound/index.js.map +1 -0
  38. package/dist/index.d.ts +14 -0
  39. package/dist/index.d.ts.map +1 -0
  40. package/dist/index.js +14 -0
  41. package/dist/index.js.map +1 -0
  42. package/dist/onboarding/index.d.ts +2 -0
  43. package/dist/onboarding/index.d.ts.map +1 -0
  44. package/dist/onboarding/index.js +2 -0
  45. package/dist/onboarding/index.js.map +1 -0
  46. package/dist/onboarding/swap.d.ts +60 -0
  47. package/dist/onboarding/swap.d.ts.map +1 -0
  48. package/dist/onboarding/swap.js +148 -0
  49. package/dist/onboarding/swap.js.map +1 -0
  50. package/dist/provision/adopt.d.ts +31 -0
  51. package/dist/provision/adopt.d.ts.map +1 -0
  52. package/dist/provision/adopt.js +114 -0
  53. package/dist/provision/adopt.js.map +1 -0
  54. package/dist/provision/armor.d.ts +19 -0
  55. package/dist/provision/armor.d.ts.map +1 -0
  56. package/dist/provision/armor.js +243 -0
  57. package/dist/provision/armor.js.map +1 -0
  58. package/dist/provision/crc24.d.ts +5 -0
  59. package/dist/provision/crc24.d.ts.map +1 -0
  60. package/dist/provision/crc24.js +30 -0
  61. package/dist/provision/crc24.js.map +1 -0
  62. package/dist/provision/hpke.d.ts +17 -0
  63. package/dist/provision/hpke.d.ts.map +1 -0
  64. package/dist/provision/hpke.js +60 -0
  65. package/dist/provision/hpke.js.map +1 -0
  66. package/dist/provision/index.d.ts +10 -0
  67. package/dist/provision/index.d.ts.map +1 -0
  68. package/dist/provision/index.js +16 -0
  69. package/dist/provision/index.js.map +1 -0
  70. package/dist/provision/open.d.ts +28 -0
  71. package/dist/provision/open.d.ts.map +1 -0
  72. package/dist/provision/open.js +224 -0
  73. package/dist/provision/open.js.map +1 -0
  74. package/dist/provision/request.d.ts +65 -0
  75. package/dist/provision/request.d.ts.map +1 -0
  76. package/dist/provision/request.js +53 -0
  77. package/dist/provision/request.js.map +1 -0
  78. package/dist/provision/run.d.ts +76 -0
  79. package/dist/provision/run.d.ts.map +1 -0
  80. package/dist/provision/run.js +110 -0
  81. package/dist/provision/run.js.map +1 -0
  82. package/dist/provision/send.d.ts +85 -0
  83. package/dist/provision/send.d.ts.map +1 -0
  84. package/dist/provision/send.js +87 -0
  85. package/dist/provision/send.js.map +1 -0
  86. package/dist/provision/types.d.ts +110 -0
  87. package/dist/provision/types.d.ts.map +1 -0
  88. package/dist/provision/types.js +17 -0
  89. package/dist/provision/types.js.map +1 -0
  90. package/dist/rp-login/didcomm.d.ts +34 -0
  91. package/dist/rp-login/didcomm.d.ts.map +1 -0
  92. package/dist/rp-login/didcomm.js +72 -0
  93. package/dist/rp-login/didcomm.js.map +1 -0
  94. package/dist/rp-login/index.d.ts +3 -0
  95. package/dist/rp-login/index.d.ts.map +1 -0
  96. package/dist/rp-login/index.js +3 -0
  97. package/dist/rp-login/index.js.map +1 -0
  98. package/dist/rp-login/step-up.d.ts +43 -0
  99. package/dist/rp-login/step-up.d.ts.map +1 -0
  100. package/dist/rp-login/step-up.js +118 -0
  101. package/dist/rp-login/step-up.js.map +1 -0
  102. package/dist/siop/index.d.ts +3 -0
  103. package/dist/siop/index.d.ts.map +1 -0
  104. package/dist/siop/index.js +3 -0
  105. package/dist/siop/index.js.map +1 -0
  106. package/dist/siop/login-client.d.ts +29 -0
  107. package/dist/siop/login-client.d.ts.map +1 -0
  108. package/dist/siop/login-client.js +79 -0
  109. package/dist/siop/login-client.js.map +1 -0
  110. package/dist/siop/self-issued.d.ts +96 -0
  111. package/dist/siop/self-issued.d.ts.map +1 -0
  112. package/dist/siop/self-issued.js +162 -0
  113. package/dist/siop/self-issued.js.map +1 -0
  114. package/dist/store/holder-identity.d.ts +241 -0
  115. package/dist/store/holder-identity.d.ts.map +1 -0
  116. package/dist/store/holder-identity.js +441 -0
  117. package/dist/store/holder-identity.js.map +1 -0
  118. package/dist/store/index.d.ts +4 -0
  119. package/dist/store/index.d.ts.map +1 -0
  120. package/dist/store/index.js +4 -0
  121. package/dist/store/index.js.map +1 -0
  122. package/dist/store/kv-store.d.ts +51 -0
  123. package/dist/store/kv-store.d.ts.map +1 -0
  124. package/dist/store/kv-store.js +100 -0
  125. package/dist/store/kv-store.js.map +1 -0
  126. package/dist/store/secret-wrap.d.ts +109 -0
  127. package/dist/store/secret-wrap.d.ts.map +1 -0
  128. package/dist/store/secret-wrap.js +85 -0
  129. package/dist/store/secret-wrap.js.map +1 -0
  130. package/dist/trust-tasks/index.d.ts +2 -0
  131. package/dist/trust-tasks/index.d.ts.map +1 -0
  132. package/dist/trust-tasks/index.js +2 -0
  133. package/dist/trust-tasks/index.js.map +1 -0
  134. package/dist/trust-tasks/sign.d.ts +31 -0
  135. package/dist/trust-tasks/sign.d.ts.map +1 -0
  136. package/dist/trust-tasks/sign.js +141 -0
  137. package/dist/trust-tasks/sign.js.map +1 -0
  138. package/dist/util/timing.d.ts +14 -0
  139. package/dist/util/timing.d.ts.map +1 -0
  140. package/dist/util/timing.js +20 -0
  141. package/dist/util/timing.js.map +1 -0
  142. package/dist/vault/delete.d.ts +19 -0
  143. package/dist/vault/delete.d.ts.map +1 -0
  144. package/dist/vault/delete.js +35 -0
  145. package/dist/vault/delete.js.map +1 -0
  146. package/dist/vault/index.d.ts +8 -0
  147. package/dist/vault/index.d.ts.map +1 -0
  148. package/dist/vault/index.js +7 -0
  149. package/dist/vault/index.js.map +1 -0
  150. package/dist/vault/list.d.ts +96 -0
  151. package/dist/vault/list.d.ts.map +1 -0
  152. package/dist/vault/list.js +106 -0
  153. package/dist/vault/list.js.map +1 -0
  154. package/dist/vault/proxy-login.d.ts +100 -0
  155. package/dist/vault/proxy-login.d.ts.map +1 -0
  156. package/dist/vault/proxy-login.js +106 -0
  157. package/dist/vault/proxy-login.js.map +1 -0
  158. package/dist/vault/release.d.ts +33 -0
  159. package/dist/vault/release.d.ts.map +1 -0
  160. package/dist/vault/release.js +83 -0
  161. package/dist/vault/release.js.map +1 -0
  162. package/dist/vault/sign-trust-task.d.ts +26 -0
  163. package/dist/vault/sign-trust-task.d.ts.map +1 -0
  164. package/dist/vault/sign-trust-task.js +53 -0
  165. package/dist/vault/sign-trust-task.js.map +1 -0
  166. package/dist/vault/transport.d.ts +50 -0
  167. package/dist/vault/transport.d.ts.map +1 -0
  168. package/dist/vault/transport.js +118 -0
  169. package/dist/vault/transport.js.map +1 -0
  170. package/dist/vault/upsert.d.ts +102 -0
  171. package/dist/vault/upsert.d.ts.map +1 -0
  172. package/dist/vault/upsert.js +92 -0
  173. package/dist/vault/upsert.js.map +1 -0
  174. package/dist/vta/bridge-mediator-session.d.ts +26 -0
  175. package/dist/vta/bridge-mediator-session.d.ts.map +1 -0
  176. package/dist/vta/bridge-mediator-session.js +37 -0
  177. package/dist/vta/bridge-mediator-session.js.map +1 -0
  178. package/dist/vta/bridge-memory.d.ts +80 -0
  179. package/dist/vta/bridge-memory.d.ts.map +1 -0
  180. package/dist/vta/bridge-memory.js +162 -0
  181. package/dist/vta/bridge-memory.js.map +1 -0
  182. package/dist/vta/client.d.ts +40 -0
  183. package/dist/vta/client.d.ts.map +1 -0
  184. package/dist/vta/client.js +91 -0
  185. package/dist/vta/client.js.map +1 -0
  186. package/dist/vta/contexts.d.ts +60 -0
  187. package/dist/vta/contexts.d.ts.map +1 -0
  188. package/dist/vta/contexts.js +118 -0
  189. package/dist/vta/contexts.js.map +1 -0
  190. package/dist/vta/didcomm.d.ts +57 -0
  191. package/dist/vta/didcomm.d.ts.map +1 -0
  192. package/dist/vta/didcomm.js +138 -0
  193. package/dist/vta/didcomm.js.map +1 -0
  194. package/dist/vta/errors.d.ts +20 -0
  195. package/dist/vta/errors.d.ts.map +1 -0
  196. package/dist/vta/errors.js +64 -0
  197. package/dist/vta/errors.js.map +1 -0
  198. package/dist/vta/index.d.ts +15 -0
  199. package/dist/vta/index.d.ts.map +1 -0
  200. package/dist/vta/index.js +15 -0
  201. package/dist/vta/index.js.map +1 -0
  202. package/dist/vta/mediation.d.ts +80 -0
  203. package/dist/vta/mediation.d.ts.map +1 -0
  204. package/dist/vta/mediation.js +29 -0
  205. package/dist/vta/mediation.js.map +1 -0
  206. package/dist/vta/mediator-client.d.ts +66 -0
  207. package/dist/vta/mediator-client.d.ts.map +1 -0
  208. package/dist/vta/mediator-client.js +139 -0
  209. package/dist/vta/mediator-client.js.map +1 -0
  210. package/dist/vta/pickup.d.ts +81 -0
  211. package/dist/vta/pickup.d.ts.map +1 -0
  212. package/dist/vta/pickup.js +30 -0
  213. package/dist/vta/pickup.js.map +1 -0
  214. package/dist/vta/protocol.d.ts +76 -0
  215. package/dist/vta/protocol.d.ts.map +1 -0
  216. package/dist/vta/protocol.js +30 -0
  217. package/dist/vta/protocol.js.map +1 -0
  218. package/dist/vta/smoke.d.ts +59 -0
  219. package/dist/vta/smoke.d.ts.map +1 -0
  220. package/dist/vta/smoke.js +408 -0
  221. package/dist/vta/smoke.js.map +1 -0
  222. package/dist/vta/transport.d.ts +55 -0
  223. package/dist/vta/transport.d.ts.map +1 -0
  224. package/dist/vta/transport.js +2 -0
  225. package/dist/vta/transport.js.map +1 -0
  226. package/dist/vta/types.d.ts +50 -0
  227. package/dist/vta/types.d.ts.map +1 -0
  228. package/dist/vta/types.js +2 -0
  229. package/dist/vta/types.js.map +1 -0
  230. package/dist/vta/wallet-session.d.ts +87 -0
  231. package/dist/vta/wallet-session.d.ts.map +1 -0
  232. package/dist/vta/wallet-session.js +106 -0
  233. package/dist/vta/wallet-session.js.map +1 -0
  234. package/dist/webauthn/base64url.d.ts +3 -0
  235. package/dist/webauthn/base64url.d.ts.map +1 -0
  236. package/dist/webauthn/base64url.js +17 -0
  237. package/dist/webauthn/base64url.js.map +1 -0
  238. package/dist/webauthn/index.d.ts +4 -0
  239. package/dist/webauthn/index.d.ts.map +1 -0
  240. package/dist/webauthn/index.js +4 -0
  241. package/dist/webauthn/index.js.map +1 -0
  242. package/dist/webauthn/multikey.d.ts +26 -0
  243. package/dist/webauthn/multikey.d.ts.map +1 -0
  244. package/dist/webauthn/multikey.js +91 -0
  245. package/dist/webauthn/multikey.js.map +1 -0
  246. package/dist/webauthn/register.d.ts +36 -0
  247. package/dist/webauthn/register.d.ts.map +1 -0
  248. package/dist/webauthn/register.js +77 -0
  249. package/dist/webauthn/register.js.map +1 -0
  250. package/package.json +56 -0
@@ -0,0 +1,109 @@
1
+ /**
2
+ * Pluggable encryption wrapper for the holder's Ed25519 root
3
+ * secret.
4
+ *
5
+ * The wallet's persisted holder identity is keyed by an Ed25519
6
+ * scalar that IS the authentication key — anyone with that
7
+ * secret can impersonate the wallet at every RP. The bare
8
+ * IndexedDB store keeps it as plaintext base64url; an attacker
9
+ * with origin-scoped storage access (a malicious extension with
10
+ * matching permissions, a same-origin XSS in the extension's
11
+ * pages, or device-level exfil) walks away with the wallet.
12
+ *
13
+ * The H1 fix wraps the secret with a key derived from a user-
14
+ * gesture authenticator (WebAuthn PRF in the extension build),
15
+ * so storage exfil yields ciphertext that's useless without
16
+ * the operator's biometric / FIDO2 device.
17
+ *
18
+ * This module is the abstraction; concrete implementations live
19
+ * in the extension (`webauthn-prf-wrap.ts`) and in the PWA. The
20
+ * core stays platform-agnostic.
21
+ */
22
+ /**
23
+ * Trait every wallet-secret wrap implements.
24
+ *
25
+ * Wraps a fresh-minted secret on first persistence; unwraps it
26
+ * on every subsequent load. Implementations cache derived keys
27
+ * across calls (e.g. `chrome.storage.session`) so the operator
28
+ * doesn't have to tap their authenticator for every wallet
29
+ * operation — only when the cache is cold (first load after
30
+ * browser restart).
31
+ *
32
+ * `wrap` is called exactly once per persisted identity (at
33
+ * mint time). `unwrap` is called every load.
34
+ *
35
+ * Returning `null` from either side is a non-fatal signal that
36
+ * the wrapper is unavailable (e.g. authenticator declined,
37
+ * platform doesn't support PRF, operator hasn't enrolled);
38
+ * the caller falls back to plaintext persistence with a `warn`.
39
+ * This keeps existing plaintext-stored wallets loadable through
40
+ * an OS upgrade or browser change that breaks the wrapper.
41
+ */
42
+ export interface SecretWrap {
43
+ /** Short identifier persisted alongside the wrap metadata so
44
+ * a future unwrap can pick the right implementation. */
45
+ readonly algorithm: string;
46
+ /**
47
+ * Encrypt `secret` and return the wire envelope. Returning
48
+ * `null` lets the caller fall back to plaintext (with a
49
+ * warning).
50
+ */
51
+ wrap(secret: Uint8Array): Promise<WrappedSecret | null>;
52
+ /**
53
+ * Decrypt `wrapped.ciphertext` and return the original
54
+ * secret bytes. Returning `null` lets the caller surface a
55
+ * "wallet locked; tap your authenticator" UX without
56
+ * crashing the load path.
57
+ */
58
+ unwrap(wrapped: WrappedSecret): Promise<Uint8Array | null>;
59
+ }
60
+ /**
61
+ * On-disk envelope for a wrapped secret. Persisted as part of
62
+ * the holder record; the wrap implementation reads `params`
63
+ * to reconstitute its derived key.
64
+ */
65
+ export interface WrappedSecret {
66
+ /** Matches [`SecretWrap.algorithm`] of the wrap that produced
67
+ * it; the loader looks up the right implementation. */
68
+ algorithm: string;
69
+ /** AES-GCM ciphertext of the original secret, base64url. */
70
+ ciphertextB64u: string;
71
+ /** Initialisation vector / nonce, base64url. AES-GCM
72
+ * recommends 96 bits = 12 bytes. */
73
+ ivB64u: string;
74
+ /** Free-form opaque params the wrap needs at unwrap time
75
+ * (credentialId, PRF salt, KDF salt, etc.). The core treats
76
+ * this as opaque; only the matching wrap implementation
77
+ * reads it. */
78
+ params: Record<string, string>;
79
+ }
80
+ /**
81
+ * No-op wrap. Used in tests, in non-extension callers that
82
+ * don't have a wrap available, and as the explicit "I know
83
+ * this is plaintext" fallback. The wrap helper still records
84
+ * a `passthrough` algorithm tag so an upgrade path can detect
85
+ * "this record predates the encrypted-secret flow."
86
+ */
87
+ export declare class PassthroughWrap implements SecretWrap {
88
+ readonly algorithm = "passthrough";
89
+ wrap(secret: Uint8Array): Promise<WrappedSecret>;
90
+ unwrap(wrapped: WrappedSecret): Promise<Uint8Array>;
91
+ }
92
+ /**
93
+ * Apply the wrap when present, fall back to a passthrough wrap
94
+ * otherwise. Centralised so the [`generateOrLoadHolderIdentity`]
95
+ * path doesn't have to branch.
96
+ */
97
+ export declare function wrapSecret(secret: Uint8Array, wrap?: SecretWrap): Promise<WrappedSecret>;
98
+ /**
99
+ * Unwrap a persisted secret. The wrap is selected by
100
+ * `wrapped.algorithm`:
101
+ *
102
+ * - `"passthrough"` → use [`PassthroughWrap`] (no-op).
103
+ * - Anything else → require the caller-supplied `wrap` to
104
+ * match. A mismatch (`wrap.algorithm !== wrapped.algorithm`)
105
+ * throws; the caller is responsible for picking the right
106
+ * wrap impl for the persisted record.
107
+ */
108
+ export declare function unwrapSecret(wrapped: WrappedSecret, wrap?: SecretWrap): Promise<Uint8Array>;
109
+ //# sourceMappingURL=secret-wrap.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"secret-wrap.d.ts","sourceRoot":"","sources":["../../src/store/secret-wrap.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;GAoBG;AAIH;;;;;;;;;;;;;;;;;;;GAmBG;AACH,MAAM,WAAW,UAAU;IACzB;6DACyD;IACzD,QAAQ,CAAC,SAAS,EAAE,MAAM,CAAC;IAE3B;;;;OAIG;IACH,IAAI,CAAC,MAAM,EAAE,UAAU,GAAG,OAAO,CAAC,aAAa,GAAG,IAAI,CAAC,CAAC;IAExD;;;;;OAKG;IACH,MAAM,CAAC,OAAO,EAAE,aAAa,GAAG,OAAO,CAAC,UAAU,GAAG,IAAI,CAAC,CAAC;CAC5D;AAED;;;;GAIG;AACH,MAAM,WAAW,aAAa;IAC5B;4DACwD;IACxD,SAAS,EAAE,MAAM,CAAC;IAClB,4DAA4D;IAC5D,cAAc,EAAE,MAAM,CAAC;IACvB;yCACqC;IACrC,MAAM,EAAE,MAAM,CAAC;IACf;;;oBAGgB;IAChB,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;CAChC;AAED;;;;;;GAMG;AACH,qBAAa,eAAgB,YAAW,UAAU;IAChD,QAAQ,CAAC,SAAS,iBAAiB;IAE7B,IAAI,CAAC,MAAM,EAAE,UAAU,GAAG,OAAO,CAAC,aAAa,CAAC;IAShD,MAAM,CAAC,OAAO,EAAE,aAAa,GAAG,OAAO,CAAC,UAAU,CAAC;CAG1D;AAED;;;;GAIG;AACH,wBAAsB,UAAU,CAC9B,MAAM,EAAE,UAAU,EAClB,IAAI,CAAC,EAAE,UAAU,GAChB,OAAO,CAAC,aAAa,CAAC,CAaxB;AAED;;;;;;;;;GASG;AACH,wBAAsB,YAAY,CAChC,OAAO,EAAE,aAAa,EACtB,IAAI,CAAC,EAAE,UAAU,GAChB,OAAO,CAAC,UAAU,CAAC,CAgBrB"}
@@ -0,0 +1,85 @@
1
+ /**
2
+ * Pluggable encryption wrapper for the holder's Ed25519 root
3
+ * secret.
4
+ *
5
+ * The wallet's persisted holder identity is keyed by an Ed25519
6
+ * scalar that IS the authentication key — anyone with that
7
+ * secret can impersonate the wallet at every RP. The bare
8
+ * IndexedDB store keeps it as plaintext base64url; an attacker
9
+ * with origin-scoped storage access (a malicious extension with
10
+ * matching permissions, a same-origin XSS in the extension's
11
+ * pages, or device-level exfil) walks away with the wallet.
12
+ *
13
+ * The H1 fix wraps the secret with a key derived from a user-
14
+ * gesture authenticator (WebAuthn PRF in the extension build),
15
+ * so storage exfil yields ciphertext that's useless without
16
+ * the operator's biometric / FIDO2 device.
17
+ *
18
+ * This module is the abstraction; concrete implementations live
19
+ * in the extension (`webauthn-prf-wrap.ts`) and in the PWA. The
20
+ * core stays platform-agnostic.
21
+ */
22
+ import { base64url } from "@openvtc/vti-didcomm-js";
23
+ /**
24
+ * No-op wrap. Used in tests, in non-extension callers that
25
+ * don't have a wrap available, and as the explicit "I know
26
+ * this is plaintext" fallback. The wrap helper still records
27
+ * a `passthrough` algorithm tag so an upgrade path can detect
28
+ * "this record predates the encrypted-secret flow."
29
+ */
30
+ export class PassthroughWrap {
31
+ algorithm = "passthrough";
32
+ async wrap(secret) {
33
+ return {
34
+ algorithm: this.algorithm,
35
+ ciphertextB64u: base64url.encode(secret),
36
+ ivB64u: "",
37
+ params: {},
38
+ };
39
+ }
40
+ async unwrap(wrapped) {
41
+ return base64url.decode(wrapped.ciphertextB64u);
42
+ }
43
+ }
44
+ /**
45
+ * Apply the wrap when present, fall back to a passthrough wrap
46
+ * otherwise. Centralised so the [`generateOrLoadHolderIdentity`]
47
+ * path doesn't have to branch.
48
+ */
49
+ export async function wrapSecret(secret, wrap) {
50
+ if (wrap) {
51
+ const wrapped = await wrap.wrap(secret);
52
+ if (wrapped)
53
+ return wrapped;
54
+ // Wrapper available but declined (operator cancelled the
55
+ // authenticator prompt, etc.). The caller may decide
56
+ // separately whether to proceed plaintext; we surface the
57
+ // signal as a thrown error so the choice is explicit.
58
+ throw new Error(`SecretWrap '${wrap.algorithm}' declined to wrap (operator cancelled?)`);
59
+ }
60
+ return new PassthroughWrap().wrap(secret);
61
+ }
62
+ /**
63
+ * Unwrap a persisted secret. The wrap is selected by
64
+ * `wrapped.algorithm`:
65
+ *
66
+ * - `"passthrough"` → use [`PassthroughWrap`] (no-op).
67
+ * - Anything else → require the caller-supplied `wrap` to
68
+ * match. A mismatch (`wrap.algorithm !== wrapped.algorithm`)
69
+ * throws; the caller is responsible for picking the right
70
+ * wrap impl for the persisted record.
71
+ */
72
+ export async function unwrapSecret(wrapped, wrap) {
73
+ if (wrapped.algorithm === "passthrough") {
74
+ return new PassthroughWrap().unwrap(wrapped);
75
+ }
76
+ if (!wrap || wrap.algorithm !== wrapped.algorithm) {
77
+ throw new Error(`wallet is wrapped with '${wrapped.algorithm}' but no matching SecretWrap was supplied`);
78
+ }
79
+ const secret = await wrap.unwrap(wrapped);
80
+ if (!secret) {
81
+ throw new Error(`SecretWrap '${wrap.algorithm}' declined to unwrap (operator cancelled?)`);
82
+ }
83
+ return secret;
84
+ }
85
+ //# sourceMappingURL=secret-wrap.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"secret-wrap.js","sourceRoot":"","sources":["../../src/store/secret-wrap.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;GAoBG;AAEH,OAAO,EAAE,SAAS,EAAE,MAAM,yBAAyB,CAAC;AAgEpD;;;;;;GAMG;AACH,MAAM,OAAO,eAAe;IACjB,SAAS,GAAG,aAAa,CAAC;IAEnC,KAAK,CAAC,IAAI,CAAC,MAAkB;QAC3B,OAAO;YACL,SAAS,EAAE,IAAI,CAAC,SAAS;YACzB,cAAc,EAAE,SAAS,CAAC,MAAM,CAAC,MAAM,CAAC;YACxC,MAAM,EAAE,EAAE;YACV,MAAM,EAAE,EAAE;SACX,CAAC;IACJ,CAAC;IAED,KAAK,CAAC,MAAM,CAAC,OAAsB;QACjC,OAAO,SAAS,CAAC,MAAM,CAAC,OAAO,CAAC,cAAc,CAAC,CAAC;IAClD,CAAC;CACF;AAED;;;;GAIG;AACH,MAAM,CAAC,KAAK,UAAU,UAAU,CAC9B,MAAkB,EAClB,IAAiB;IAEjB,IAAI,IAAI,EAAE,CAAC;QACT,MAAM,OAAO,GAAG,MAAM,IAAI,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC;QACxC,IAAI,OAAO;YAAE,OAAO,OAAO,CAAC;QAC5B,yDAAyD;QACzD,qDAAqD;QACrD,0DAA0D;QAC1D,sDAAsD;QACtD,MAAM,IAAI,KAAK,CACb,eAAe,IAAI,CAAC,SAAS,0CAA0C,CACxE,CAAC;IACJ,CAAC;IACD,OAAO,IAAI,eAAe,EAAE,CAAC,IAAI,CAAC,MAAM,CAA2B,CAAC;AACtE,CAAC;AAED;;;;;;;;;GASG;AACH,MAAM,CAAC,KAAK,UAAU,YAAY,CAChC,OAAsB,EACtB,IAAiB;IAEjB,IAAI,OAAO,CAAC,SAAS,KAAK,aAAa,EAAE,CAAC;QACxC,OAAO,IAAI,eAAe,EAAE,CAAC,MAAM,CAAC,OAAO,CAAC,CAAC;IAC/C,CAAC;IACD,IAAI,CAAC,IAAI,IAAI,IAAI,CAAC,SAAS,KAAK,OAAO,CAAC,SAAS,EAAE,CAAC;QAClD,MAAM,IAAI,KAAK,CACb,2BAA2B,OAAO,CAAC,SAAS,2CAA2C,CACxF,CAAC;IACJ,CAAC;IACD,MAAM,MAAM,GAAG,MAAM,IAAI,CAAC,MAAM,CAAC,OAAO,CAAC,CAAC;IAC1C,IAAI,CAAC,MAAM,EAAE,CAAC;QACZ,MAAM,IAAI,KAAK,CACb,eAAe,IAAI,CAAC,SAAS,4CAA4C,CAC1E,CAAC;IACJ,CAAC;IACD,OAAO,MAAM,CAAC;AAChB,CAAC"}
@@ -0,0 +1,2 @@
1
+ export * from "./sign.js";
2
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/trust-tasks/index.ts"],"names":[],"mappings":"AAAA,cAAc,WAAW,CAAC"}
@@ -0,0 +1,2 @@
1
+ export * from "./sign.js";
2
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/trust-tasks/index.ts"],"names":[],"mappings":"AAAA,cAAc,WAAW,CAAC"}
@@ -0,0 +1,31 @@
1
+ import type { SigningIdentity } from "../siop/self-issued.js";
2
+ /** A Trust-Task envelope before signing — anything serializable to JSON.
3
+ * `proof` is the only field this module reads/writes. */
4
+ export type TrustTaskEnvelope = Record<string, unknown> & {
5
+ proof?: unknown;
6
+ };
7
+ export interface SignTrustTaskOptions {
8
+ /** Envelope to sign in place. The function returns the same reference for
9
+ * ergonomics; mutates `envelope.proof` and leaves every other field
10
+ * byte-identical (the JCS canonical form must round-trip exactly). */
11
+ envelope: TrustTaskEnvelope;
12
+ /** Holder signing identity — its DID is what the RP attributes the
13
+ * request to, and its `kid` becomes the proof's `verificationMethod`. */
14
+ signing: SigningIdentity;
15
+ /** Proof purpose written into the Data Integrity proof.
16
+ *
17
+ * Defaults to `"assertionMethod"` — the right choice for trust-task
18
+ * envelopes vouching for a claim. Set to `"authentication"` when the
19
+ * signature *is* the holder proving control of an identity rather than
20
+ * attesting to a separate claim — e.g. a VP-framed bootstrap request
21
+ * (the provision-integration flow) or a SIOP-shaped self-attestation. */
22
+ proofPurpose?: "assertionMethod" | "authentication";
23
+ }
24
+ /**
25
+ * Attach an `eddsa-jcs-2022` Data Integrity proof to a Trust-Task envelope
26
+ * and return the same envelope. The signed input is the concatenation of
27
+ * SHA-256(JCS(proofConfig)) and SHA-256(JCS(envelope minus proof)), per
28
+ * https://www.w3.org/TR/vc-di-eddsa/#eddsa-jcs-2022.
29
+ */
30
+ export declare function signTrustTask({ envelope, signing, proofPurpose, }: SignTrustTaskOptions): Promise<TrustTaskEnvelope>;
31
+ //# sourceMappingURL=sign.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"sign.d.ts","sourceRoot":"","sources":["../../src/trust-tasks/sign.ts"],"names":[],"mappings":"AAWA,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,wBAAwB,CAAC;AAE9D;0DAC0D;AAC1D,MAAM,MAAM,iBAAiB,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG;IAAE,KAAK,CAAC,EAAE,OAAO,CAAA;CAAE,CAAC;AAE9E,MAAM,WAAW,oBAAoB;IACnC;;2EAEuE;IACvE,QAAQ,EAAE,iBAAiB,CAAC;IAC5B;8EAC0E;IAC1E,OAAO,EAAE,eAAe,CAAC;IACzB;;;;;;8EAM0E;IAC1E,YAAY,CAAC,EAAE,iBAAiB,GAAG,gBAAgB,CAAC;CACrD;AAED;;;;;GAKG;AACH,wBAAsB,aAAa,CAAC,EAClC,QAAQ,EACR,OAAO,EACP,YAAgC,GACjC,EAAE,oBAAoB,GAAG,OAAO,CAAC,iBAAiB,CAAC,CA2BnD"}
@@ -0,0 +1,141 @@
1
+ // Sign a Trust-Task envelope with a W3C Data Integrity proof
2
+ // (`eddsa-jcs-2022`). The wallet uses this to sign on-behalf-of operations
3
+ // at a Relying Party that authenticates the wallet by its holder did:peer
4
+ // — the proof's `verificationMethod` is the holder's `#key-2` URL, and the
5
+ // RP's server resolves the did:peer to verify.
6
+ //
7
+ // Same signing primitive (Ed25519) and same canonicalization (JCS / RFC
8
+ // 8785) the did-hosting UI uses for its session-key signed trust tasks, so
9
+ // a single AffinidiVerifier on the server-side accepts both flows.
10
+ import { ed25519 } from "@noble/curves/ed25519.js";
11
+ /**
12
+ * Attach an `eddsa-jcs-2022` Data Integrity proof to a Trust-Task envelope
13
+ * and return the same envelope. The signed input is the concatenation of
14
+ * SHA-256(JCS(proofConfig)) and SHA-256(JCS(envelope minus proof)), per
15
+ * https://www.w3.org/TR/vc-di-eddsa/#eddsa-jcs-2022.
16
+ */
17
+ export async function signTrustTask({ envelope, signing, proofPurpose = "assertionMethod", }) {
18
+ const proofConfig = {
19
+ type: "DataIntegrityProof",
20
+ cryptosuite: "eddsa-jcs-2022",
21
+ verificationMethod: signing.kid,
22
+ created: new Date().toISOString(),
23
+ proofPurpose,
24
+ };
25
+ const docCopy = { ...envelope };
26
+ delete docCopy.proof;
27
+ const proofConfigHash = await sha256(jcsCanonicalize(proofConfig));
28
+ const docHash = await sha256(jcsCanonicalize(docCopy));
29
+ const toSign = new Uint8Array(proofConfigHash.length + docHash.length);
30
+ toSign.set(proofConfigHash, 0);
31
+ toSign.set(docHash, proofConfigHash.length);
32
+ const sig = ed25519.sign(toSign, signing.privateKey);
33
+ if (sig.length !== 64) {
34
+ throw new Error(`unexpected Ed25519 signature length: ${sig.length} bytes`);
35
+ }
36
+ proofConfig.proofValue = "z" + base58btcEncode(sig);
37
+ envelope.proof = proofConfig;
38
+ return envelope;
39
+ }
40
+ // ─── JCS (RFC 8785) ───
41
+ // Minified JSON, object keys sorted lexicographically by UTF-16 code unit,
42
+ // strict JSON-only string escaping per ECMA-404. Mirrors the did-hosting-ui
43
+ // `session-key.ts` implementation so wallet-signed and session-signed
44
+ // envelopes hash identically when given equivalent input.
45
+ function jcsCanonicalize(value) {
46
+ const seen = new WeakSet();
47
+ return enc(value);
48
+ function enc(v) {
49
+ if (v === null)
50
+ return "null";
51
+ if (v === true)
52
+ return "true";
53
+ if (v === false)
54
+ return "false";
55
+ if (typeof v === "number") {
56
+ if (!Number.isFinite(v))
57
+ throw new Error("JCS rejects non-finite numbers");
58
+ if (Object.is(v, -0))
59
+ return "0";
60
+ return String(v);
61
+ }
62
+ if (typeof v === "string")
63
+ return encString(v);
64
+ if (Array.isArray(v)) {
65
+ if (seen.has(v))
66
+ throw new Error("circular reference in JCS input");
67
+ seen.add(v);
68
+ const out = "[" + v.map(enc).join(",") + "]";
69
+ seen.delete(v);
70
+ return out;
71
+ }
72
+ if (typeof v === "object" && v !== null) {
73
+ if (seen.has(v))
74
+ throw new Error("circular reference in JCS input");
75
+ seen.add(v);
76
+ const obj = v;
77
+ const keys = Object.keys(obj).sort();
78
+ const parts = keys.map((k) => encString(k) + ":" + enc(obj[k]));
79
+ seen.delete(v);
80
+ return "{" + parts.join(",") + "}";
81
+ }
82
+ throw new Error(`JCS cannot encode value of type ${typeof v}`);
83
+ }
84
+ function encString(s) {
85
+ let out = '"';
86
+ for (let i = 0; i < s.length; i++) {
87
+ const ch = s.charCodeAt(i);
88
+ if (ch === 0x22)
89
+ out += '\\"';
90
+ else if (ch === 0x5c)
91
+ out += "\\\\";
92
+ else if (ch === 0x08)
93
+ out += "\\b";
94
+ else if (ch === 0x0c)
95
+ out += "\\f";
96
+ else if (ch === 0x0a)
97
+ out += "\\n";
98
+ else if (ch === 0x0d)
99
+ out += "\\r";
100
+ else if (ch === 0x09)
101
+ out += "\\t";
102
+ else if (ch < 0x20)
103
+ out += "\\u" + ch.toString(16).padStart(4, "0");
104
+ else
105
+ out += s[i];
106
+ }
107
+ return out + '"';
108
+ }
109
+ }
110
+ // ─── base58btc (Bitcoin alphabet) ───
111
+ // Used as the `z`-prefixed multibase encoding for the Ed25519 `proofValue`.
112
+ const B58_ALPHABET = "123456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz";
113
+ function base58btcEncode(bytes) {
114
+ let zeros = 0;
115
+ while (zeros < bytes.length && bytes[zeros] === 0)
116
+ zeros++;
117
+ const digits = [];
118
+ for (let i = 0; i < bytes.length; i++) {
119
+ let carry = bytes[i];
120
+ for (let j = 0; j < digits.length; j++) {
121
+ carry += digits[j] << 8;
122
+ digits[j] = carry % 58;
123
+ carry = (carry / 58) | 0;
124
+ }
125
+ while (carry > 0) {
126
+ digits.push(carry % 58);
127
+ carry = (carry / 58) | 0;
128
+ }
129
+ }
130
+ let out = "";
131
+ for (let z = 0; z < zeros; z++)
132
+ out += "1";
133
+ for (let i = digits.length - 1; i >= 0; i--)
134
+ out += B58_ALPHABET[digits[i]];
135
+ return out;
136
+ }
137
+ async function sha256(input) {
138
+ const buf = new TextEncoder().encode(input);
139
+ return new Uint8Array(await crypto.subtle.digest("SHA-256", buf));
140
+ }
141
+ //# sourceMappingURL=sign.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"sign.js","sourceRoot":"","sources":["../../src/trust-tasks/sign.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,14 @@
1
+ export interface TimingMark {
2
+ label: string;
3
+ ms: number;
4
+ }
5
+ export interface Stopwatch {
6
+ /** Record a phase: ms elapsed since the previous mark (or creation). */
7
+ mark(label: string): void;
8
+ /** The recorded phase marks, in order. */
9
+ readonly marks: TimingMark[];
10
+ /** Total ms elapsed since the stopwatch was created. */
11
+ total(): number;
12
+ }
13
+ export declare function createStopwatch(): Stopwatch;
14
+ //# sourceMappingURL=timing.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"timing.d.ts","sourceRoot":"","sources":["../../src/util/timing.ts"],"names":[],"mappings":"AAIA,MAAM,WAAW,UAAU;IACzB,KAAK,EAAE,MAAM,CAAC;IACd,EAAE,EAAE,MAAM,CAAC;CACZ;AAED,MAAM,WAAW,SAAS;IACxB,wEAAwE;IACxE,IAAI,CAAC,KAAK,EAAE,MAAM,GAAG,IAAI,CAAC;IAC1B,0CAA0C;IAC1C,QAAQ,CAAC,KAAK,EAAE,UAAU,EAAE,CAAC;IAC7B,wDAAwD;IACxD,KAAK,IAAI,MAAM,CAAC;CACjB;AAED,wBAAgB,eAAe,IAAI,SAAS,CAe3C"}
@@ -0,0 +1,20 @@
1
+ // Lightweight phase timing for the auth flows, so the demo can show how long
2
+ // each step takes. Marks are wall-clock deltas (ms) between successive
3
+ // `mark()` calls; `total()` is elapsed since creation.
4
+ export function createStopwatch() {
5
+ const t0 = Date.now();
6
+ let last = t0;
7
+ const marks = [];
8
+ return {
9
+ marks,
10
+ mark(label) {
11
+ const now = Date.now();
12
+ marks.push({ label, ms: now - last });
13
+ last = now;
14
+ },
15
+ total() {
16
+ return Date.now() - t0;
17
+ },
18
+ };
19
+ }
20
+ //# sourceMappingURL=timing.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"timing.js","sourceRoot":"","sources":["../../src/util/timing.ts"],"names":[],"mappings":"AAAA,6EAA6E;AAC7E,uEAAuE;AACvE,uDAAuD;AAgBvD,MAAM,UAAU,eAAe;IAC7B,MAAM,EAAE,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC;IACtB,IAAI,IAAI,GAAG,EAAE,CAAC;IACd,MAAM,KAAK,GAAiB,EAAE,CAAC;IAC/B,OAAO;QACL,KAAK;QACL,IAAI,CAAC,KAAa;YAChB,MAAM,GAAG,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC;YACvB,KAAK,CAAC,IAAI,CAAC,EAAE,KAAK,EAAE,EAAE,EAAE,GAAG,GAAG,IAAI,EAAE,CAAC,CAAC;YACtC,IAAI,GAAG,GAAG,CAAC;QACb,CAAC;QACD,KAAK;YACH,OAAO,IAAI,CAAC,GAAG,EAAE,GAAG,EAAE,CAAC;QACzB,CAAC;KACF,CAAC;AACJ,CAAC"}
@@ -0,0 +1,19 @@
1
+ import { type VtaAuthInputs } from "./transport.js";
2
+ export interface VaultDeleteRestOptions extends VtaAuthInputs {
3
+ id: string;
4
+ /** Observed `version` for optimistic concurrency. Strongly RECOMMENDED;
5
+ * the maintainer rejects with `vault/delete:version_conflict` on
6
+ * mismatch (with `details.currentVersion` for retry). */
7
+ expectedVersion?: number;
8
+ /** Human-readable rationale recorded in the audit trail. */
9
+ reason?: string;
10
+ }
11
+ export interface VaultDeleteResponse {
12
+ id: string;
13
+ deletedAt: string;
14
+ /** Equals `deletedAt` when the maintainer hard-deletes (M2A.2). Real
15
+ * grace windows arrive with sync (M5). */
16
+ graceUntil: string;
17
+ }
18
+ export declare function vaultDeleteRest(opts: VaultDeleteRestOptions): Promise<VaultDeleteResponse>;
19
+ //# sourceMappingURL=delete.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"delete.d.ts","sourceRoot":"","sources":["../../src/vault/delete.ts"],"names":[],"mappings":"AAOA,OAAO,EAA+B,KAAK,aAAa,EAAE,MAAM,gBAAgB,CAAC;AAKjF,MAAM,WAAW,sBAAuB,SAAQ,aAAa;IAC3D,EAAE,EAAE,MAAM,CAAC;IACX;;8DAE0D;IAC1D,eAAe,CAAC,EAAE,MAAM,CAAC;IACzB,4DAA4D;IAC5D,MAAM,CAAC,EAAE,MAAM,CAAC;CACjB;AAED,MAAM,WAAW,mBAAmB;IAClC,EAAE,EAAE,MAAM,CAAC;IACX,SAAS,EAAE,MAAM,CAAC;IAClB;+CAC2C;IAC3C,UAAU,EAAE,MAAM,CAAC;CACpB;AAED,wBAAsB,eAAe,CACnC,IAAI,EAAE,sBAAsB,GAC3B,OAAO,CAAC,mBAAmB,CAAC,CAyB9B"}
@@ -0,0 +1,35 @@
1
+ // Vault — delete (M2A.5).
2
+ //
3
+ // Posts a `https://trusttasks.org/spec/vault/delete/0.1` envelope to the
4
+ // VTA's trust-task dispatcher. No envelope / sealing — delete carries
5
+ // only id + optimistic-concurrency token, all visible to anyone with the
6
+ // bearer.
7
+ import { getVtaBearer, postTrustTask } from "./transport.js";
8
+ const TASK_VAULT_DELETE = "https://trusttasks.org/spec/vault/delete/0.1";
9
+ const TASK_VAULT_DELETE_RESPONSE = "https://trusttasks.org/spec/vault/delete/0.1#response";
10
+ export async function vaultDeleteRest(opts) {
11
+ const bearer = await getVtaBearer({
12
+ baseUrl: opts.baseUrl,
13
+ holder: opts.holder,
14
+ service: opts.service,
15
+ ...(opts.fetch ? { fetch: opts.fetch } : {}),
16
+ });
17
+ return postTrustTask({
18
+ baseUrl: opts.baseUrl,
19
+ bearer,
20
+ envelope: {
21
+ type: TASK_VAULT_DELETE,
22
+ payload: {
23
+ id: opts.id,
24
+ ...(opts.expectedVersion !== undefined ? { expectedVersion: opts.expectedVersion } : {}),
25
+ ...(opts.reason ? { reason: opts.reason } : {}),
26
+ },
27
+ issuer: opts.holder.did,
28
+ recipient: opts.service.did,
29
+ },
30
+ expectedResponseType: TASK_VAULT_DELETE_RESPONSE,
31
+ operationLabel: "vault/delete/0.1",
32
+ ...(opts.fetch ? { fetch: opts.fetch } : {}),
33
+ });
34
+ }
35
+ //# sourceMappingURL=delete.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"delete.js","sourceRoot":"","sources":["../../src/vault/delete.ts"],"names":[],"mappings":"AAAA,0BAA0B;AAC1B,EAAE;AACF,yEAAyE;AACzE,sEAAsE;AACtE,yEAAyE;AACzE,UAAU;AAEV,OAAO,EAAE,YAAY,EAAE,aAAa,EAAsB,MAAM,gBAAgB,CAAC;AAEjF,MAAM,iBAAiB,GAAG,8CAA8C,CAAC;AACzE,MAAM,0BAA0B,GAAG,uDAAuD,CAAC;AAoB3F,MAAM,CAAC,KAAK,UAAU,eAAe,CACnC,IAA4B;IAE5B,MAAM,MAAM,GAAG,MAAM,YAAY,CAAC;QAChC,OAAO,EAAE,IAAI,CAAC,OAAO;QACrB,MAAM,EAAE,IAAI,CAAC,MAAM;QACnB,OAAO,EAAE,IAAI,CAAC,OAAO;QACrB,GAAG,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,EAAE,KAAK,EAAE,IAAI,CAAC,KAAK,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;KAC7C,CAAC,CAAC;IAEH,OAAO,aAAa,CAAsB;QACxC,OAAO,EAAE,IAAI,CAAC,OAAO;QACrB,MAAM;QACN,QAAQ,EAAE;YACR,IAAI,EAAE,iBAAiB;YACvB,OAAO,EAAE;gBACP,EAAE,EAAE,IAAI,CAAC,EAAE;gBACX,GAAG,CAAC,IAAI,CAAC,eAAe,KAAK,SAAS,CAAC,CAAC,CAAC,EAAE,eAAe,EAAE,IAAI,CAAC,eAAe,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;gBACxF,GAAG,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,MAAM,EAAE,IAAI,CAAC,MAAM,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;aAChD;YACD,MAAM,EAAE,IAAI,CAAC,MAAM,CAAC,GAAG;YACvB,SAAS,EAAE,IAAI,CAAC,OAAO,CAAC,GAAG;SAC5B;QACD,oBAAoB,EAAE,0BAA0B;QAChD,cAAc,EAAE,kBAAkB;QAClC,GAAG,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,EAAE,KAAK,EAAE,IAAI,CAAC,KAAK,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;KAC7C,CAAC,CAAC;AACL,CAAC"}
@@ -0,0 +1,8 @@
1
+ export * from "./list.js";
2
+ export * from "./upsert.js";
3
+ export * from "./delete.js";
4
+ export * from "./release.js";
5
+ export * from "./proxy-login.js";
6
+ export * from "./sign-trust-task.js";
7
+ export type { VaultTaskRequest, VtaAuthInputs } from "./transport.js";
8
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/vault/index.ts"],"names":[],"mappings":"AAAA,cAAc,WAAW,CAAC;AAC1B,cAAc,aAAa,CAAC;AAC5B,cAAc,aAAa,CAAC;AAC5B,cAAc,cAAc,CAAC;AAC7B,cAAc,kBAAkB,CAAC;AACjC,cAAc,sBAAsB,CAAC;AACrC,YAAY,EAAE,gBAAgB,EAAE,aAAa,EAAE,MAAM,gBAAgB,CAAC"}
@@ -0,0 +1,7 @@
1
+ export * from "./list.js";
2
+ export * from "./upsert.js";
3
+ export * from "./delete.js";
4
+ export * from "./release.js";
5
+ export * from "./proxy-login.js";
6
+ export * from "./sign-trust-task.js";
7
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/vault/index.ts"],"names":[],"mappings":"AAAA,cAAc,WAAW,CAAC;AAC1B,cAAc,aAAa,CAAC;AAC5B,cAAc,aAAa,CAAC;AAC5B,cAAc,cAAc,CAAC;AAC7B,cAAc,kBAAkB,CAAC;AACjC,cAAc,sBAAsB,CAAC"}
@@ -0,0 +1,96 @@
1
+ import { type Identity } from "../didcomm/index.js";
2
+ import type { RemoteDidcommEndpoint } from "../vta/didcomm.js";
3
+ /** Discriminator that mirrors the canonical SecretKind enum. */
4
+ export type SecretKind = "password" | "passkey" | "oauth-tokens" | "did-self-issued" | "didcomm-peer" | "bearer-token" | "ssh-key" | "custom";
5
+ /** Tagged union — see `vault/_shared/0.1/vault-entry.schema.json` $defs/SiteTarget. */
6
+ export type SiteTarget = {
7
+ kind: "web-origin";
8
+ origin: string;
9
+ } | {
10
+ kind: "did";
11
+ did: string;
12
+ } | {
13
+ kind: "ios-app";
14
+ bundleId: string;
15
+ teamId?: string;
16
+ } | {
17
+ kind: "android-app";
18
+ packageName: string;
19
+ sha256CertFingerprints: string[];
20
+ };
21
+ /** Metadata view of a single vault entry. No secret bytes. */
22
+ export interface VaultEntry {
23
+ id: string;
24
+ contextId: string;
25
+ targets: SiteTarget[];
26
+ label: string;
27
+ secretKind: SecretKind;
28
+ tags?: string[];
29
+ notes?: string;
30
+ favicon?: string;
31
+ selectors?: string[];
32
+ customFieldNames?: string[];
33
+ attachments?: Array<{
34
+ id: string;
35
+ name: string;
36
+ sizeBytes: number;
37
+ sha256: string;
38
+ contentType?: string;
39
+ }>;
40
+ expiresAt?: string;
41
+ breachedAt?: string;
42
+ passwordChangedAt?: string;
43
+ createdAt: string;
44
+ createdBy?: string;
45
+ updatedAt: string;
46
+ updatedBy?: string;
47
+ lastUsedAt?: string;
48
+ version: number;
49
+ /** Cached DID the entry acts AS for DID-shaped flows. Mirrors the
50
+ * `did` field of `did-self-issued` / `didcomm-peer` secrets;
51
+ * absent for kinds without a DID concept. Maintainer-derived from
52
+ * the secret at every upsert — a producer-supplied value on the
53
+ * wire is ignored. */
54
+ principalDid?: string;
55
+ }
56
+ /** Filters accepted by vault/list/0.1. All AND-combined. */
57
+ export interface VaultListFilter {
58
+ contextId?: string;
59
+ targetOriginPrefix?: string;
60
+ targetDid?: string;
61
+ targetIosBundleId?: string;
62
+ targetAndroidPackage?: string;
63
+ secretKind?: SecretKind;
64
+ tag?: string;
65
+ usedSince?: string;
66
+ neverUsed?: boolean;
67
+ expiresBefore?: string;
68
+ breached?: boolean;
69
+ pageSize?: number;
70
+ cursor?: string;
71
+ }
72
+ export interface VaultListResponse {
73
+ entries: VaultEntry[];
74
+ truncated: boolean;
75
+ cursor?: string;
76
+ redactedFields?: string[];
77
+ }
78
+ export interface VaultListRestOptions {
79
+ /** VTA REST base URL — from the connection state's `restBaseUrl`. */
80
+ baseUrl: string;
81
+ /** Authcrypt sender (the holder's DIDComm identity post-onboarding swap). */
82
+ holder: Identity;
83
+ /** VTA's keyAgreement endpoint (resolved via `resolveKeyAgreement`). */
84
+ service: RemoteDidcommEndpoint;
85
+ /** Filters (omit for "all entries the caller can read"). */
86
+ filter?: VaultListFilter;
87
+ /** fetch impl (defaults to global). */
88
+ fetch?: typeof fetch;
89
+ }
90
+ /**
91
+ * Authenticate to the VTA over REST + DIDComm-authcrypt, then post the
92
+ * canonical vault/list/0.1 Trust Task envelope and return the parsed
93
+ * entries. Single round-trip's worth of auth — no token cache in M1.
94
+ */
95
+ export declare function vaultListRest(opts: VaultListRestOptions): Promise<VaultListResponse>;
96
+ //# sourceMappingURL=list.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"list.d.ts","sourceRoot":"","sources":["../../src/vault/list.ts"],"names":[],"mappings":"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"}