agent-comms 1.13.0 → 1.15.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 (256) hide show
  1. package/.claude-plugin/plugin.json +1 -1
  2. package/README.md +1 -1
  3. package/dist/bridges/claude-code/channel.d.ts.map +1 -1
  4. package/dist/bridges/claude-code/channel.js +6 -1
  5. package/dist/bridges/claude-code/channel.js.map +1 -1
  6. package/dist/bridges/codex/tool.d.ts.map +1 -1
  7. package/dist/bridges/codex/tool.js +6 -1
  8. package/dist/bridges/codex/tool.js.map +1 -1
  9. package/dist/bridges/mcp/index.d.ts.map +1 -1
  10. package/dist/bridges/mcp/index.js +6 -1
  11. package/dist/bridges/mcp/index.js.map +1 -1
  12. package/dist/bridges/opencode/plugin.d.ts.map +1 -1
  13. package/dist/bridges/opencode/plugin.js +5 -0
  14. package/dist/bridges/opencode/plugin.js.map +1 -1
  15. package/dist/bridges/pi/index.d.ts +5 -2
  16. package/dist/bridges/pi/index.d.ts.map +1 -1
  17. package/dist/bridges/pi/index.js +125 -20
  18. package/dist/bridges/pi/index.js.map +1 -1
  19. package/dist/bridges/user/controller.d.ts +10 -1
  20. package/dist/bridges/user/controller.d.ts.map +1 -1
  21. package/dist/bridges/user/controller.js +37 -1
  22. package/dist/bridges/user/controller.js.map +1 -1
  23. package/dist/bridges/user/tui.js +4 -0
  24. package/dist/bridges/user/tui.js.map +1 -1
  25. package/dist/bridges/user/web/build.d.ts +4 -4
  26. package/dist/bridges/user/web/build.js +53 -34
  27. package/dist/bridges/user/web/build.js.map +1 -1
  28. package/dist/bridges/user/web/frontend/components/App.d.ts +28 -0
  29. package/dist/bridges/user/web/frontend/components/App.d.ts.map +1 -0
  30. package/dist/bridges/user/web/frontend/components/App.js +7 -0
  31. package/dist/bridges/user/web/frontend/components/App.js.map +1 -0
  32. package/dist/bridges/user/web/frontend/components/ChatArea.d.ts +14 -0
  33. package/dist/bridges/user/web/frontend/components/ChatArea.d.ts.map +1 -0
  34. package/dist/bridges/user/web/frontend/components/ChatArea.js +38 -0
  35. package/dist/bridges/user/web/frontend/components/ChatArea.js.map +1 -0
  36. package/dist/bridges/user/web/frontend/components/CreateRoomForm.d.ts +11 -0
  37. package/dist/bridges/user/web/frontend/components/CreateRoomForm.d.ts.map +1 -0
  38. package/dist/bridges/user/web/frontend/components/CreateRoomForm.js +33 -0
  39. package/dist/bridges/user/web/frontend/components/CreateRoomForm.js.map +1 -0
  40. package/dist/bridges/user/web/frontend/components/JoinForm.d.ts +11 -0
  41. package/dist/bridges/user/web/frontend/components/JoinForm.d.ts.map +1 -0
  42. package/dist/bridges/user/web/frontend/components/JoinForm.js +28 -0
  43. package/dist/bridges/user/web/frontend/components/JoinForm.js.map +1 -0
  44. package/dist/bridges/user/web/frontend/components/Message.d.ts +8 -0
  45. package/dist/bridges/user/web/frontend/components/Message.d.ts.map +1 -0
  46. package/dist/bridges/user/web/frontend/components/Message.js +15 -0
  47. package/dist/bridges/user/web/frontend/components/Message.js.map +1 -0
  48. package/dist/bridges/user/web/frontend/components/MessageList.d.ts +8 -0
  49. package/dist/bridges/user/web/frontend/components/MessageList.d.ts.map +1 -0
  50. package/dist/bridges/user/web/frontend/components/MessageList.js +16 -0
  51. package/dist/bridges/user/web/frontend/components/MessageList.js.map +1 -0
  52. package/dist/bridges/user/web/frontend/components/ProjectTree.d.ts +17 -0
  53. package/dist/bridges/user/web/frontend/components/ProjectTree.d.ts.map +1 -0
  54. package/dist/bridges/user/web/frontend/components/ProjectTree.js +62 -0
  55. package/dist/bridges/user/web/frontend/components/ProjectTree.js.map +1 -0
  56. package/dist/bridges/user/web/frontend/components/RelayPanel.d.ts +15 -0
  57. package/dist/bridges/user/web/frontend/components/RelayPanel.d.ts.map +1 -0
  58. package/dist/bridges/user/web/frontend/components/RelayPanel.js +46 -0
  59. package/dist/bridges/user/web/frontend/components/RelayPanel.js.map +1 -0
  60. package/dist/bridges/user/web/frontend/components/Sidebar.d.ts +21 -0
  61. package/dist/bridges/user/web/frontend/components/Sidebar.d.ts.map +1 -0
  62. package/dist/bridges/user/web/frontend/components/Sidebar.js +37 -0
  63. package/dist/bridges/user/web/frontend/components/Sidebar.js.map +1 -0
  64. package/dist/bridges/user/web/frontend/dom.d.ts +12 -22
  65. package/dist/bridges/user/web/frontend/dom.d.ts.map +1 -1
  66. package/dist/bridges/user/web/frontend/dom.js +24 -49
  67. package/dist/bridges/user/web/frontend/dom.js.map +1 -1
  68. package/dist/bridges/user/web/frontend/input.d.ts +15 -0
  69. package/dist/bridges/user/web/frontend/input.d.ts.map +1 -1
  70. package/dist/bridges/user/web/frontend/input.js +39 -1
  71. package/dist/bridges/user/web/frontend/input.js.map +1 -1
  72. package/dist/bridges/user/web/frontend/main.d.ts +3 -3
  73. package/dist/bridges/user/web/frontend/main.d.ts.map +1 -1
  74. package/dist/bridges/user/web/frontend/main.js +135 -52
  75. package/dist/bridges/user/web/frontend/main.js.map +1 -1
  76. package/dist/bridges/user/web/frontend/mesh-client.d.ts +43 -0
  77. package/dist/bridges/user/web/frontend/mesh-client.d.ts.map +1 -0
  78. package/dist/bridges/user/web/frontend/mesh-client.js +132 -0
  79. package/dist/bridges/user/web/frontend/mesh-client.js.map +1 -0
  80. package/dist/bridges/user/web/frontend/mesh-worker.d.ts +14 -0
  81. package/dist/bridges/user/web/frontend/mesh-worker.d.ts.map +1 -0
  82. package/dist/bridges/user/web/frontend/mesh-worker.js +274 -0
  83. package/dist/bridges/user/web/frontend/mesh-worker.js.map +1 -0
  84. package/dist/bridges/user/web/frontend/messages.d.ts +17 -0
  85. package/dist/bridges/user/web/frontend/messages.d.ts.map +1 -0
  86. package/dist/bridges/user/web/frontend/messages.js +82 -0
  87. package/dist/bridges/user/web/frontend/messages.js.map +1 -0
  88. package/dist/bridges/user/web/frontend/project-tree.d.ts +9 -0
  89. package/dist/bridges/user/web/frontend/project-tree.d.ts.map +1 -0
  90. package/dist/bridges/user/web/frontend/project-tree.js +173 -0
  91. package/dist/bridges/user/web/frontend/project-tree.js.map +1 -0
  92. package/dist/bridges/user/web/frontend/relay-client.d.ts +40 -0
  93. package/dist/bridges/user/web/frontend/relay-client.d.ts.map +1 -0
  94. package/dist/bridges/user/web/frontend/relay-client.js +97 -0
  95. package/dist/bridges/user/web/frontend/relay-client.js.map +1 -0
  96. package/dist/bridges/user/web/frontend/relay-worker.d.ts +15 -0
  97. package/dist/bridges/user/web/frontend/relay-worker.d.ts.map +1 -0
  98. package/dist/bridges/user/web/frontend/relay-worker.js +366 -0
  99. package/dist/bridges/user/web/frontend/relay-worker.js.map +1 -0
  100. package/dist/bridges/user/web/frontend/state.d.ts +8 -1
  101. package/dist/bridges/user/web/frontend/state.d.ts.map +1 -1
  102. package/dist/bridges/user/web/frontend/state.js +17 -1
  103. package/dist/bridges/user/web/frontend/state.js.map +1 -1
  104. package/dist/bridges/user/web/frontend/sw.d.ts +16 -0
  105. package/dist/bridges/user/web/frontend/sw.d.ts.map +1 -0
  106. package/dist/bridges/user/web/frontend/sw.js +145 -0
  107. package/dist/bridges/user/web/frontend/sw.js.map +1 -0
  108. package/dist/bridges/user/web/frontend/types.d.ts +52 -0
  109. package/dist/bridges/user/web/frontend/types.d.ts.map +1 -1
  110. package/dist/bridges/user/web/frontend/url-sync.d.ts +48 -0
  111. package/dist/bridges/user/web/frontend/url-sync.d.ts.map +1 -0
  112. package/dist/bridges/user/web/frontend/url-sync.js +74 -0
  113. package/dist/bridges/user/web/frontend/url-sync.js.map +1 -0
  114. package/dist/bridges/user/web/server.d.ts +10 -3
  115. package/dist/bridges/user/web/server.d.ts.map +1 -1
  116. package/dist/bridges/user/web/server.js +280 -15
  117. package/dist/bridges/user/web/server.js.map +1 -1
  118. package/dist/bridges/user/web/test/web-server.integration.test.d.ts +7 -0
  119. package/dist/bridges/user/web/test/web-server.integration.test.d.ts.map +1 -0
  120. package/dist/bridges/user/web/test/web-server.integration.test.js +187 -0
  121. package/dist/bridges/user/web/test/web-server.integration.test.js.map +1 -0
  122. package/dist/core/bridge.d.ts +43 -0
  123. package/dist/core/bridge.d.ts.map +1 -1
  124. package/dist/core/bridge.js +197 -0
  125. package/dist/core/bridge.js.map +1 -1
  126. package/dist/core/comms-store.d.ts +22 -1
  127. package/dist/core/comms-store.d.ts.map +1 -1
  128. package/dist/core/discovery-mdns.d.ts +33 -0
  129. package/dist/core/discovery-mdns.d.ts.map +1 -0
  130. package/dist/core/discovery-mdns.js +182 -0
  131. package/dist/core/discovery-mdns.js.map +1 -0
  132. package/dist/core/discovery-tailscale.d.ts +40 -0
  133. package/dist/core/discovery-tailscale.d.ts.map +1 -0
  134. package/dist/core/discovery-tailscale.js +158 -0
  135. package/dist/core/discovery-tailscale.js.map +1 -0
  136. package/dist/core/discovery.d.ts +82 -0
  137. package/dist/core/discovery.d.ts.map +1 -0
  138. package/dist/core/discovery.js +194 -0
  139. package/dist/core/discovery.js.map +1 -0
  140. package/dist/core/federation.d.ts +100 -0
  141. package/dist/core/federation.d.ts.map +1 -0
  142. package/dist/core/federation.js +411 -0
  143. package/dist/core/federation.js.map +1 -0
  144. package/dist/core/identity.d.ts +31 -0
  145. package/dist/core/identity.d.ts.map +1 -0
  146. package/dist/core/identity.js +251 -0
  147. package/dist/core/identity.js.map +1 -0
  148. package/dist/core/index.d.ts +12 -1
  149. package/dist/core/index.d.ts.map +1 -1
  150. package/dist/core/index.js +7 -1
  151. package/dist/core/index.js.map +1 -1
  152. package/dist/core/mesh-store.d.ts +75 -26
  153. package/dist/core/mesh-store.d.ts.map +1 -1
  154. package/dist/core/mesh-store.js +570 -355
  155. package/dist/core/mesh-store.js.map +1 -1
  156. package/dist/core/push-manager.d.ts +41 -0
  157. package/dist/core/push-manager.d.ts.map +1 -0
  158. package/dist/core/push-manager.js +60 -0
  159. package/dist/core/push-manager.js.map +1 -0
  160. package/dist/core/store.d.ts +21 -1
  161. package/dist/core/store.d.ts.map +1 -1
  162. package/dist/core/store.js +44 -0
  163. package/dist/core/store.js.map +1 -1
  164. package/dist/core/tcp-transport.d.ts +77 -0
  165. package/dist/core/tcp-transport.d.ts.map +1 -0
  166. package/dist/core/tcp-transport.js +596 -0
  167. package/dist/core/tcp-transport.js.map +1 -0
  168. package/dist/core/test/bridge.unit.test.d.ts +5 -0
  169. package/dist/core/test/bridge.unit.test.d.ts.map +1 -0
  170. package/dist/core/test/bridge.unit.test.js +120 -0
  171. package/dist/core/test/bridge.unit.test.js.map +1 -0
  172. package/dist/core/test/identity.unit.test.d.ts +5 -0
  173. package/dist/core/test/identity.unit.test.d.ts.map +1 -0
  174. package/dist/core/test/identity.unit.test.js +70 -0
  175. package/dist/core/test/identity.unit.test.js.map +1 -0
  176. package/dist/core/tls-transport.d.ts +69 -0
  177. package/dist/core/tls-transport.d.ts.map +1 -0
  178. package/dist/core/tls-transport.js +602 -0
  179. package/dist/core/tls-transport.js.map +1 -0
  180. package/dist/core/tool.d.ts +23 -2
  181. package/dist/core/tool.d.ts.map +1 -1
  182. package/dist/core/tool.js +269 -1
  183. package/dist/core/tool.js.map +1 -1
  184. package/dist/core/transport.d.ts +166 -0
  185. package/dist/core/transport.d.ts.map +1 -0
  186. package/dist/core/transport.js +20 -0
  187. package/dist/core/transport.js.map +1 -0
  188. package/dist/core/types.d.ts +146 -0
  189. package/dist/core/types.d.ts.map +1 -1
  190. package/dist/core/types.js +77 -0
  191. package/dist/core/types.js.map +1 -1
  192. package/dist/core/vapid.d.ts +22 -0
  193. package/dist/core/vapid.d.ts.map +1 -0
  194. package/dist/core/vapid.js +50 -0
  195. package/dist/core/vapid.js.map +1 -0
  196. package/dist/core/web-push.d.ts +37 -0
  197. package/dist/core/web-push.d.ts.map +1 -0
  198. package/dist/core/web-push.js +198 -0
  199. package/dist/core/web-push.js.map +1 -0
  200. package/dist/core/wire-protocol.d.ts +131 -0
  201. package/dist/core/wire-protocol.d.ts.map +1 -0
  202. package/dist/core/wire-protocol.js +54 -0
  203. package/dist/core/wire-protocol.js.map +1 -0
  204. package/dist/core/ws-transport.d.ts +71 -0
  205. package/dist/core/ws-transport.d.ts.map +1 -0
  206. package/dist/core/ws-transport.js +560 -0
  207. package/dist/core/ws-transport.js.map +1 -0
  208. package/dist/test/approval.integration.test.d.ts +9 -0
  209. package/dist/test/approval.integration.test.d.ts.map +1 -0
  210. package/dist/test/approval.integration.test.js +361 -0
  211. package/dist/test/approval.integration.test.js.map +1 -0
  212. package/dist/test/delivery-receipt.helper.d.ts +16 -0
  213. package/dist/test/delivery-receipt.helper.d.ts.map +1 -0
  214. package/dist/test/delivery-receipt.helper.js +409 -0
  215. package/dist/test/delivery-receipt.helper.js.map +1 -0
  216. package/dist/test/delivery-receipt.runner.d.ts +13 -0
  217. package/dist/test/delivery-receipt.runner.d.ts.map +1 -0
  218. package/dist/test/delivery-receipt.runner.js +51 -0
  219. package/dist/test/delivery-receipt.runner.js.map +1 -0
  220. package/dist/test/federation.integration.test.d.ts +15 -0
  221. package/dist/test/federation.integration.test.d.ts.map +1 -0
  222. package/dist/test/federation.integration.test.js +218 -0
  223. package/dist/test/federation.integration.test.js.map +1 -0
  224. package/dist/test/listener-policy.integration.test.d.ts +9 -0
  225. package/dist/test/listener-policy.integration.test.d.ts.map +1 -0
  226. package/dist/test/listener-policy.integration.test.js +239 -0
  227. package/dist/test/listener-policy.integration.test.js.map +1 -0
  228. package/dist/test/tls-transport.integration.test.d.ts +8 -0
  229. package/dist/test/tls-transport.integration.test.d.ts.map +1 -0
  230. package/dist/test/tls-transport.integration.test.js +158 -0
  231. package/dist/test/tls-transport.integration.test.js.map +1 -0
  232. package/dist/test/visibility.integration.test.d.ts +12 -0
  233. package/dist/test/visibility.integration.test.d.ts.map +1 -0
  234. package/dist/test/visibility.integration.test.js +181 -0
  235. package/dist/test/visibility.integration.test.js.map +1 -0
  236. package/package.json +7 -3
  237. package/dist/bridges/user/web/frontend/render.d.ts +0 -30
  238. package/dist/bridges/user/web/frontend/render.d.ts.map +0 -1
  239. package/dist/bridges/user/web/frontend/render.js +0 -129
  240. package/dist/bridges/user/web/frontend/render.js.map +0 -1
  241. package/dist/bridges/user/web/frontend/test/dom.unit.test.d.ts +0 -5
  242. package/dist/bridges/user/web/frontend/test/dom.unit.test.d.ts.map +0 -1
  243. package/dist/bridges/user/web/frontend/test/dom.unit.test.js +0 -149
  244. package/dist/bridges/user/web/frontend/test/dom.unit.test.js.map +0 -1
  245. package/dist/bridges/user/web/frontend/test/input.unit.test.d.ts +0 -5
  246. package/dist/bridges/user/web/frontend/test/input.unit.test.d.ts.map +0 -1
  247. package/dist/bridges/user/web/frontend/test/input.unit.test.js +0 -131
  248. package/dist/bridges/user/web/frontend/test/input.unit.test.js.map +0 -1
  249. package/dist/bridges/user/web/frontend/test/render.unit.test.d.ts +0 -5
  250. package/dist/bridges/user/web/frontend/test/render.unit.test.d.ts.map +0 -1
  251. package/dist/bridges/user/web/frontend/test/render.unit.test.js +0 -436
  252. package/dist/bridges/user/web/frontend/test/render.unit.test.js.map +0 -1
  253. package/dist/bridges/user/web/frontend/test/state.unit.test.d.ts +0 -5
  254. package/dist/bridges/user/web/frontend/test/state.unit.test.d.ts.map +0 -1
  255. package/dist/bridges/user/web/frontend/test/state.unit.test.js +0 -119
  256. package/dist/bridges/user/web/frontend/test/state.unit.test.js.map +0 -1
@@ -0,0 +1,120 @@
1
+ /**
2
+ * Unit tests for bridge.ts — formatDeliveryEvent.
3
+ */
4
+ import { describe, it } from "node:test";
5
+ import assert from "node:assert/strict";
6
+ import { formatDeliveryEvent, isActionableEvent } from "../bridge.js";
7
+ describe("formatDeliveryEvent", () => {
8
+ it("formats name_changed event", () => {
9
+ const event = {
10
+ type: "name_changed",
11
+ agent: "abc123",
12
+ oldName: "Alice",
13
+ newName: "Bob",
14
+ };
15
+ const result = formatDeliveryEvent(event);
16
+ assert.strictEqual(result, "Alice is now known as Bob");
17
+ });
18
+ it("formats room_message", () => {
19
+ const event = {
20
+ type: "room_message",
21
+ message: {
22
+ id: "m1",
23
+ from: "a1",
24
+ room: "r1",
25
+ content: "hello",
26
+ timestamp: "2025-01-01T00:00:00Z",
27
+ readBy: [],
28
+ },
29
+ };
30
+ const result = formatDeliveryEvent(event);
31
+ assert.strictEqual(result, "[r1] a1: hello");
32
+ });
33
+ it("formats member_status", () => {
34
+ const event = {
35
+ type: "member_status",
36
+ room: "r1",
37
+ agent: "a1",
38
+ status: "busy",
39
+ };
40
+ const result = formatDeliveryEvent(event);
41
+ assert.strictEqual(result, "a1 is now busy in r1");
42
+ });
43
+ });
44
+ describe("isActionableEvent", () => {
45
+ it("classifies room_message as actionable", () => {
46
+ const event = {
47
+ type: "room_message",
48
+ message: {
49
+ id: "m1",
50
+ from: "a1",
51
+ room: "r1",
52
+ content: "hello",
53
+ timestamp: "2025-01-01T00:00:00Z",
54
+ readBy: [],
55
+ },
56
+ };
57
+ assert.strictEqual(isActionableEvent(event), true);
58
+ });
59
+ it("classifies dm as actionable", () => {
60
+ const event = {
61
+ type: "dm",
62
+ message: {
63
+ id: "dm1",
64
+ from: "a1",
65
+ to: "a2",
66
+ content: "hey",
67
+ timestamp: "2025-01-01T00:00:00Z",
68
+ readBy: [],
69
+ },
70
+ };
71
+ assert.strictEqual(isActionableEvent(event), true);
72
+ });
73
+ it("classifies room_invite as actionable", () => {
74
+ const event = {
75
+ type: "room_invite",
76
+ room: "r1",
77
+ roomDescription: "",
78
+ from: "a1",
79
+ fromName: "Alice",
80
+ fromCwd: "/home",
81
+ };
82
+ assert.strictEqual(isActionableEvent(event), true);
83
+ });
84
+ it("classifies member_joined as informational", () => {
85
+ const event = {
86
+ type: "member_joined",
87
+ room: "r1",
88
+ agent: "a1",
89
+ };
90
+ assert.strictEqual(isActionableEvent(event), false);
91
+ });
92
+ it("classifies member_status as informational", () => {
93
+ const event = {
94
+ type: "member_status",
95
+ room: "r1",
96
+ agent: "a1",
97
+ status: "offline",
98
+ };
99
+ assert.strictEqual(isActionableEvent(event), false);
100
+ });
101
+ it("classifies name_changed as informational", () => {
102
+ const event = {
103
+ type: "name_changed",
104
+ agent: "a1",
105
+ oldName: "Alice",
106
+ newName: "Bob",
107
+ };
108
+ assert.strictEqual(isActionableEvent(event), false);
109
+ });
110
+ it("classifies delivery_status as informational", () => {
111
+ const event = {
112
+ type: "delivery_status",
113
+ messageId: "m1",
114
+ agent: "a1",
115
+ status: "delivered",
116
+ };
117
+ assert.strictEqual(isActionableEvent(event), false);
118
+ });
119
+ });
120
+ //# sourceMappingURL=bridge.unit.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"bridge.unit.test.js","sourceRoot":"","sources":["../../../src/core/test/bridge.unit.test.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,5 @@
1
+ /**
2
+ * Unit tests for identity.ts — cryptographic identity generation.
3
+ */
4
+ export {};
5
+ //# sourceMappingURL=identity.unit.test.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"identity.unit.test.d.ts","sourceRoot":"","sources":["../../../src/core/test/identity.unit.test.ts"],"names":[],"mappings":"AAAA;;GAEG"}
@@ -0,0 +1,70 @@
1
+ /**
2
+ * Unit tests for identity.ts — cryptographic identity generation.
3
+ */
4
+ import { describe, it } from "node:test";
5
+ import assert from "node:assert/strict";
6
+ import { X509Certificate } from "node:crypto";
7
+ import { generateIdentity, getCertificateFingerprint } from "../identity.js";
8
+ describe("generateIdentity", () => {
9
+ it("returns a valid PeerIdentity with all required fields", () => {
10
+ const identity = generateIdentity();
11
+ assert.ok(identity.privateKey, "private key should be present");
12
+ assert.ok(identity.certificate, "certificate should be present");
13
+ assert.ok(identity.fingerprint, "fingerprint should be present");
14
+ });
15
+ it("produces a valid PEM-encoded private key", () => {
16
+ const { privateKey } = generateIdentity();
17
+ assert.match(privateKey, /^-----BEGIN PRIVATE KEY-----/, "private key should start with PEM header");
18
+ assert.match(privateKey, /-----END PRIVATE KEY-----\n?$/, "private key should end with PEM footer");
19
+ });
20
+ it("produces a valid PEM-encoded certificate", () => {
21
+ const { certificate } = generateIdentity();
22
+ assert.match(certificate, /^-----BEGIN CERTIFICATE-----/, "certificate should start with PEM header");
23
+ assert.match(certificate, /-----END CERTIFICATE-----\n?$/, "certificate should end with PEM footer");
24
+ });
25
+ it("produces a fingerprint that is a 95-character SHA-256 hex string with colons", () => {
26
+ const { fingerprint } = generateIdentity();
27
+ // SHA-256 = 32 bytes = 64 hex chars + 31 colons = 95 chars
28
+ assert.strictEqual(fingerprint.length, 95);
29
+ assert.match(fingerprint, /^[0-9A-F]{2}(:[0-9A-F]{2}){31}$/, "fingerprint should be hex pairs separated by colons");
30
+ });
31
+ it("produces a fingerprint that matches Node's own X509Certificate.fingerprint256", () => {
32
+ const { certificate, fingerprint } = generateIdentity();
33
+ const x509 = new X509Certificate(certificate);
34
+ assert.strictEqual(fingerprint, x509.fingerprint256);
35
+ });
36
+ it("produces a certificate that is valid and self-signed", () => {
37
+ const { certificate } = generateIdentity();
38
+ const x509 = new X509Certificate(certificate);
39
+ assert.strictEqual(x509.subject, "CN=agent-comms");
40
+ assert.strictEqual(x509.issuer, "CN=agent-comms");
41
+ assert.ok(x509.verify(x509.publicKey), "certificate should verify against its own public key");
42
+ });
43
+ it("includes localhost and 127.0.0.1 in Subject Alternative Names", () => {
44
+ const { certificate } = generateIdentity();
45
+ const x509 = new X509Certificate(certificate);
46
+ assert.ok(x509.checkHost("localhost"), "should match DNS:localhost");
47
+ assert.ok(x509.checkIP("127.0.0.1"), "should match IP:127.0.0.1");
48
+ });
49
+ it("produces different fingerprints on successive calls (different keypairs)", () => {
50
+ const a = generateIdentity();
51
+ const b = generateIdentity();
52
+ assert.notStrictEqual(a.fingerprint, b.fingerprint);
53
+ assert.notStrictEqual(a.privateKey, b.privateKey);
54
+ assert.notStrictEqual(a.certificate, b.certificate);
55
+ });
56
+ });
57
+ describe("getCertificateFingerprint", () => {
58
+ it("is deterministic — same cert always produces same fingerprint", () => {
59
+ const { certificate, fingerprint } = generateIdentity();
60
+ const recomputed = getCertificateFingerprint(certificate);
61
+ assert.strictEqual(recomputed, fingerprint);
62
+ });
63
+ it("produces the same result when called multiple times", () => {
64
+ const { certificate } = generateIdentity();
65
+ const first = getCertificateFingerprint(certificate);
66
+ const second = getCertificateFingerprint(certificate);
67
+ assert.strictEqual(first, second);
68
+ });
69
+ });
70
+ //# sourceMappingURL=identity.unit.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"identity.unit.test.js","sourceRoot":"","sources":["../../../src/core/test/identity.unit.test.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,OAAO,EAAE,QAAQ,EAAE,EAAE,EAAE,MAAM,WAAW,CAAC;AACzC,OAAO,MAAM,MAAM,oBAAoB,CAAC;AACxC,OAAO,EAAE,eAAe,EAAE,MAAM,aAAa,CAAC;AAC9C,OAAO,EAAE,gBAAgB,EAAE,yBAAyB,EAAE,MAAM,gBAAgB,CAAC;AAE7E,QAAQ,CAAC,kBAAkB,EAAE,GAAG,EAAE;IAChC,EAAE,CAAC,uDAAuD,EAAE,GAAG,EAAE;QAC/D,MAAM,QAAQ,GAAG,gBAAgB,EAAE,CAAC;QAEpC,MAAM,CAAC,EAAE,CAAC,QAAQ,CAAC,UAAU,EAAE,+BAA+B,CAAC,CAAC;QAChE,MAAM,CAAC,EAAE,CAAC,QAAQ,CAAC,WAAW,EAAE,+BAA+B,CAAC,CAAC;QACjE,MAAM,CAAC,EAAE,CAAC,QAAQ,CAAC,WAAW,EAAE,+BAA+B,CAAC,CAAC;IACnE,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,0CAA0C,EAAE,GAAG,EAAE;QAClD,MAAM,EAAE,UAAU,EAAE,GAAG,gBAAgB,EAAE,CAAC;QAE1C,MAAM,CAAC,KAAK,CACV,UAAU,EACV,8BAA8B,EAC9B,0CAA0C,CAC3C,CAAC;QACF,MAAM,CAAC,KAAK,CACV,UAAU,EACV,+BAA+B,EAC/B,wCAAwC,CACzC,CAAC;IACJ,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,0CAA0C,EAAE,GAAG,EAAE;QAClD,MAAM,EAAE,WAAW,EAAE,GAAG,gBAAgB,EAAE,CAAC;QAE3C,MAAM,CAAC,KAAK,CACV,WAAW,EACX,8BAA8B,EAC9B,0CAA0C,CAC3C,CAAC;QACF,MAAM,CAAC,KAAK,CACV,WAAW,EACX,+BAA+B,EAC/B,wCAAwC,CACzC,CAAC;IACJ,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,8EAA8E,EAAE,GAAG,EAAE;QACtF,MAAM,EAAE,WAAW,EAAE,GAAG,gBAAgB,EAAE,CAAC;QAE3C,2DAA2D;QAC3D,MAAM,CAAC,WAAW,CAAC,WAAW,CAAC,MAAM,EAAE,EAAE,CAAC,CAAC;QAC3C,MAAM,CAAC,KAAK,CACV,WAAW,EACX,iCAAiC,EACjC,qDAAqD,CACtD,CAAC;IACJ,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,+EAA+E,EAAE,GAAG,EAAE;QACvF,MAAM,EAAE,WAAW,EAAE,WAAW,EAAE,GAAG,gBAAgB,EAAE,CAAC;QACxD,MAAM,IAAI,GAAG,IAAI,eAAe,CAAC,WAAW,CAAC,CAAC;QAE9C,MAAM,CAAC,WAAW,CAAC,WAAW,EAAE,IAAI,CAAC,cAAc,CAAC,CAAC;IACvD,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,sDAAsD,EAAE,GAAG,EAAE;QAC9D,MAAM,EAAE,WAAW,EAAE,GAAG,gBAAgB,EAAE,CAAC;QAC3C,MAAM,IAAI,GAAG,IAAI,eAAe,CAAC,WAAW,CAAC,CAAC;QAE9C,MAAM,CAAC,WAAW,CAAC,IAAI,CAAC,OAAO,EAAE,gBAAgB,CAAC,CAAC;QACnD,MAAM,CAAC,WAAW,CAAC,IAAI,CAAC,MAAM,EAAE,gBAAgB,CAAC,CAAC;QAClD,MAAM,CAAC,EAAE,CACP,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,SAAS,CAAC,EAC3B,sDAAsD,CACvD,CAAC;IACJ,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,+DAA+D,EAAE,GAAG,EAAE;QACvE,MAAM,EAAE,WAAW,EAAE,GAAG,gBAAgB,EAAE,CAAC;QAC3C,MAAM,IAAI,GAAG,IAAI,eAAe,CAAC,WAAW,CAAC,CAAC;QAE9C,MAAM,CAAC,EAAE,CAAC,IAAI,CAAC,SAAS,CAAC,WAAW,CAAC,EAAE,4BAA4B,CAAC,CAAC;QACrE,MAAM,CAAC,EAAE,CAAC,IAAI,CAAC,OAAO,CAAC,WAAW,CAAC,EAAE,2BAA2B,CAAC,CAAC;IACpE,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,0EAA0E,EAAE,GAAG,EAAE;QAClF,MAAM,CAAC,GAAG,gBAAgB,EAAE,CAAC;QAC7B,MAAM,CAAC,GAAG,gBAAgB,EAAE,CAAC;QAE7B,MAAM,CAAC,cAAc,CAAC,CAAC,CAAC,WAAW,EAAE,CAAC,CAAC,WAAW,CAAC,CAAC;QACpD,MAAM,CAAC,cAAc,CAAC,CAAC,CAAC,UAAU,EAAE,CAAC,CAAC,UAAU,CAAC,CAAC;QAClD,MAAM,CAAC,cAAc,CAAC,CAAC,CAAC,WAAW,EAAE,CAAC,CAAC,WAAW,CAAC,CAAC;IACtD,CAAC,CAAC,CAAC;AACL,CAAC,CAAC,CAAC;AAEH,QAAQ,CAAC,2BAA2B,EAAE,GAAG,EAAE;IACzC,EAAE,CAAC,+DAA+D,EAAE,GAAG,EAAE;QACvE,MAAM,EAAE,WAAW,EAAE,WAAW,EAAE,GAAG,gBAAgB,EAAE,CAAC;QACxD,MAAM,UAAU,GAAG,yBAAyB,CAAC,WAAW,CAAC,CAAC;QAE1D,MAAM,CAAC,WAAW,CAAC,UAAU,EAAE,WAAW,CAAC,CAAC;IAC9C,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,qDAAqD,EAAE,GAAG,EAAE;QAC7D,MAAM,EAAE,WAAW,EAAE,GAAG,gBAAgB,EAAE,CAAC;QAC3C,MAAM,KAAK,GAAG,yBAAyB,CAAC,WAAW,CAAC,CAAC;QACrD,MAAM,MAAM,GAAG,yBAAyB,CAAC,WAAW,CAAC,CAAC;QAEtD,MAAM,CAAC,WAAW,CAAC,KAAK,EAAE,MAAM,CAAC,CAAC;IACpC,CAAC,CAAC,CAAC;AACL,CAAC,CAAC,CAAC"}
@@ -0,0 +1,69 @@
1
+ /**
2
+ * TlsTransport — TLS-encrypted transport for the peer mesh.
3
+ *
4
+ * Same wire protocol as TcpTransport, but all connections are wrapped in TLS
5
+ * with certificate fingerprint authentication. Each peer generates an ECDSA
6
+ * P-256 keypair and self-signed X.509 certificate on startup. The peer ID
7
+ * is the certificate fingerprint — verifying a peer's identity is simply
8
+ * checking that the presented certificate's fingerprint matches the known ID.
9
+ *
10
+ * This is the Syncthing trust model: no CA, no PKI, just certificate pinning.
11
+ * Overlay networks (Tailscale, WireGuard) are still recommended for NAT
12
+ * traversal but are not required for security — TLS handles encryption and
13
+ * authentication at the protocol level.
14
+ *
15
+ * The transport is a drop-in replacement for TcpTransport. Same interface,
16
+ * same wire protocol, same event callbacks. MeshStore cannot tell the
17
+ * difference.
18
+ */
19
+ import type { MeshMessage, PeerInfo } from "./wire-protocol.js";
20
+ import type { ConnectionHandle, ListenerInfo, ListenerPolicy, TransportEvents } from "./transport.js";
21
+ import type { PeerIdentity } from "./identity.js";
22
+ export declare class TlsTransport {
23
+ private dataServer;
24
+ private _dataPort;
25
+ private coordinatorListeners;
26
+ /** The default localhost listener ID (set once during becomeCoordinator). */
27
+ private defaultListenerId;
28
+ private _isCoordinator;
29
+ private coordinatorSocket;
30
+ private peerConnections;
31
+ private dataServerSockets;
32
+ private coordinatorServerSockets;
33
+ private introConnections;
34
+ private pendingConnections;
35
+ private shutDown;
36
+ private _peerId;
37
+ private readonly events;
38
+ private readonly identity;
39
+ constructor(events: TransportEvents, identity: PeerIdentity);
40
+ get dataPort(): number;
41
+ get isCoordinator(): boolean;
42
+ private get tlsOptions();
43
+ private get connectOptions();
44
+ startDataServer(): Promise<void>;
45
+ connectToCoordinator(host: string, port: number, peerId: string, localDataPort: number): Promise<void>;
46
+ connectToRemote(host: string, port: number, peerId: string, localDataPort: number, name: string, fingerprint: string): Promise<void>;
47
+ becomeCoordinator(host: string, port: number): Promise<void>;
48
+ addListener(host: string, port: number, policy: ListenerPolicy): Promise<string>;
49
+ removeListener(id: string): Promise<void>;
50
+ listListeners(): ListenerInfo[];
51
+ connectToPeer(peer: PeerInfo, ownPeerId: string): Promise<void>;
52
+ send(handle: ConnectionHandle, message: MeshMessage): Promise<void>;
53
+ acceptConnection(handle: ConnectionHandle): Promise<void>;
54
+ rejectConnection(handle: ConnectionHandle, reason: string): Promise<void>;
55
+ broadcast(message: MeshMessage): Promise<void>;
56
+ shutdown(): Promise<void>;
57
+ unref(): void;
58
+ private dispatchCoordinatorClientMessage;
59
+ private dispatchDataMessage;
60
+ /**
61
+ * Accepts a new connection on a coordinator server. Reads
62
+ * introduce messages and fires onIntroduction so MeshStore can
63
+ * respond with the peer list and broadcast the arrival.
64
+ * The connection is tagged with the listener's policy.
65
+ */
66
+ private handleCoordinatorServerConnection;
67
+ private handleIncomingDataConnection;
68
+ }
69
+ //# sourceMappingURL=tls-transport.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"tls-transport.d.ts","sourceRoot":"","sources":["../../src/core/tls-transport.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;GAiBG;AAKH,OAAO,KAAK,EAAE,WAAW,EAAE,QAAQ,EAAE,MAAM,oBAAoB,CAAC;AAChE,OAAO,KAAK,EACV,gBAAgB,EAChB,YAAY,EACZ,cAAc,EACd,eAAe,EAChB,MAAM,gBAAgB,CAAC;AACxB,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,eAAe,CAAC;AAkClD,qBAAa,YAAY;IAEvB,OAAO,CAAC,UAAU,CAAyB;IAC3C,OAAO,CAAC,SAAS,CAAK;IAGtB,OAAO,CAAC,oBAAoB,CASxB;IACJ,6EAA6E;IAC7E,OAAO,CAAC,iBAAiB,CAAqB;IAC9C,OAAO,CAAC,cAAc,CAAS;IAG/B,OAAO,CAAC,iBAAiB,CAA4B;IAGrD,OAAO,CAAC,eAAe,CAGnB;IAGJ,OAAO,CAAC,iBAAiB,CAA4B;IAGrD,OAAO,CAAC,wBAAwB,CAA4B;IAG5D,OAAO,CAAC,gBAAgB,CAAoC;IAG5D,OAAO,CAAC,kBAAkB,CAUtB;IAGJ,OAAO,CAAC,QAAQ,CAAS;IAGzB,OAAO,CAAC,OAAO,CAAM;IAErB,OAAO,CAAC,QAAQ,CAAC,MAAM,CAAkB;IACzC,OAAO,CAAC,QAAQ,CAAC,QAAQ,CAAe;gBAE5B,MAAM,EAAE,eAAe,EAAE,QAAQ,EAAE,YAAY;IAO3D,IAAI,QAAQ,IAAI,MAAM,CAErB;IAED,IAAI,aAAa,IAAI,OAAO,CAE3B;IAMD,OAAO,KAAK,UAAU,GASrB;IAED,OAAO,KAAK,cAAc,GAOzB;IAMK,eAAe,IAAI,OAAO,CAAC,IAAI,CAAC;IAoBhC,oBAAoB,CACxB,IAAI,EAAE,MAAM,EACZ,IAAI,EAAE,MAAM,EACZ,MAAM,EAAE,MAAM,EACd,aAAa,EAAE,MAAM,GACpB,OAAO,CAAC,IAAI,CAAC;IAiDV,eAAe,CACnB,IAAI,EAAE,MAAM,EACZ,IAAI,EAAE,MAAM,EACZ,MAAM,EAAE,MAAM,EACd,aAAa,EAAE,MAAM,EACrB,IAAI,EAAE,MAAM,EACZ,WAAW,EAAE,MAAM,GAClB,OAAO,CAAC,IAAI,CAAC;IA8DV,iBAAiB,CAAC,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IA8B5D,WAAW,CACf,IAAI,EAAE,MAAM,EACZ,IAAI,EAAE,MAAM,EACZ,MAAM,EAAE,cAAc,GACrB,OAAO,CAAC,MAAM,CAAC;IAgCZ,cAAc,CAAC,EAAE,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAc/C,aAAa,IAAI,YAAY,EAAE;IAkBzB,aAAa,CAAC,IAAI,EAAE,QAAQ,EAAE,SAAS,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAuD/D,IAAI,CAAC,MAAM,EAAE,gBAAgB,EAAE,OAAO,EAAE,WAAW,GAAG,OAAO,CAAC,IAAI,CAAC;IAkBnE,gBAAgB,CAAC,MAAM,EAAE,gBAAgB,GAAG,OAAO,CAAC,IAAI,CAAC;IA4BzD,gBAAgB,CACpB,MAAM,EAAE,gBAAgB,EACxB,MAAM,EAAE,MAAM,GACb,OAAO,CAAC,IAAI,CAAC;IAkBV,SAAS,CAAC,OAAO,EAAE,WAAW,GAAG,OAAO,CAAC,IAAI,CAAC;IAiB9C,QAAQ,IAAI,OAAO,CAAC,IAAI,CAAC;IAuD/B,KAAK,IAAI,IAAI;IAYb,OAAO,CAAC,gCAAgC;IAgBxC,OAAO,CAAC,mBAAmB;IAiB3B;;;;;OAKG;IACH,OAAO,CAAC,iCAAiC;IAmDzC,OAAO,CAAC,4BAA4B;CAoDrC"}