@earendil-works/chord 1.0.4 → 1.2.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 (186) hide show
  1. package/CHANGELOG.md +20 -0
  2. package/README.md +77 -194
  3. package/dist/cell.d.ts +101 -0
  4. package/dist/cell.d.ts.map +1 -0
  5. package/dist/cell.js +316 -0
  6. package/dist/cell.js.map +1 -0
  7. package/dist/cluster.d.ts +26 -0
  8. package/dist/cluster.d.ts.map +1 -0
  9. package/dist/cluster.js +214 -0
  10. package/dist/cluster.js.map +1 -0
  11. package/dist/connection.d.ts +157 -0
  12. package/dist/connection.d.ts.map +1 -0
  13. package/dist/connection.js +757 -0
  14. package/dist/connection.js.map +1 -0
  15. package/dist/context/index.d.ts +12 -1
  16. package/dist/context/index.d.ts.map +1 -1
  17. package/dist/context/index.js.map +1 -1
  18. package/dist/contract.d.ts +133 -0
  19. package/dist/contract.d.ts.map +1 -0
  20. package/dist/contract.js +157 -0
  21. package/dist/contract.js.map +1 -0
  22. package/dist/declare.d.ts +70 -0
  23. package/dist/declare.d.ts.map +1 -0
  24. package/dist/declare.js +22 -0
  25. package/dist/declare.js.map +1 -0
  26. package/dist/delta/apply-immutable-trusted.js.map +1 -1
  27. package/dist/delta/diff.d.ts +1 -1
  28. package/dist/delta/diff.d.ts.map +1 -1
  29. package/dist/delta/diff.js.map +1 -1
  30. package/dist/delta/index.d.ts +2 -2
  31. package/dist/delta/index.d.ts.map +1 -1
  32. package/dist/delta/index.js +41 -0
  33. package/dist/delta/index.js.map +1 -1
  34. package/dist/delta/revision-validator.d.ts +1 -1
  35. package/dist/delta/revision-validator.d.ts.map +1 -1
  36. package/dist/delta/revision-validator.js.map +1 -1
  37. package/dist/delta/tracker.d.ts +1 -1
  38. package/dist/delta/tracker.d.ts.map +1 -1
  39. package/dist/delta/tracker.js +40 -4
  40. package/dist/delta/tracker.js.map +1 -1
  41. package/dist/errors.d.ts +27 -0
  42. package/dist/errors.d.ts.map +1 -0
  43. package/dist/errors.js +44 -0
  44. package/dist/errors.js.map +1 -0
  45. package/dist/host.d.ts +254 -0
  46. package/dist/host.d.ts.map +1 -0
  47. package/dist/host.js +795 -0
  48. package/dist/host.js.map +1 -0
  49. package/dist/index.d.ts +17 -10
  50. package/dist/index.d.ts.map +1 -1
  51. package/dist/index.js +8 -8
  52. package/dist/index.js.map +1 -1
  53. package/dist/json.d.ts +9 -1
  54. package/dist/json.d.ts.map +1 -1
  55. package/dist/json.js.map +1 -1
  56. package/dist/link.d.ts +72 -0
  57. package/dist/link.d.ts.map +1 -0
  58. package/dist/link.js +169 -0
  59. package/dist/link.js.map +1 -0
  60. package/dist/loader.d.ts +4 -0
  61. package/dist/loader.d.ts.map +1 -0
  62. package/dist/loader.js +68 -0
  63. package/dist/loader.js.map +1 -0
  64. package/dist/manager.d.ts +115 -0
  65. package/dist/manager.d.ts.map +1 -0
  66. package/dist/manager.js +319 -0
  67. package/dist/manager.js.map +1 -0
  68. package/dist/node.d.ts +3 -4
  69. package/dist/node.d.ts.map +1 -1
  70. package/dist/node.js +3 -2
  71. package/dist/node.js.map +1 -1
  72. package/dist/publish.d.ts +5 -0
  73. package/dist/publish.d.ts.map +1 -0
  74. package/dist/publish.js +40 -0
  75. package/dist/publish.js.map +1 -0
  76. package/dist/record.d.ts +320 -0
  77. package/dist/record.d.ts.map +1 -0
  78. package/dist/record.js +1292 -0
  79. package/dist/record.js.map +1 -0
  80. package/dist/registry.d.ts +25 -0
  81. package/dist/registry.d.ts.map +1 -0
  82. package/dist/registry.js +6 -0
  83. package/dist/registry.js.map +1 -0
  84. package/dist/reload.d.ts +118 -0
  85. package/dist/reload.d.ts.map +1 -0
  86. package/dist/reload.js +589 -0
  87. package/dist/reload.js.map +1 -0
  88. package/dist/remote.d.ts +70 -0
  89. package/dist/remote.d.ts.map +1 -0
  90. package/dist/remote.js +308 -0
  91. package/dist/remote.js.map +1 -0
  92. package/dist/schema.d.ts +21 -0
  93. package/dist/schema.d.ts.map +1 -0
  94. package/dist/schema.js +228 -0
  95. package/dist/schema.js.map +1 -0
  96. package/dist/state.d.ts +92 -0
  97. package/dist/state.d.ts.map +1 -0
  98. package/dist/{services/state.js → state.js} +28 -138
  99. package/dist/state.js.map +1 -0
  100. package/dist/types.d.ts +62 -262
  101. package/dist/types.d.ts.map +1 -1
  102. package/dist/types.js.map +1 -1
  103. package/dist/websocket.d.ts +16 -0
  104. package/dist/websocket.d.ts.map +1 -0
  105. package/dist/websocket.js +15 -0
  106. package/dist/websocket.js.map +1 -0
  107. package/dist/wire.d.ts +135 -0
  108. package/dist/wire.d.ts.map +1 -0
  109. package/dist/wire.js +112 -0
  110. package/dist/wire.js.map +1 -0
  111. package/docs/guide.md +750 -0
  112. package/docs/spec.md +261 -0
  113. package/docs/tutorial.md +909 -0
  114. package/package.json +10 -11
  115. package/src/delta/README.md +5 -3
  116. package/dist/api.d.ts +0 -20
  117. package/dist/api.d.ts.map +0 -1
  118. package/dist/api.js +0 -77
  119. package/dist/api.js.map +0 -1
  120. package/dist/bundler.d.ts +0 -6
  121. package/dist/bundler.d.ts.map +0 -1
  122. package/dist/bundler.js +0 -3
  123. package/dist/bundler.js.map +0 -1
  124. package/dist/facets/host.d.ts +0 -12
  125. package/dist/facets/host.d.ts.map +0 -1
  126. package/dist/facets/host.js +0 -763
  127. package/dist/facets/host.js.map +0 -1
  128. package/dist/facets/loader.d.ts +0 -3
  129. package/dist/facets/loader.d.ts.map +0 -1
  130. package/dist/facets/loader.js +0 -5
  131. package/dist/facets/loader.js.map +0 -1
  132. package/dist/node/bundle-loader.d.ts +0 -30
  133. package/dist/node/bundle-loader.d.ts.map +0 -1
  134. package/dist/node/bundle-loader.js +0 -377
  135. package/dist/node/bundle-loader.js.map +0 -1
  136. package/dist/node/bundle.d.ts +0 -26
  137. package/dist/node/bundle.d.ts.map +0 -1
  138. package/dist/node/bundle.js +0 -183
  139. package/dist/node/bundle.js.map +0 -1
  140. package/dist/node/manifest.d.ts +0 -36
  141. package/dist/node/manifest.d.ts.map +0 -1
  142. package/dist/node/manifest.js +0 -6
  143. package/dist/node/manifest.js.map +0 -1
  144. package/dist/node/package.d.ts +0 -15
  145. package/dist/node/package.d.ts.map +0 -1
  146. package/dist/node/package.js +0 -199
  147. package/dist/node/package.js.map +0 -1
  148. package/dist/services/consumer.d.ts +0 -11
  149. package/dist/services/consumer.d.ts.map +0 -1
  150. package/dist/services/consumer.js +0 -585
  151. package/dist/services/consumer.js.map +0 -1
  152. package/dist/services/errors.d.ts +0 -8
  153. package/dist/services/errors.d.ts.map +0 -1
  154. package/dist/services/errors.js +0 -22
  155. package/dist/services/errors.js.map +0 -1
  156. package/dist/services/handle.d.ts +0 -15
  157. package/dist/services/handle.d.ts.map +0 -1
  158. package/dist/services/handle.js +0 -101
  159. package/dist/services/handle.js.map +0 -1
  160. package/dist/services/instances.d.ts +0 -26
  161. package/dist/services/instances.d.ts.map +0 -1
  162. package/dist/services/instances.js +0 -140
  163. package/dist/services/instances.js.map +0 -1
  164. package/dist/services/loopback.d.ts +0 -5
  165. package/dist/services/loopback.d.ts.map +0 -1
  166. package/dist/services/loopback.js +0 -15
  167. package/dist/services/loopback.js.map +0 -1
  168. package/dist/services/provider.d.ts +0 -37
  169. package/dist/services/provider.d.ts.map +0 -1
  170. package/dist/services/provider.js +0 -521
  171. package/dist/services/provider.js.map +0 -1
  172. package/dist/services/state-codec.d.ts +0 -15
  173. package/dist/services/state-codec.d.ts.map +0 -1
  174. package/dist/services/state-codec.js +0 -133
  175. package/dist/services/state-codec.js.map +0 -1
  176. package/dist/services/state-internals.d.ts +0 -13
  177. package/dist/services/state-internals.d.ts.map +0 -1
  178. package/dist/services/state-internals.js +0 -10
  179. package/dist/services/state-internals.js.map +0 -1
  180. package/dist/services/state.d.ts +0 -28
  181. package/dist/services/state.d.ts.map +0 -1
  182. package/dist/services/state.js.map +0 -1
  183. package/dist/services/wire.d.ts +0 -63
  184. package/dist/services/wire.d.ts.map +0 -1
  185. package/dist/services/wire.js +0 -186
  186. package/dist/services/wire.js.map +0 -1
package/dist/wire.d.ts ADDED
@@ -0,0 +1,135 @@
1
+ import type { Description } from "./contract.ts";
2
+ import type { WireOp } from "./delta/index.ts";
3
+ import { ChordError, type ChordErrorCode } from "./errors.ts";
4
+ import type { Principal } from "./types.ts";
5
+ export interface RootRef {
6
+ readonly rootId: string;
7
+ readonly epoch: number;
8
+ }
9
+ export interface WireError {
10
+ readonly code: ChordErrorCode;
11
+ readonly message: string;
12
+ readonly reason?: string;
13
+ }
14
+ export interface WireReloadOptions {
15
+ readonly remove?: readonly string[];
16
+ readonly gateDeadline?: number;
17
+ readonly retireDeadline?: number;
18
+ }
19
+ /** A child's prepared reload, sent with its vote (same fields as `ReloadReport`, without children). */
20
+ export interface WireReloadReport {
21
+ readonly epoch: number;
22
+ readonly previous: number;
23
+ readonly changed: readonly string[];
24
+ readonly removed: readonly string[];
25
+ readonly prepared: readonly string[];
26
+ readonly gated: readonly string[];
27
+ }
28
+ export type Frame = {
29
+ readonly t: "hello";
30
+ readonly name: string;
31
+ readonly kind: "host" | "client";
32
+ readonly epoch: number;
33
+ } | {
34
+ readonly t: "hold";
35
+ readonly id: number;
36
+ /** Target host name. */
37
+ readonly at: string;
38
+ /** The consumer's contract token; the provider checks that it covers it. */
39
+ readonly token: Description;
40
+ readonly input: unknown;
41
+ /** A forwarded principal. Honored only on frames from the parent link. */
42
+ readonly principal?: Principal;
43
+ /** Set by a relay when the hold originates from a client (browser): not a reload participant. */
44
+ readonly client?: boolean;
45
+ } | {
46
+ readonly t: "release";
47
+ readonly id: number;
48
+ } | {
49
+ readonly t: "shape";
50
+ readonly id: number;
51
+ readonly kind?: string;
52
+ readonly members: readonly string[];
53
+ readonly contract: string;
54
+ readonly epoch: number;
55
+ } | {
56
+ readonly t: "gone";
57
+ readonly id: number;
58
+ readonly error: WireError;
59
+ } | {
60
+ readonly t: "call";
61
+ readonly id: number;
62
+ readonly hold: number;
63
+ readonly member: string;
64
+ readonly args: unknown;
65
+ /** Absent: the receiving host starts a root (browsers never carry roots). */
66
+ readonly root?: RootRef;
67
+ } | {
68
+ readonly t: "result";
69
+ readonly id: number;
70
+ readonly value?: unknown;
71
+ readonly error?: WireError;
72
+ } | {
73
+ readonly t: "cancel";
74
+ readonly id: number;
75
+ } | {
76
+ readonly t: "sub";
77
+ readonly id: number;
78
+ readonly hold: number;
79
+ readonly member: string;
80
+ } | {
81
+ readonly t: "unsub";
82
+ readonly id: number;
83
+ } | {
84
+ readonly t: "state";
85
+ readonly id: number;
86
+ readonly snap?: unknown;
87
+ readonly reset?: unknown;
88
+ /** Encoded with the subscription's delta encoder. */
89
+ readonly ops?: readonly WireOp[];
90
+ readonly error?: WireError;
91
+ } | {
92
+ readonly t: "ping";
93
+ readonly n: number;
94
+ } | {
95
+ readonly t: "pong";
96
+ readonly n: number;
97
+ } | {
98
+ readonly t: "bye";
99
+ readonly reason?: string;
100
+ }
101
+ /** The root ended at its origin: its leases on records end (sent on every link the root's calls used). */
102
+ | {
103
+ readonly t: "root_end";
104
+ readonly rootId: string;
105
+ } | {
106
+ readonly t: "invalidate";
107
+ readonly pattern: Readonly<Record<string, unknown>>;
108
+ } | {
109
+ readonly t: "prepare";
110
+ readonly reload: number;
111
+ readonly epoch: number;
112
+ readonly plugins: readonly string[];
113
+ readonly options: WireReloadOptions;
114
+ } | {
115
+ readonly t: "vote";
116
+ readonly reload: number;
117
+ readonly error?: WireError;
118
+ readonly report?: WireReloadReport;
119
+ } | {
120
+ readonly t: "commit";
121
+ readonly reload: number;
122
+ }
123
+ /** The parent dropped `epoch`: roots of it may still come from there no longer. */
124
+ | {
125
+ readonly t: "retire";
126
+ readonly epoch: number;
127
+ } | {
128
+ readonly t: "abort";
129
+ readonly reload: number;
130
+ };
131
+ export declare function toWireError(error: unknown): WireError;
132
+ export declare const fromWireError: (error: WireError) => ChordError;
133
+ /** A frame that passes structural validation; anything else is a protocol violation. */
134
+ export declare const isFrame: (value: unknown) => value is Frame;
135
+ //# sourceMappingURL=wire.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"wire.d.ts","sourceRoot":"","sources":["../src/wire.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,eAAe,CAAC;AACjD,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,kBAAkB,CAAC;AAC/C,OAAO,EAAE,UAAU,EAAE,KAAK,cAAc,EAAE,MAAM,aAAa,CAAC;AAC9D,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,YAAY,CAAC;AAQ5C,MAAM,WAAW,OAAO;IACvB,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;IACxB,QAAQ,CAAC,KAAK,EAAE,MAAM,CAAC;CACvB;AAED,MAAM,WAAW,SAAS;IACzB,QAAQ,CAAC,IAAI,EAAE,cAAc,CAAC;IAC9B,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC;IACzB,QAAQ,CAAC,MAAM,CAAC,EAAE,MAAM,CAAC;CACzB;AAED,MAAM,WAAW,iBAAiB;IACjC,QAAQ,CAAC,MAAM,CAAC,EAAE,SAAS,MAAM,EAAE,CAAC;IACpC,QAAQ,CAAC,YAAY,CAAC,EAAE,MAAM,CAAC;IAC/B,QAAQ,CAAC,cAAc,CAAC,EAAE,MAAM,CAAC;CACjC;AAED,uGAAuG;AACvG,MAAM,WAAW,gBAAgB;IAChC,QAAQ,CAAC,KAAK,EAAE,MAAM,CAAC;IACvB,QAAQ,CAAC,QAAQ,EAAE,MAAM,CAAC;IAC1B,QAAQ,CAAC,OAAO,EAAE,SAAS,MAAM,EAAE,CAAC;IACpC,QAAQ,CAAC,OAAO,EAAE,SAAS,MAAM,EAAE,CAAC;IACpC,QAAQ,CAAC,QAAQ,EAAE,SAAS,MAAM,EAAE,CAAC;IACrC,QAAQ,CAAC,KAAK,EAAE,SAAS,MAAM,EAAE,CAAC;CAClC;AAED,MAAM,MAAM,KAAK,GACd;IAAE,QAAQ,CAAC,CAAC,EAAE,OAAO,CAAC;IAAC,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IAAC,QAAQ,CAAC,IAAI,EAAE,MAAM,GAAG,QAAQ,CAAC;IAAC,QAAQ,CAAC,KAAK,EAAE,MAAM,CAAA;CAAE,GACxG;IACA,QAAQ,CAAC,CAAC,EAAE,MAAM,CAAC;IACnB,QAAQ,CAAC,EAAE,EAAE,MAAM,CAAC;IACpB,wBAAwB;IACxB,QAAQ,CAAC,EAAE,EAAE,MAAM,CAAC;IACpB,4EAA4E;IAC5E,QAAQ,CAAC,KAAK,EAAE,WAAW,CAAC;IAC5B,QAAQ,CAAC,KAAK,EAAE,OAAO,CAAC;IACxB,0EAA0E;IAC1E,QAAQ,CAAC,SAAS,CAAC,EAAE,SAAS,CAAC;IAC/B,iGAAiG;IACjG,QAAQ,CAAC,MAAM,CAAC,EAAE,OAAO,CAAC;CACzB,GACD;IAAE,QAAQ,CAAC,CAAC,EAAE,SAAS,CAAC;IAAC,QAAQ,CAAC,EAAE,EAAE,MAAM,CAAA;CAAE,GAC9C;IACA,QAAQ,CAAC,CAAC,EAAE,OAAO,CAAC;IACpB,QAAQ,CAAC,EAAE,EAAE,MAAM,CAAC;IACpB,QAAQ,CAAC,IAAI,CAAC,EAAE,MAAM,CAAC;IACvB,QAAQ,CAAC,OAAO,EAAE,SAAS,MAAM,EAAE,CAAC;IACpC,QAAQ,CAAC,QAAQ,EAAE,MAAM,CAAC;IAC1B,QAAQ,CAAC,KAAK,EAAE,MAAM,CAAC;CACtB,GACD;IAAE,QAAQ,CAAC,CAAC,EAAE,MAAM,CAAC;IAAC,QAAQ,CAAC,EAAE,EAAE,MAAM,CAAC;IAAC,QAAQ,CAAC,KAAK,EAAE,SAAS,CAAA;CAAE,GACtE;IACA,QAAQ,CAAC,CAAC,EAAE,MAAM,CAAC;IACnB,QAAQ,CAAC,EAAE,EAAE,MAAM,CAAC;IACpB,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;IACxB,QAAQ,CAAC,IAAI,EAAE,OAAO,CAAC;IACvB,6EAA6E;IAC7E,QAAQ,CAAC,IAAI,CAAC,EAAE,OAAO,CAAC;CACvB,GACD;IAAE,QAAQ,CAAC,CAAC,EAAE,QAAQ,CAAC;IAAC,QAAQ,CAAC,EAAE,EAAE,MAAM,CAAC;IAAC,QAAQ,CAAC,KAAK,CAAC,EAAE,OAAO,CAAC;IAAC,QAAQ,CAAC,KAAK,CAAC,EAAE,SAAS,CAAA;CAAE,GACnG;IAAE,QAAQ,CAAC,CAAC,EAAE,QAAQ,CAAC;IAAC,QAAQ,CAAC,EAAE,EAAE,MAAM,CAAA;CAAE,GAC7C;IAAE,QAAQ,CAAC,CAAC,EAAE,KAAK,CAAC;IAAC,QAAQ,CAAC,EAAE,EAAE,MAAM,CAAC;IAAC,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IAAC,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAA;CAAE,GAC1F;IAAE,QAAQ,CAAC,CAAC,EAAE,OAAO,CAAC;IAAC,QAAQ,CAAC,EAAE,EAAE,MAAM,CAAA;CAAE,GAC5C;IACA,QAAQ,CAAC,CAAC,EAAE,OAAO,CAAC;IACpB,QAAQ,CAAC,EAAE,EAAE,MAAM,CAAC;IACpB,QAAQ,CAAC,IAAI,CAAC,EAAE,OAAO,CAAC;IACxB,QAAQ,CAAC,KAAK,CAAC,EAAE,OAAO,CAAC;IACzB,qDAAqD;IACrD,QAAQ,CAAC,GAAG,CAAC,EAAE,SAAS,MAAM,EAAE,CAAC;IACjC,QAAQ,CAAC,KAAK,CAAC,EAAE,SAAS,CAAC;CAC1B,GACD;IAAE,QAAQ,CAAC,CAAC,EAAE,MAAM,CAAC;IAAC,QAAQ,CAAC,CAAC,EAAE,MAAM,CAAA;CAAE,GAC1C;IAAE,QAAQ,CAAC,CAAC,EAAE,MAAM,CAAC;IAAC,QAAQ,CAAC,CAAC,EAAE,MAAM,CAAA;CAAE,GAC1C;IAAE,QAAQ,CAAC,CAAC,EAAE,KAAK,CAAC;IAAC,QAAQ,CAAC,MAAM,CAAC,EAAE,MAAM,CAAA;CAAE;AACjD,0GAA0G;GACxG;IAAE,QAAQ,CAAC,CAAC,EAAE,UAAU,CAAC;IAAC,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAA;CAAE,GACnD;IAAE,QAAQ,CAAC,CAAC,EAAE,YAAY,CAAC;IAAC,QAAQ,CAAC,OAAO,EAAE,QAAQ,CAAC,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC,CAAA;CAAE,GACjF;IACA,QAAQ,CAAC,CAAC,EAAE,SAAS,CAAC;IACtB,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;IACxB,QAAQ,CAAC,KAAK,EAAE,MAAM,CAAC;IACvB,QAAQ,CAAC,OAAO,EAAE,SAAS,MAAM,EAAE,CAAC;IACpC,QAAQ,CAAC,OAAO,EAAE,iBAAiB,CAAC;CACnC,GACD;IAAE,QAAQ,CAAC,CAAC,EAAE,MAAM,CAAC;IAAC,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;IAAC,QAAQ,CAAC,KAAK,CAAC,EAAE,SAAS,CAAC;IAAC,QAAQ,CAAC,MAAM,CAAC,EAAE,gBAAgB,CAAA;CAAE,GAC/G;IAAE,QAAQ,CAAC,CAAC,EAAE,QAAQ,CAAC;IAAC,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAA;CAAE;AACnD,mFAAmF;GACjF;IAAE,QAAQ,CAAC,CAAC,EAAE,QAAQ,CAAC;IAAC,QAAQ,CAAC,KAAK,EAAE,MAAM,CAAA;CAAE,GAChD;IAAE,QAAQ,CAAC,CAAC,EAAE,OAAO,CAAC;IAAC,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAA;CAAE,CAAC;AAEpD,wBAAgB,WAAW,CAAC,KAAK,EAAE,OAAO,GAAG,SAAS,CAOrD;AAED,eAAO,MAAM,aAAa,UAAW,SAAS,KAAG,UACyD,CAAC;AAwG3G,wFAAwF;AACxF,eAAO,MAAM,OAAO,UAAW,OAAO,KAAG,KAAK,IAAI,KAAwC,CAAC"}
package/dist/wire.js ADDED
@@ -0,0 +1,112 @@
1
+ import { Type } from "typebox";
2
+ import { Value } from "typebox/value";
3
+ import { ChordError } from "./errors.js";
4
+ export function toWireError(error) {
5
+ if (error instanceof ChordError) {
6
+ return error.reason === undefined
7
+ ? { code: error.code, message: error.message }
8
+ : { code: error.code, message: error.message, reason: error.reason };
9
+ }
10
+ return { code: "unavailable", message: error instanceof Error ? error.message : String(error) };
11
+ }
12
+ export const fromWireError = (error) => new ChordError(error.code, error.message.replace(/^[a-z_]+(\/[a-z_]+)?: /, ""), { reason: error.reason });
13
+ // ─── validation ──────────────────────────────────────────────────────────────
14
+ const Id = Type.Integer({ minimum: 1 });
15
+ const Name = Type.String({ minLength: 1 });
16
+ const Root = Type.Object({ rootId: Name, epoch: Type.Integer({ minimum: 1 }) });
17
+ const ErrorShape = Type.Object({ code: Type.String(), message: Type.String(), reason: Type.Optional(Type.String()) });
18
+ const Reload = Type.Integer({ minimum: 1 });
19
+ /** Structural schema of every frame. Payloads (args, values, ops) are checked where they are used. */
20
+ const FrameSchema = Type.Union([
21
+ Type.Object({
22
+ t: Type.Literal("hello"),
23
+ name: Name,
24
+ kind: Type.Union([Type.Literal("host"), Type.Literal("client")]),
25
+ epoch: Type.Integer({ minimum: 0 }),
26
+ }),
27
+ Type.Object({
28
+ t: Type.Literal("hold"),
29
+ id: Id,
30
+ at: Name,
31
+ token: Type.Object({
32
+ name: Name,
33
+ scope: Type.String(),
34
+ version: Type.Integer(),
35
+ input: Type.Unknown(),
36
+ variants: Type.Record(Type.String(), Type.Unknown()),
37
+ }),
38
+ input: Type.Unknown(),
39
+ principal: Type.Optional(Type.Unknown()),
40
+ client: Type.Optional(Type.Boolean()),
41
+ }),
42
+ Type.Object({ t: Type.Literal("release"), id: Id }),
43
+ Type.Object({
44
+ t: Type.Literal("shape"),
45
+ id: Id,
46
+ kind: Type.Optional(Type.String()),
47
+ members: Type.Array(Type.String()),
48
+ contract: Type.String(),
49
+ epoch: Type.Integer(),
50
+ }),
51
+ Type.Object({ t: Type.Literal("gone"), id: Id, error: ErrorShape }),
52
+ Type.Object({
53
+ t: Type.Literal("call"),
54
+ id: Id,
55
+ hold: Id,
56
+ member: Name,
57
+ args: Type.Unknown(),
58
+ root: Type.Optional(Root),
59
+ }),
60
+ Type.Object({
61
+ t: Type.Literal("result"),
62
+ id: Id,
63
+ value: Type.Optional(Type.Unknown()),
64
+ error: Type.Optional(ErrorShape),
65
+ }),
66
+ Type.Object({ t: Type.Literal("cancel"), id: Id }),
67
+ Type.Object({ t: Type.Literal("sub"), id: Id, hold: Id, member: Name }),
68
+ Type.Object({ t: Type.Literal("unsub"), id: Id }),
69
+ Type.Object({
70
+ t: Type.Literal("state"),
71
+ id: Id,
72
+ snap: Type.Optional(Type.Unknown()),
73
+ reset: Type.Optional(Type.Unknown()),
74
+ ops: Type.Optional(Type.Array(Type.Array(Type.Unknown()))),
75
+ error: Type.Optional(ErrorShape),
76
+ }),
77
+ Type.Object({ t: Type.Literal("ping"), n: Type.Integer() }),
78
+ Type.Object({ t: Type.Literal("pong"), n: Type.Integer() }),
79
+ Type.Object({ t: Type.Literal("bye"), reason: Type.Optional(Type.String()) }),
80
+ Type.Object({ t: Type.Literal("root_end"), rootId: Name }),
81
+ Type.Object({ t: Type.Literal("invalidate"), pattern: Type.Record(Type.String(), Type.Unknown()) }),
82
+ Type.Object({
83
+ t: Type.Literal("prepare"),
84
+ reload: Reload,
85
+ epoch: Type.Integer({ minimum: 1 }),
86
+ plugins: Type.Array(Type.String()),
87
+ options: Type.Object({
88
+ remove: Type.Optional(Type.Array(Type.String())),
89
+ gateDeadline: Type.Optional(Type.Number()),
90
+ retireDeadline: Type.Optional(Type.Number()),
91
+ }),
92
+ }),
93
+ Type.Object({
94
+ t: Type.Literal("vote"),
95
+ reload: Reload,
96
+ error: Type.Optional(ErrorShape),
97
+ report: Type.Optional(Type.Object({
98
+ epoch: Type.Integer(),
99
+ previous: Type.Integer(),
100
+ changed: Type.Array(Type.String()),
101
+ removed: Type.Array(Type.String()),
102
+ prepared: Type.Array(Type.String()),
103
+ gated: Type.Array(Type.String()),
104
+ })),
105
+ }),
106
+ Type.Object({ t: Type.Literal("commit"), reload: Reload }),
107
+ Type.Object({ t: Type.Literal("retire"), epoch: Type.Integer({ minimum: 1 }) }),
108
+ Type.Object({ t: Type.Literal("abort"), reload: Reload }),
109
+ ]);
110
+ /** A frame that passes structural validation; anything else is a protocol violation. */
111
+ export const isFrame = (value) => Value.Check(FrameSchema, value);
112
+ //# sourceMappingURL=wire.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"wire.js","sourceRoot":"","sources":["../src/wire.ts"],"names":[],"mappings":"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","sourcesContent":["import { Type } from \"typebox\";\nimport { Value } from \"typebox/value\";\nimport type { Description } from \"./contract.ts\";\nimport type { WireOp } from \"./delta/index.ts\";\nimport { ChordError, type ChordErrorCode } from \"./errors.ts\";\nimport type { Principal } from \"./types.ts\";\n\n// JSON frames between two hosts (or a host and a client). Ids are chosen by the side that creates the hold, call or\n// subscription; every frame type has one direction, so ids never collide:\n// consumer → provider: hold, release, call, cancel, sub, unsub\n// provider → consumer: shape, gone, result, state\n// both: hello, ping, pong, bye, root_end; parent → child: invalidate, prepare, commit, abort, retire; child → parent: vote\n\nexport interface RootRef {\n\treadonly rootId: string;\n\treadonly epoch: number;\n}\n\nexport interface WireError {\n\treadonly code: ChordErrorCode;\n\treadonly message: string;\n\treadonly reason?: string;\n}\n\nexport interface WireReloadOptions {\n\treadonly remove?: readonly string[];\n\treadonly gateDeadline?: number;\n\treadonly retireDeadline?: number;\n}\n\n/** A child's prepared reload, sent with its vote (same fields as `ReloadReport`, without children). */\nexport interface WireReloadReport {\n\treadonly epoch: number;\n\treadonly previous: number;\n\treadonly changed: readonly string[];\n\treadonly removed: readonly string[];\n\treadonly prepared: readonly string[];\n\treadonly gated: readonly string[];\n}\n\nexport type Frame =\n\t| { readonly t: \"hello\"; readonly name: string; readonly kind: \"host\" | \"client\"; readonly epoch: number }\n\t| {\n\t\t\treadonly t: \"hold\";\n\t\t\treadonly id: number;\n\t\t\t/** Target host name. */\n\t\t\treadonly at: string;\n\t\t\t/** The consumer's contract token; the provider checks that it covers it. */\n\t\t\treadonly token: Description;\n\t\t\treadonly input: unknown;\n\t\t\t/** A forwarded principal. Honored only on frames from the parent link. */\n\t\t\treadonly principal?: Principal;\n\t\t\t/** Set by a relay when the hold originates from a client (browser): not a reload participant. */\n\t\t\treadonly client?: boolean;\n\t }\n\t| { readonly t: \"release\"; readonly id: number }\n\t| {\n\t\t\treadonly t: \"shape\";\n\t\t\treadonly id: number;\n\t\t\treadonly kind?: string;\n\t\t\treadonly members: readonly string[];\n\t\t\treadonly contract: string;\n\t\t\treadonly epoch: number;\n\t }\n\t| { readonly t: \"gone\"; readonly id: number; readonly error: WireError }\n\t| {\n\t\t\treadonly t: \"call\";\n\t\t\treadonly id: number;\n\t\t\treadonly hold: number;\n\t\t\treadonly member: string;\n\t\t\treadonly args: unknown;\n\t\t\t/** Absent: the receiving host starts a root (browsers never carry roots). */\n\t\t\treadonly root?: RootRef;\n\t }\n\t| { readonly t: \"result\"; readonly id: number; readonly value?: unknown; readonly error?: WireError }\n\t| { readonly t: \"cancel\"; readonly id: number }\n\t| { readonly t: \"sub\"; readonly id: number; readonly hold: number; readonly member: string }\n\t| { readonly t: \"unsub\"; readonly id: number }\n\t| {\n\t\t\treadonly t: \"state\";\n\t\t\treadonly id: number;\n\t\t\treadonly snap?: unknown;\n\t\t\treadonly reset?: unknown;\n\t\t\t/** Encoded with the subscription's delta encoder. */\n\t\t\treadonly ops?: readonly WireOp[];\n\t\t\treadonly error?: WireError;\n\t }\n\t| { readonly t: \"ping\"; readonly n: number }\n\t| { readonly t: \"pong\"; readonly n: number }\n\t| { readonly t: \"bye\"; readonly reason?: string }\n\t/** The root ended at its origin: its leases on records end (sent on every link the root's calls used). */\n\t| { readonly t: \"root_end\"; readonly rootId: string }\n\t| { readonly t: \"invalidate\"; readonly pattern: Readonly<Record<string, unknown>> }\n\t| {\n\t\t\treadonly t: \"prepare\";\n\t\t\treadonly reload: number;\n\t\t\treadonly epoch: number;\n\t\t\treadonly plugins: readonly string[];\n\t\t\treadonly options: WireReloadOptions;\n\t }\n\t| { readonly t: \"vote\"; readonly reload: number; readonly error?: WireError; readonly report?: WireReloadReport }\n\t| { readonly t: \"commit\"; readonly reload: number }\n\t/** The parent dropped `epoch`: roots of it may still come from there no longer. */\n\t| { readonly t: \"retire\"; readonly epoch: number }\n\t| { readonly t: \"abort\"; readonly reload: number };\n\nexport function toWireError(error: unknown): WireError {\n\tif (error instanceof ChordError) {\n\t\treturn error.reason === undefined\n\t\t\t? { code: error.code, message: error.message }\n\t\t\t: { code: error.code, message: error.message, reason: error.reason };\n\t}\n\treturn { code: \"unavailable\", message: error instanceof Error ? error.message : String(error) };\n}\n\nexport const fromWireError = (error: WireError): ChordError =>\n\tnew ChordError(error.code, error.message.replace(/^[a-z_]+(\\/[a-z_]+)?: /, \"\"), { reason: error.reason });\n\n// ─── validation ──────────────────────────────────────────────────────────────\n\nconst Id = Type.Integer({ minimum: 1 });\nconst Name = Type.String({ minLength: 1 });\nconst Root = Type.Object({ rootId: Name, epoch: Type.Integer({ minimum: 1 }) });\nconst ErrorShape = Type.Object({ code: Type.String(), message: Type.String(), reason: Type.Optional(Type.String()) });\nconst Reload = Type.Integer({ minimum: 1 });\n\n/** Structural schema of every frame. Payloads (args, values, ops) are checked where they are used. */\nconst FrameSchema = Type.Union([\n\tType.Object({\n\t\tt: Type.Literal(\"hello\"),\n\t\tname: Name,\n\t\tkind: Type.Union([Type.Literal(\"host\"), Type.Literal(\"client\")]),\n\t\tepoch: Type.Integer({ minimum: 0 }),\n\t}),\n\tType.Object({\n\t\tt: Type.Literal(\"hold\"),\n\t\tid: Id,\n\t\tat: Name,\n\t\ttoken: Type.Object({\n\t\t\tname: Name,\n\t\t\tscope: Type.String(),\n\t\t\tversion: Type.Integer(),\n\t\t\tinput: Type.Unknown(),\n\t\t\tvariants: Type.Record(Type.String(), Type.Unknown()),\n\t\t}),\n\t\tinput: Type.Unknown(),\n\t\tprincipal: Type.Optional(Type.Unknown()),\n\t\tclient: Type.Optional(Type.Boolean()),\n\t}),\n\tType.Object({ t: Type.Literal(\"release\"), id: Id }),\n\tType.Object({\n\t\tt: Type.Literal(\"shape\"),\n\t\tid: Id,\n\t\tkind: Type.Optional(Type.String()),\n\t\tmembers: Type.Array(Type.String()),\n\t\tcontract: Type.String(),\n\t\tepoch: Type.Integer(),\n\t}),\n\tType.Object({ t: Type.Literal(\"gone\"), id: Id, error: ErrorShape }),\n\tType.Object({\n\t\tt: Type.Literal(\"call\"),\n\t\tid: Id,\n\t\thold: Id,\n\t\tmember: Name,\n\t\targs: Type.Unknown(),\n\t\troot: Type.Optional(Root),\n\t}),\n\tType.Object({\n\t\tt: Type.Literal(\"result\"),\n\t\tid: Id,\n\t\tvalue: Type.Optional(Type.Unknown()),\n\t\terror: Type.Optional(ErrorShape),\n\t}),\n\tType.Object({ t: Type.Literal(\"cancel\"), id: Id }),\n\tType.Object({ t: Type.Literal(\"sub\"), id: Id, hold: Id, member: Name }),\n\tType.Object({ t: Type.Literal(\"unsub\"), id: Id }),\n\tType.Object({\n\t\tt: Type.Literal(\"state\"),\n\t\tid: Id,\n\t\tsnap: Type.Optional(Type.Unknown()),\n\t\treset: Type.Optional(Type.Unknown()),\n\t\tops: Type.Optional(Type.Array(Type.Array(Type.Unknown()))),\n\t\terror: Type.Optional(ErrorShape),\n\t}),\n\tType.Object({ t: Type.Literal(\"ping\"), n: Type.Integer() }),\n\tType.Object({ t: Type.Literal(\"pong\"), n: Type.Integer() }),\n\tType.Object({ t: Type.Literal(\"bye\"), reason: Type.Optional(Type.String()) }),\n\tType.Object({ t: Type.Literal(\"root_end\"), rootId: Name }),\n\tType.Object({ t: Type.Literal(\"invalidate\"), pattern: Type.Record(Type.String(), Type.Unknown()) }),\n\tType.Object({\n\t\tt: Type.Literal(\"prepare\"),\n\t\treload: Reload,\n\t\tepoch: Type.Integer({ minimum: 1 }),\n\t\tplugins: Type.Array(Type.String()),\n\t\toptions: Type.Object({\n\t\t\tremove: Type.Optional(Type.Array(Type.String())),\n\t\t\tgateDeadline: Type.Optional(Type.Number()),\n\t\t\tretireDeadline: Type.Optional(Type.Number()),\n\t\t}),\n\t}),\n\tType.Object({\n\t\tt: Type.Literal(\"vote\"),\n\t\treload: Reload,\n\t\terror: Type.Optional(ErrorShape),\n\t\treport: Type.Optional(\n\t\t\tType.Object({\n\t\t\t\tepoch: Type.Integer(),\n\t\t\t\tprevious: Type.Integer(),\n\t\t\t\tchanged: Type.Array(Type.String()),\n\t\t\t\tremoved: Type.Array(Type.String()),\n\t\t\t\tprepared: Type.Array(Type.String()),\n\t\t\t\tgated: Type.Array(Type.String()),\n\t\t\t}),\n\t\t),\n\t}),\n\tType.Object({ t: Type.Literal(\"commit\"), reload: Reload }),\n\tType.Object({ t: Type.Literal(\"retire\"), epoch: Type.Integer({ minimum: 1 }) }),\n\tType.Object({ t: Type.Literal(\"abort\"), reload: Reload }),\n]);\n\n/** A frame that passes structural validation; anything else is a protocol violation. */\nexport const isFrame = (value: unknown): value is Frame => Value.Check(FrameSchema, value);\n"]}