@rookdaemon/agora 0.1.2 → 0.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 (68) hide show
  1. package/README.md +457 -1
  2. package/dist/cli.js +627 -37
  3. package/dist/cli.js.map +1 -1
  4. package/dist/config.d.ts +44 -0
  5. package/dist/config.d.ts.map +1 -0
  6. package/dist/config.js +74 -0
  7. package/dist/config.js.map +1 -0
  8. package/dist/discovery/bootstrap.d.ts +32 -0
  9. package/dist/discovery/bootstrap.d.ts.map +1 -0
  10. package/dist/discovery/bootstrap.js +36 -0
  11. package/dist/discovery/bootstrap.js.map +1 -0
  12. package/dist/discovery/peer-discovery.d.ts +59 -0
  13. package/dist/discovery/peer-discovery.d.ts.map +1 -0
  14. package/dist/discovery/peer-discovery.js +108 -0
  15. package/dist/discovery/peer-discovery.js.map +1 -0
  16. package/dist/index.d.ts +9 -0
  17. package/dist/index.d.ts.map +1 -1
  18. package/dist/index.js +9 -0
  19. package/dist/index.js.map +1 -1
  20. package/dist/message/envelope.d.ts +1 -1
  21. package/dist/message/envelope.d.ts.map +1 -1
  22. package/dist/message/envelope.js.map +1 -1
  23. package/dist/message/types/paper-discovery.d.ts +28 -0
  24. package/dist/message/types/paper-discovery.d.ts.map +1 -0
  25. package/dist/message/types/paper-discovery.js +2 -0
  26. package/dist/message/types/paper-discovery.js.map +1 -0
  27. package/dist/message/types/peer-discovery.d.ts +78 -0
  28. package/dist/message/types/peer-discovery.d.ts.map +1 -0
  29. package/dist/message/types/peer-discovery.js +90 -0
  30. package/dist/message/types/peer-discovery.js.map +1 -0
  31. package/dist/peer/client.d.ts +50 -0
  32. package/dist/peer/client.d.ts.map +1 -0
  33. package/dist/peer/client.js +138 -0
  34. package/dist/peer/client.js.map +1 -0
  35. package/dist/peer/manager.d.ts +65 -0
  36. package/dist/peer/manager.d.ts.map +1 -0
  37. package/dist/peer/manager.js +153 -0
  38. package/dist/peer/manager.js.map +1 -0
  39. package/dist/peer/server.d.ts +65 -0
  40. package/dist/peer/server.d.ts.map +1 -0
  41. package/dist/peer/server.js +154 -0
  42. package/dist/peer/server.js.map +1 -0
  43. package/dist/registry/discovery-service.d.ts +64 -0
  44. package/dist/registry/discovery-service.d.ts.map +1 -0
  45. package/dist/registry/discovery-service.js +129 -0
  46. package/dist/registry/discovery-service.js.map +1 -0
  47. package/dist/registry/messages.d.ts +55 -0
  48. package/dist/registry/messages.d.ts.map +1 -1
  49. package/dist/relay/client.d.ts +112 -0
  50. package/dist/relay/client.d.ts.map +1 -0
  51. package/dist/relay/client.js +281 -0
  52. package/dist/relay/client.js.map +1 -0
  53. package/dist/relay/server.d.ts +76 -0
  54. package/dist/relay/server.d.ts.map +1 -0
  55. package/dist/relay/server.js +338 -0
  56. package/dist/relay/server.js.map +1 -0
  57. package/dist/relay/types.d.ts +35 -0
  58. package/dist/relay/types.d.ts.map +1 -0
  59. package/dist/relay/types.js +2 -0
  60. package/dist/relay/types.js.map +1 -0
  61. package/dist/transport/peer-config.d.ts +3 -2
  62. package/dist/transport/peer-config.d.ts.map +1 -1
  63. package/dist/transport/peer-config.js.map +1 -1
  64. package/dist/transport/relay.d.ts +23 -0
  65. package/dist/transport/relay.d.ts.map +1 -0
  66. package/dist/transport/relay.js +85 -0
  67. package/dist/transport/relay.js.map +1 -0
  68. package/package.json +7 -2
@@ -0,0 +1,338 @@
1
+ import { EventEmitter } from 'node:events';
2
+ import { WebSocketServer, WebSocket } from 'ws';
3
+ import { verifyEnvelope, createEnvelope } from '../message/envelope.js';
4
+ /**
5
+ * WebSocket relay server for routing messages between agents.
6
+ *
7
+ * Agents connect to the relay and register with their public key.
8
+ * Messages are routed to recipients based on the 'to' field.
9
+ * All envelopes are verified before being forwarded.
10
+ */
11
+ export class RelayServer extends EventEmitter {
12
+ wss = null;
13
+ agents = new Map();
14
+ identity;
15
+ constructor(identity) {
16
+ super();
17
+ this.identity = identity;
18
+ }
19
+ /**
20
+ * Start the relay server
21
+ */
22
+ start(port) {
23
+ return new Promise((resolve, reject) => {
24
+ try {
25
+ this.wss = new WebSocketServer({ port });
26
+ let resolved = false;
27
+ this.wss.on('error', (error) => {
28
+ this.emit('error', error);
29
+ if (!resolved) {
30
+ resolved = true;
31
+ reject(error);
32
+ }
33
+ });
34
+ this.wss.on('listening', () => {
35
+ if (!resolved) {
36
+ resolved = true;
37
+ resolve();
38
+ }
39
+ });
40
+ this.wss.on('connection', (socket) => {
41
+ this.handleConnection(socket);
42
+ });
43
+ }
44
+ catch (error) {
45
+ reject(error);
46
+ }
47
+ });
48
+ }
49
+ /**
50
+ * Stop the relay server
51
+ */
52
+ async stop() {
53
+ return new Promise((resolve, reject) => {
54
+ if (!this.wss) {
55
+ resolve();
56
+ return;
57
+ }
58
+ // Close all agent connections
59
+ for (const agent of this.agents.values()) {
60
+ agent.socket.close();
61
+ }
62
+ this.agents.clear();
63
+ this.wss.close((err) => {
64
+ if (err) {
65
+ reject(err);
66
+ }
67
+ else {
68
+ this.wss = null;
69
+ resolve();
70
+ }
71
+ });
72
+ });
73
+ }
74
+ /**
75
+ * Get all connected agents
76
+ */
77
+ getAgents() {
78
+ return new Map(this.agents);
79
+ }
80
+ /**
81
+ * Handle incoming connection
82
+ */
83
+ handleConnection(socket) {
84
+ let agentPublicKey = null;
85
+ socket.on('message', (data) => {
86
+ try {
87
+ const msg = JSON.parse(data.toString());
88
+ // Handle registration
89
+ if (msg.type === 'register' && !agentPublicKey) {
90
+ if (!msg.publicKey || typeof msg.publicKey !== 'string') {
91
+ this.sendError(socket, 'Invalid registration: missing or invalid publicKey');
92
+ socket.close();
93
+ return;
94
+ }
95
+ const publicKey = msg.publicKey;
96
+ const name = msg.name;
97
+ agentPublicKey = publicKey;
98
+ const agent = {
99
+ publicKey,
100
+ name,
101
+ socket,
102
+ lastSeen: Date.now(),
103
+ };
104
+ this.agents.set(publicKey, agent);
105
+ this.emit('agent-registered', publicKey);
106
+ // Send registration confirmation with list of online peers
107
+ const peers = Array.from(this.agents.values())
108
+ .filter(a => a.publicKey !== publicKey)
109
+ .map(a => ({ publicKey: a.publicKey, name: a.name }));
110
+ socket.send(JSON.stringify({
111
+ type: 'registered',
112
+ publicKey,
113
+ peers,
114
+ }));
115
+ // Notify other agents that this agent is now online
116
+ this.broadcastPeerEvent('peer_online', publicKey, name);
117
+ return;
118
+ }
119
+ // Require registration before processing messages
120
+ if (!agentPublicKey) {
121
+ this.sendError(socket, 'Not registered: send registration message first');
122
+ socket.close();
123
+ return;
124
+ }
125
+ // Handle message relay
126
+ if (msg.type === 'message') {
127
+ if (!msg.to || typeof msg.to !== 'string') {
128
+ this.sendError(socket, 'Invalid message: missing or invalid "to" field');
129
+ return;
130
+ }
131
+ if (!msg.envelope || typeof msg.envelope !== 'object') {
132
+ this.sendError(socket, 'Invalid message: missing or invalid "envelope" field');
133
+ return;
134
+ }
135
+ const envelope = msg.envelope;
136
+ // Verify envelope signature
137
+ const verification = verifyEnvelope(envelope);
138
+ if (!verification.valid) {
139
+ this.sendError(socket, `Invalid envelope: ${verification.reason || 'verification failed'}`);
140
+ return;
141
+ }
142
+ // Verify sender matches registered agent
143
+ if (envelope.sender !== agentPublicKey) {
144
+ this.sendError(socket, 'Envelope sender does not match registered public key');
145
+ return;
146
+ }
147
+ // Update lastSeen timestamp
148
+ const senderAgent = this.agents.get(agentPublicKey);
149
+ if (senderAgent) {
150
+ senderAgent.lastSeen = Date.now();
151
+ }
152
+ // Handle peer_list_request directed at relay
153
+ if (envelope.type === 'peer_list_request' && this.identity && msg.to === this.identity.publicKey) {
154
+ this.handlePeerListRequest(envelope, socket, agentPublicKey);
155
+ return;
156
+ }
157
+ // Find recipient
158
+ const recipient = this.agents.get(msg.to);
159
+ if (!recipient || recipient.socket.readyState !== WebSocket.OPEN) {
160
+ this.sendError(socket, 'Recipient not connected');
161
+ return;
162
+ }
163
+ // Forward envelope to recipient wrapped in relay message format
164
+ try {
165
+ const senderAgent = this.agents.get(agentPublicKey);
166
+ const relayMessage = {
167
+ type: 'message',
168
+ from: agentPublicKey,
169
+ name: senderAgent?.name,
170
+ envelope,
171
+ };
172
+ recipient.socket.send(JSON.stringify(relayMessage));
173
+ this.emit('message-relayed', agentPublicKey, msg.to, envelope);
174
+ }
175
+ catch (err) {
176
+ this.sendError(socket, 'Failed to relay message');
177
+ this.emit('error', err);
178
+ }
179
+ return;
180
+ }
181
+ // Handle broadcast: same validation as message, then forward to all other agents
182
+ if (msg.type === 'broadcast') {
183
+ if (!msg.envelope || typeof msg.envelope !== 'object') {
184
+ this.sendError(socket, 'Invalid broadcast: missing or invalid "envelope" field');
185
+ return;
186
+ }
187
+ const envelope = msg.envelope;
188
+ const verification = verifyEnvelope(envelope);
189
+ if (!verification.valid) {
190
+ this.sendError(socket, `Invalid envelope: ${verification.reason || 'verification failed'}`);
191
+ return;
192
+ }
193
+ if (envelope.sender !== agentPublicKey) {
194
+ this.sendError(socket, 'Envelope sender does not match registered public key');
195
+ return;
196
+ }
197
+ // Update lastSeen timestamp
198
+ const senderAgentBroadcast = this.agents.get(agentPublicKey);
199
+ if (senderAgentBroadcast) {
200
+ senderAgentBroadcast.lastSeen = Date.now();
201
+ }
202
+ const senderAgent = this.agents.get(agentPublicKey);
203
+ const relayMessage = {
204
+ type: 'message',
205
+ from: agentPublicKey,
206
+ name: senderAgent?.name,
207
+ envelope,
208
+ };
209
+ const messageStr = JSON.stringify(relayMessage);
210
+ for (const agent of this.agents.values()) {
211
+ if (agent.publicKey !== agentPublicKey && agent.socket.readyState === WebSocket.OPEN) {
212
+ try {
213
+ agent.socket.send(messageStr);
214
+ }
215
+ catch (err) {
216
+ this.emit('error', err);
217
+ }
218
+ }
219
+ }
220
+ return;
221
+ }
222
+ // Handle ping
223
+ if (msg.type === 'ping') {
224
+ socket.send(JSON.stringify({ type: 'pong' }));
225
+ return;
226
+ }
227
+ // Unknown message type
228
+ this.sendError(socket, `Unknown message type: ${msg.type}`);
229
+ }
230
+ catch (err) {
231
+ // Invalid JSON or other parsing errors
232
+ this.emit('error', new Error(`Message parsing failed: ${err instanceof Error ? err.message : String(err)}`));
233
+ this.sendError(socket, 'Invalid message format');
234
+ }
235
+ });
236
+ socket.on('close', () => {
237
+ if (agentPublicKey) {
238
+ const agent = this.agents.get(agentPublicKey);
239
+ const agentName = agent?.name;
240
+ this.agents.delete(agentPublicKey);
241
+ this.emit('agent-disconnected', agentPublicKey);
242
+ // Notify other agents that this agent went offline
243
+ this.broadcastPeerEvent('peer_offline', agentPublicKey, agentName);
244
+ }
245
+ });
246
+ socket.on('error', (error) => {
247
+ this.emit('error', error);
248
+ });
249
+ }
250
+ /**
251
+ * Send an error message to a client
252
+ */
253
+ sendError(socket, message) {
254
+ try {
255
+ if (socket.readyState === WebSocket.OPEN) {
256
+ socket.send(JSON.stringify({ type: 'error', message }));
257
+ }
258
+ }
259
+ catch (err) {
260
+ // Log errors when sending error messages, but don't propagate to avoid cascading failures
261
+ this.emit('error', new Error(`Failed to send error message: ${err instanceof Error ? err.message : String(err)}`));
262
+ }
263
+ }
264
+ /**
265
+ * Broadcast a peer event to all connected agents
266
+ */
267
+ broadcastPeerEvent(eventType, publicKey, name) {
268
+ const message = {
269
+ type: eventType,
270
+ publicKey,
271
+ name,
272
+ };
273
+ const messageStr = JSON.stringify(message);
274
+ for (const agent of this.agents.values()) {
275
+ // Don't send the event to the agent it's about
276
+ if (agent.publicKey !== publicKey && agent.socket.readyState === WebSocket.OPEN) {
277
+ try {
278
+ agent.socket.send(messageStr);
279
+ }
280
+ catch (err) {
281
+ this.emit('error', new Error(`Failed to send ${eventType} event: ${err instanceof Error ? err.message : String(err)}`));
282
+ }
283
+ }
284
+ }
285
+ }
286
+ /**
287
+ * Handle peer list request from an agent
288
+ */
289
+ handlePeerListRequest(envelope, socket, requesterPublicKey) {
290
+ if (!this.identity) {
291
+ this.sendError(socket, 'Relay does not support peer discovery (no identity configured)');
292
+ return;
293
+ }
294
+ const { filters } = envelope.payload;
295
+ const now = Date.now();
296
+ let peers = Array.from(this.agents.values());
297
+ // Filter out requester first
298
+ peers = peers.filter(p => p.publicKey !== requesterPublicKey);
299
+ // Apply filters
300
+ if (filters?.activeWithin) {
301
+ peers = peers.filter(p => (now - p.lastSeen) < filters.activeWithin);
302
+ }
303
+ if (filters?.limit && filters.limit > 0) {
304
+ peers = peers.slice(0, filters.limit);
305
+ }
306
+ // Build response payload
307
+ const response = {
308
+ peers: peers.map(p => ({
309
+ publicKey: p.publicKey,
310
+ metadata: p.name || p.metadata ? {
311
+ name: p.name,
312
+ version: p.metadata?.version,
313
+ capabilities: p.metadata?.capabilities,
314
+ } : undefined,
315
+ lastSeen: p.lastSeen,
316
+ })),
317
+ totalPeers: this.agents.size - 1, // Exclude requester from count
318
+ relayPublicKey: this.identity.publicKey,
319
+ };
320
+ // Create signed envelope
321
+ const responseEnvelope = createEnvelope('peer_list_response', this.identity.publicKey, this.identity.privateKey, response, envelope.id // Reply to the request
322
+ );
323
+ // Send response
324
+ const relayMessage = {
325
+ type: 'message',
326
+ from: this.identity.publicKey,
327
+ name: 'relay',
328
+ envelope: responseEnvelope,
329
+ };
330
+ try {
331
+ socket.send(JSON.stringify(relayMessage));
332
+ }
333
+ catch (err) {
334
+ this.emit('error', new Error(`Failed to send peer list response: ${err instanceof Error ? err.message : String(err)}`));
335
+ }
336
+ }
337
+ }
338
+ //# sourceMappingURL=server.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"server.js","sourceRoot":"","sources":["../../src/relay/server.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,35 @@
1
+ import type { Envelope } from '../message/envelope.js';
2
+ /**
3
+ * Messages sent from client to relay server
4
+ */
5
+ export interface RelayClientMessage {
6
+ type: 'register' | 'message' | 'broadcast' | 'ping';
7
+ publicKey?: string;
8
+ name?: string;
9
+ to?: string;
10
+ envelope?: Envelope;
11
+ }
12
+ /**
13
+ * Messages received from relay server
14
+ */
15
+ export interface RelayServerMessage {
16
+ type: 'registered' | 'message' | 'error' | 'pong' | 'peer_online' | 'peer_offline';
17
+ publicKey?: string;
18
+ name?: string;
19
+ from?: string;
20
+ envelope?: Envelope;
21
+ peers?: Array<{
22
+ publicKey: string;
23
+ name?: string;
24
+ }>;
25
+ code?: string;
26
+ message?: string;
27
+ }
28
+ /**
29
+ * Peer presence information
30
+ */
31
+ export interface RelayPeer {
32
+ publicKey: string;
33
+ name?: string;
34
+ }
35
+ //# sourceMappingURL=types.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../src/relay/types.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,wBAAwB,CAAC;AAEvD;;GAEG;AACH,MAAM,WAAW,kBAAkB;IACjC,IAAI,EAAE,UAAU,GAAG,SAAS,GAAG,WAAW,GAAG,MAAM,CAAC;IACpD,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,EAAE,CAAC,EAAE,MAAM,CAAC;IACZ,QAAQ,CAAC,EAAE,QAAQ,CAAC;CACrB;AAED;;GAEG;AACH,MAAM,WAAW,kBAAkB;IACjC,IAAI,EAAE,YAAY,GAAG,SAAS,GAAG,OAAO,GAAG,MAAM,GAAG,aAAa,GAAG,cAAc,CAAC;IACnF,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,QAAQ,CAAC,EAAE,QAAQ,CAAC;IACpB,KAAK,CAAC,EAAE,KAAK,CAAC;QAAE,SAAS,EAAE,MAAM,CAAC;QAAC,IAAI,CAAC,EAAE,MAAM,CAAA;KAAE,CAAC,CAAC;IACpD,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,OAAO,CAAC,EAAE,MAAM,CAAC;CAClB;AAED;;GAEG;AACH,MAAM,WAAW,SAAS;IACxB,SAAS,EAAE,MAAM,CAAC;IAClB,IAAI,CAAC,EAAE,MAAM,CAAC;CACf"}
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=types.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.js","sourceRoot":"","sources":["../../src/relay/types.ts"],"names":[],"mappings":""}
@@ -3,9 +3,10 @@ export interface PeerConfigFile {
3
3
  publicKey: string;
4
4
  privateKey: string;
5
5
  };
6
+ relay?: string;
6
7
  peers: Record<string, {
7
- url: string;
8
- token: string;
8
+ url?: string;
9
+ token?: string;
9
10
  publicKey: string;
10
11
  name?: string;
11
12
  }>;
@@ -1 +1 @@
1
- {"version":3,"file":"peer-config.d.ts","sourceRoot":"","sources":["../../src/transport/peer-config.ts"],"names":[],"mappings":"AAGA,MAAM,WAAW,cAAc;IAC7B,QAAQ,EAAE;QACR,SAAS,EAAE,MAAM,CAAC;QAClB,UAAU,EAAE,MAAM,CAAC;KACpB,CAAC;IACF,KAAK,EAAE,MAAM,CAAC,MAAM,EAAE;QACpB,GAAG,EAAE,MAAM,CAAC;QACZ,KAAK,EAAE,MAAM,CAAC;QACd,SAAS,EAAE,MAAM,CAAC;QAClB,IAAI,CAAC,EAAE,MAAM,CAAC;KACf,CAAC,CAAC;CACJ;AAED;;;;;GAKG;AACH,wBAAgB,cAAc,CAAC,IAAI,EAAE,MAAM,GAAG,cAAc,CAG3D;AAED;;;;GAIG;AACH,wBAAgB,cAAc,CAAC,IAAI,EAAE,MAAM,EAAE,MAAM,EAAE,cAAc,GAAG,IAAI,CAGzE;AAED;;;;;GAKG;AACH,wBAAgB,cAAc,CAAC,IAAI,EAAE,MAAM,GAAG,cAAc,CAc3D"}
1
+ {"version":3,"file":"peer-config.d.ts","sourceRoot":"","sources":["../../src/transport/peer-config.ts"],"names":[],"mappings":"AAGA,MAAM,WAAW,cAAc;IAC7B,QAAQ,EAAE;QACR,SAAS,EAAE,MAAM,CAAC;QAClB,UAAU,EAAE,MAAM,CAAC;KACpB,CAAC;IACF,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,KAAK,EAAE,MAAM,CAAC,MAAM,EAAE;QACpB,GAAG,CAAC,EAAE,MAAM,CAAC;QACb,KAAK,CAAC,EAAE,MAAM,CAAC;QACf,SAAS,EAAE,MAAM,CAAC;QAClB,IAAI,CAAC,EAAE,MAAM,CAAC;KACf,CAAC,CAAC;CACJ;AAED;;;;;GAKG;AACH,wBAAgB,cAAc,CAAC,IAAI,EAAE,MAAM,GAAG,cAAc,CAG3D;AAED;;;;GAIG;AACH,wBAAgB,cAAc,CAAC,IAAI,EAAE,MAAM,EAAE,MAAM,EAAE,cAAc,GAAG,IAAI,CAGzE;AAED;;;;;GAKG;AACH,wBAAgB,cAAc,CAAC,IAAI,EAAE,MAAM,GAAG,cAAc,CAc3D"}
@@ -1 +1 @@
1
- {"version":3,"file":"peer-config.js","sourceRoot":"","sources":["../../src/transport/peer-config.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAE,aAAa,EAAE,UAAU,EAAE,MAAM,SAAS,CAAC;AAClE,OAAO,EAAE,eAAe,EAAE,MAAM,wBAAwB,CAAC;AAezD;;;;;GAKG;AACH,MAAM,UAAU,cAAc,CAAC,IAAY;IACzC,MAAM,OAAO,GAAG,YAAY,CAAC,IAAI,EAAE,OAAO,CAAC,CAAC;IAC5C,OAAO,IAAI,CAAC,KAAK,CAAC,OAAO,CAAmB,CAAC;AAC/C,CAAC;AAED;;;;GAIG;AACH,MAAM,UAAU,cAAc,CAAC,IAAY,EAAE,MAAsB;IACjE,MAAM,OAAO,GAAG,IAAI,CAAC,SAAS,CAAC,MAAM,EAAE,IAAI,EAAE,CAAC,CAAC,CAAC;IAChD,aAAa,CAAC,IAAI,EAAE,OAAO,EAAE,OAAO,CAAC,CAAC;AACxC,CAAC;AAED;;;;;GAKG;AACH,MAAM,UAAU,cAAc,CAAC,IAAY;IACzC,IAAI,UAAU,CAAC,IAAI,CAAC,EAAE,CAAC;QACrB,OAAO,cAAc,CAAC,IAAI,CAAC,CAAC;IAC9B,CAAC;IAED,iDAAiD;IACjD,MAAM,QAAQ,GAAG,eAAe,EAAE,CAAC;IACnC,MAAM,MAAM,GAAmB;QAC7B,QAAQ;QACR,KAAK,EAAE,EAAE;KACV,CAAC;IAEF,cAAc,CAAC,IAAI,EAAE,MAAM,CAAC,CAAC;IAC7B,OAAO,MAAM,CAAC;AAChB,CAAC"}
1
+ {"version":3,"file":"peer-config.js","sourceRoot":"","sources":["../../src/transport/peer-config.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAE,aAAa,EAAE,UAAU,EAAE,MAAM,SAAS,CAAC;AAClE,OAAO,EAAE,eAAe,EAAE,MAAM,wBAAwB,CAAC;AAgBzD;;;;;GAKG;AACH,MAAM,UAAU,cAAc,CAAC,IAAY;IACzC,MAAM,OAAO,GAAG,YAAY,CAAC,IAAI,EAAE,OAAO,CAAC,CAAC;IAC5C,OAAO,IAAI,CAAC,KAAK,CAAC,OAAO,CAAmB,CAAC;AAC/C,CAAC;AAED;;;;GAIG;AACH,MAAM,UAAU,cAAc,CAAC,IAAY,EAAE,MAAsB;IACjE,MAAM,OAAO,GAAG,IAAI,CAAC,SAAS,CAAC,MAAM,EAAE,IAAI,EAAE,CAAC,CAAC,CAAC;IAChD,aAAa,CAAC,IAAI,EAAE,OAAO,EAAE,OAAO,CAAC,CAAC;AACxC,CAAC;AAED;;;;;GAKG;AACH,MAAM,UAAU,cAAc,CAAC,IAAY;IACzC,IAAI,UAAU,CAAC,IAAI,CAAC,EAAE,CAAC;QACrB,OAAO,cAAc,CAAC,IAAI,CAAC,CAAC;IAC9B,CAAC;IAED,iDAAiD;IACjD,MAAM,QAAQ,GAAG,eAAe,EAAE,CAAC;IACnC,MAAM,MAAM,GAAmB;QAC7B,QAAQ;QACR,KAAK,EAAE,EAAE;KACV,CAAC;IAEF,cAAc,CAAC,IAAI,EAAE,MAAM,CAAC,CAAC;IAC7B,OAAO,MAAM,CAAC;AAChB,CAAC"}
@@ -0,0 +1,23 @@
1
+ import { type MessageType } from '../message/envelope.js';
2
+ import type { RelayClient } from '../relay/client.js';
3
+ export interface RelayTransportConfig {
4
+ /** This agent's keypair */
5
+ identity: {
6
+ publicKey: string;
7
+ privateKey: string;
8
+ };
9
+ /** Relay server WebSocket URL (e.g., wss://agora-relay.lbsa71.net) */
10
+ relayUrl: string;
11
+ /** Optional persistent relay client (if provided, will use it instead of connect-per-message) */
12
+ relayClient?: RelayClient;
13
+ }
14
+ /**
15
+ * Send a signed envelope to a peer via relay server.
16
+ * If a persistent relayClient is provided in the config, uses that.
17
+ * Otherwise, connects to relay, registers, sends message, and disconnects.
18
+ */
19
+ export declare function sendViaRelay(config: RelayTransportConfig, peerPublicKey: string, type: MessageType, payload: unknown, inReplyTo?: string): Promise<{
20
+ ok: boolean;
21
+ error?: string;
22
+ }>;
23
+ //# sourceMappingURL=relay.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"relay.d.ts","sourceRoot":"","sources":["../../src/transport/relay.ts"],"names":[],"mappings":"AACA,OAAO,EAAiC,KAAK,WAAW,EAAE,MAAM,wBAAwB,CAAC;AACzF,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,oBAAoB,CAAC;AAEtD,MAAM,WAAW,oBAAoB;IACnC,2BAA2B;IAC3B,QAAQ,EAAE;QAAE,SAAS,EAAE,MAAM,CAAC;QAAC,UAAU,EAAE,MAAM,CAAA;KAAE,CAAC;IACpD,sEAAsE;IACtE,QAAQ,EAAE,MAAM,CAAC;IACjB,iGAAiG;IACjG,WAAW,CAAC,EAAE,WAAW,CAAC;CAC3B;AAED;;;;GAIG;AACH,wBAAsB,YAAY,CAChC,MAAM,EAAE,oBAAoB,EAC5B,aAAa,EAAE,MAAM,EACrB,IAAI,EAAE,WAAW,EACjB,OAAO,EAAE,OAAO,EAChB,SAAS,CAAC,EAAE,MAAM,GACjB,OAAO,CAAC;IAAE,EAAE,EAAE,OAAO,CAAC;IAAC,KAAK,CAAC,EAAE,MAAM,CAAA;CAAE,CAAC,CAiG1C"}
@@ -0,0 +1,85 @@
1
+ import WebSocket from 'ws';
2
+ import { createEnvelope } from '../message/envelope.js';
3
+ /**
4
+ * Send a signed envelope to a peer via relay server.
5
+ * If a persistent relayClient is provided in the config, uses that.
6
+ * Otherwise, connects to relay, registers, sends message, and disconnects.
7
+ */
8
+ export async function sendViaRelay(config, peerPublicKey, type, payload, inReplyTo) {
9
+ // If a persistent relay client is available, use it
10
+ if (config.relayClient && config.relayClient.connected()) {
11
+ const envelope = createEnvelope(type, config.identity.publicKey, config.identity.privateKey, payload, inReplyTo);
12
+ return config.relayClient.send(peerPublicKey, envelope);
13
+ }
14
+ // Otherwise, fall back to connect-per-message
15
+ return new Promise((resolve) => {
16
+ const ws = new WebSocket(config.relayUrl);
17
+ let registered = false;
18
+ let messageSent = false;
19
+ let resolved = false;
20
+ // Helper to resolve once
21
+ const resolveOnce = (result) => {
22
+ if (!resolved) {
23
+ resolved = true;
24
+ clearTimeout(timeout);
25
+ resolve(result);
26
+ }
27
+ };
28
+ // Set timeout for the entire operation
29
+ const timeout = setTimeout(() => {
30
+ if (!messageSent) {
31
+ ws.close();
32
+ resolveOnce({ ok: false, error: 'Relay connection timeout' });
33
+ }
34
+ }, 10000); // 10 second timeout
35
+ ws.on('open', () => {
36
+ // Send register message
37
+ const registerMsg = {
38
+ type: 'register',
39
+ publicKey: config.identity.publicKey,
40
+ };
41
+ ws.send(JSON.stringify(registerMsg));
42
+ });
43
+ ws.on('message', (data) => {
44
+ try {
45
+ const msg = JSON.parse(data.toString());
46
+ if (msg.type === 'registered' && !registered) {
47
+ registered = true;
48
+ // Create and sign the envelope
49
+ const envelope = createEnvelope(type, config.identity.publicKey, config.identity.privateKey, payload, inReplyTo);
50
+ // Send message via relay
51
+ const relayMsg = {
52
+ type: 'message',
53
+ to: peerPublicKey,
54
+ envelope,
55
+ };
56
+ ws.send(JSON.stringify(relayMsg));
57
+ messageSent = true;
58
+ // Close connection after sending
59
+ setTimeout(() => {
60
+ ws.close();
61
+ resolveOnce({ ok: true });
62
+ }, 100); // Small delay to ensure message is sent
63
+ }
64
+ else if (msg.type === 'error') {
65
+ ws.close();
66
+ resolveOnce({ ok: false, error: msg.message || 'Relay server error' });
67
+ }
68
+ }
69
+ catch (err) {
70
+ ws.close();
71
+ resolveOnce({ ok: false, error: err instanceof Error ? err.message : String(err) });
72
+ }
73
+ });
74
+ ws.on('error', (err) => {
75
+ ws.close();
76
+ resolveOnce({ ok: false, error: err.message });
77
+ });
78
+ ws.on('close', () => {
79
+ if (!messageSent) {
80
+ resolveOnce({ ok: false, error: 'Connection closed before message sent' });
81
+ }
82
+ });
83
+ });
84
+ }
85
+ //# sourceMappingURL=relay.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"relay.js","sourceRoot":"","sources":["../../src/transport/relay.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@rookdaemon/agora",
3
- "version": "0.1.2",
3
+ "version": "0.2.0",
4
4
  "description": "A coordination network for AI agents",
5
5
  "type": "module",
6
6
  "main": "./dist/index.js",
@@ -12,7 +12,8 @@
12
12
  "build": "tsc",
13
13
  "test": "node --import tsx --test test/*.test.ts",
14
14
  "lint": "eslint src test --ext .ts",
15
- "prepublishOnly": "npm run lint && npm run build && npm test"
15
+ "prepublishOnly": "npm run lint && npm run build && npm test",
16
+ "pretest": "npm run build"
16
17
  },
17
18
  "files": [
18
19
  "dist",
@@ -29,10 +30,14 @@
29
30
  "license": "MIT",
30
31
  "devDependencies": {
31
32
  "@types/node": "^25.1.0",
33
+ "@types/ws": "^8.18.1",
32
34
  "@typescript-eslint/eslint-plugin": "^8.54.0",
33
35
  "@typescript-eslint/parser": "^8.54.0",
34
36
  "eslint": "^9.39.2",
35
37
  "tsx": "^4.21.0",
36
38
  "typescript": "^5.9.3"
39
+ },
40
+ "dependencies": {
41
+ "ws": "^8.19.0"
37
42
  }
38
43
  }