@waku/core 0.0.20 → 0.0.22

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 (59) hide show
  1. package/CHANGELOG.md +48 -0
  2. package/bundle/index.js +290 -335
  3. package/bundle/lib/base_protocol.js +11 -6
  4. package/bundle/lib/message/version_0.js +1 -1
  5. package/bundle/lib/predefined_bootstrap_nodes.js +6 -6
  6. package/bundle/{version_0-9c941081.js → version_0-86411fdf.js} +3 -3
  7. package/dist/index.d.ts +3 -5
  8. package/dist/index.js +3 -5
  9. package/dist/index.js.map +1 -1
  10. package/dist/lib/base_protocol.d.ts +9 -5
  11. package/dist/lib/base_protocol.js +11 -6
  12. package/dist/lib/base_protocol.js.map +1 -1
  13. package/dist/lib/connection_manager.d.ts +7 -7
  14. package/dist/lib/connection_manager.js +152 -66
  15. package/dist/lib/connection_manager.js.map +1 -1
  16. package/dist/lib/filter/filter_rpc.js.map +1 -0
  17. package/dist/lib/filter/index.d.ts +2 -0
  18. package/dist/lib/filter/{v2/index.js → index.js} +20 -32
  19. package/dist/lib/filter/index.js.map +1 -0
  20. package/dist/lib/keep_alive_manager.d.ts +3 -6
  21. package/dist/lib/keep_alive_manager.js +1 -1
  22. package/dist/lib/keep_alive_manager.js.map +1 -1
  23. package/dist/lib/light_push/index.d.ts +1 -2
  24. package/dist/lib/light_push/index.js +1 -3
  25. package/dist/lib/light_push/index.js.map +1 -1
  26. package/dist/lib/predefined_bootstrap_nodes.js +6 -6
  27. package/dist/lib/predefined_bootstrap_nodes.js.map +1 -1
  28. package/dist/lib/store/index.d.ts +1 -2
  29. package/dist/lib/store/index.js +1 -3
  30. package/dist/lib/store/index.js.map +1 -1
  31. package/dist/lib/wait_for_remote_peer.js +3 -3
  32. package/dist/lib/wait_for_remote_peer.js.map +1 -1
  33. package/dist/lib/waku.d.ts +3 -4
  34. package/dist/lib/waku.js.map +1 -1
  35. package/package.json +10 -18
  36. package/src/index.ts +3 -9
  37. package/src/lib/base_protocol.ts +23 -9
  38. package/src/lib/connection_manager.ts +210 -98
  39. package/src/lib/filter/{v2/index.ts → index.ts} +27 -40
  40. package/src/lib/keep_alive_manager.ts +4 -8
  41. package/src/lib/light_push/index.ts +3 -3
  42. package/src/lib/predefined_bootstrap_nodes.ts +6 -6
  43. package/src/lib/store/index.ts +3 -3
  44. package/src/lib/wait_for_remote_peer.ts +7 -9
  45. package/src/lib/waku.ts +3 -4
  46. package/dist/lib/filter/v1/filter_rpc.d.ts +0 -23
  47. package/dist/lib/filter/v1/filter_rpc.js +0 -45
  48. package/dist/lib/filter/v1/filter_rpc.js.map +0 -1
  49. package/dist/lib/filter/v1/index.d.ts +0 -6
  50. package/dist/lib/filter/v1/index.js +0 -153
  51. package/dist/lib/filter/v1/index.js.map +0 -1
  52. package/dist/lib/filter/v2/filter_rpc.js.map +0 -1
  53. package/dist/lib/filter/v2/index.d.ts +0 -3
  54. package/dist/lib/filter/v2/index.js.map +0 -1
  55. package/src/lib/filter/v1/filter_rpc.ts +0 -53
  56. package/src/lib/filter/v1/index.ts +0 -248
  57. /package/dist/lib/filter/{v2/filter_rpc.d.ts → filter_rpc.d.ts} +0 -0
  58. /package/dist/lib/filter/{v2/filter_rpc.js → filter_rpc.js} +0 -0
  59. /package/src/lib/filter/{v2/filter_rpc.ts → filter_rpc.ts} +0 -0
@@ -1,12 +1,20 @@
1
- import type { Connection } from "@libp2p/interface-connection";
2
- import type { Libp2p } from "@libp2p/interface-libp2p";
3
1
  import type { PeerId } from "@libp2p/interface-peer-id";
4
2
  import type { PeerInfo } from "@libp2p/interface-peer-info";
5
- import type { ConnectionManagerOptions, IRelay } from "@waku/interfaces";
6
- import { Tags } from "@waku/interfaces";
3
+ import type { Peer } from "@libp2p/interface-peer-store";
4
+ import { CustomEvent, EventEmitter } from "@libp2p/interfaces/events";
5
+ import {
6
+ ConnectionManagerOptions,
7
+ EPeersByDiscoveryEvents,
8
+ IConnectionManager,
9
+ IPeersByDiscoveryEvents,
10
+ IRelay,
11
+ KeepAliveOptions,
12
+ PeersByDiscoveryResult,
13
+ } from "@waku/interfaces";
14
+ import { Libp2p, Tags } from "@waku/interfaces";
7
15
  import debug from "debug";
8
16
 
9
- import { KeepAliveManager, KeepAliveOptions } from "./keep_alive_manager.js";
17
+ import { KeepAliveManager } from "./keep_alive_manager.js";
10
18
 
11
19
  const log = debug("waku:connection-manager");
12
20
 
@@ -14,11 +22,14 @@ export const DEFAULT_MAX_BOOTSTRAP_PEERS_ALLOWED = 1;
14
22
  export const DEFAULT_MAX_DIAL_ATTEMPTS_FOR_PEER = 3;
15
23
  export const DEFAULT_MAX_PARALLEL_DIALS = 3;
16
24
 
17
- export class ConnectionManager {
25
+ export class ConnectionManager
26
+ extends EventEmitter<IPeersByDiscoveryEvents>
27
+ implements IConnectionManager
28
+ {
18
29
  private static instances = new Map<string, ConnectionManager>();
19
30
  private keepAliveManager: KeepAliveManager;
20
31
  private options: ConnectionManagerOptions;
21
- private libp2pComponents: Libp2p;
32
+ private libp2p: Libp2p;
22
33
  private dialAttemptsForPeer: Map<string, number> = new Map();
23
34
  private dialErrorsForPeer: Map<string, any> = new Map();
24
35
 
@@ -46,13 +57,58 @@ export class ConnectionManager {
46
57
  return instance;
47
58
  }
48
59
 
60
+ public async getPeersByDiscovery(): Promise<PeersByDiscoveryResult> {
61
+ const peersDiscovered = await this.libp2p.peerStore.all();
62
+ const peersConnected = this.libp2p
63
+ .getConnections()
64
+ .map((conn) => conn.remotePeer);
65
+
66
+ const peersDiscoveredByBootstrap: Peer[] = [];
67
+ const peersDiscoveredByPeerExchange: Peer[] = [];
68
+ const peersConnectedByBootstrap: Peer[] = [];
69
+ const peersConnectedByPeerExchange: Peer[] = [];
70
+
71
+ for (const peer of peersDiscovered) {
72
+ const tags = await this.getTagNamesForPeer(peer.id);
73
+
74
+ if (tags.includes(Tags.BOOTSTRAP)) {
75
+ peersDiscoveredByBootstrap.push(peer);
76
+ } else if (tags.includes(Tags.PEER_EXCHANGE)) {
77
+ peersDiscoveredByPeerExchange.push(peer);
78
+ }
79
+ }
80
+
81
+ for (const peerId of peersConnected) {
82
+ const peer = await this.libp2p.peerStore.get(peerId);
83
+ const tags = await this.getTagNamesForPeer(peerId);
84
+
85
+ if (tags.includes(Tags.BOOTSTRAP)) {
86
+ peersConnectedByBootstrap.push(peer);
87
+ } else if (tags.includes(Tags.PEER_EXCHANGE)) {
88
+ peersConnectedByPeerExchange.push(peer);
89
+ }
90
+ }
91
+
92
+ return {
93
+ DISCOVERED: {
94
+ [Tags.BOOTSTRAP]: peersDiscoveredByBootstrap,
95
+ [Tags.PEER_EXCHANGE]: peersDiscoveredByPeerExchange,
96
+ },
97
+ CONNECTED: {
98
+ [Tags.BOOTSTRAP]: peersConnectedByBootstrap,
99
+ [Tags.PEER_EXCHANGE]: peersConnectedByPeerExchange,
100
+ },
101
+ };
102
+ }
103
+
49
104
  private constructor(
50
- libp2pComponents: Libp2p,
105
+ libp2p: Libp2p,
51
106
  keepAliveOptions: KeepAliveOptions,
52
107
  relay?: IRelay,
53
108
  options?: Partial<ConnectionManagerOptions>
54
109
  ) {
55
- this.libp2pComponents = libp2pComponents;
110
+ super();
111
+ this.libp2p = libp2p;
56
112
  this.options = {
57
113
  maxDialAttemptsForPeer: DEFAULT_MAX_DIAL_ATTEMPTS_FOR_PEER,
58
114
  maxBootstrapPeersAllowed: DEFAULT_MAX_BOOTSTRAP_PEERS_ALLOWED,
@@ -69,17 +125,17 @@ export class ConnectionManager {
69
125
  // libp2p emits `peer:discovery` events during its initialization
70
126
  // which means that before the ConnectionManager is initialized, some peers may have been discovered
71
127
  // we will dial the peers in peerStore ONCE before we start to listen to the `peer:discovery` events within the ConnectionManager
72
- this.dialPeerStorePeers();
128
+ this.dialPeerStorePeers().catch((error) =>
129
+ log(`Unexpected error while dialing peer store peers`, error)
130
+ );
73
131
  }
74
132
 
75
133
  private async dialPeerStorePeers(): Promise<void> {
76
- const peerInfos = await this.libp2pComponents.peerStore.all();
134
+ const peerInfos = await this.libp2p.peerStore.all();
77
135
  const dialPromises = [];
78
136
  for (const peerInfo of peerInfos) {
79
137
  if (
80
- this.libp2pComponents
81
- .getConnections()
82
- .find((c) => c.remotePeer === peerInfo.id)
138
+ this.libp2p.getConnections().find((c) => c.remotePeer === peerInfo.id)
83
139
  )
84
140
  continue;
85
141
 
@@ -101,15 +157,15 @@ export class ConnectionManager {
101
157
 
102
158
  stop(): void {
103
159
  this.keepAliveManager.stopAll();
104
- this.libp2pComponents.removeEventListener(
160
+ this.libp2p.removeEventListener(
105
161
  "peer:connect",
106
162
  this.onEventHandlers["peer:connect"]
107
163
  );
108
- this.libp2pComponents.removeEventListener(
164
+ this.libp2p.removeEventListener(
109
165
  "peer:disconnect",
110
166
  this.onEventHandlers["peer:disconnect"]
111
167
  );
112
- this.libp2pComponents.removeEventListener(
168
+ this.libp2p.removeEventListener(
113
169
  "peer:discovery",
114
170
  this.onEventHandlers["peer:discovery"]
115
171
  );
@@ -118,57 +174,74 @@ export class ConnectionManager {
118
174
  private async dialPeer(peerId: PeerId): Promise<void> {
119
175
  this.currentActiveDialCount += 1;
120
176
  let dialAttempt = 0;
121
- while (dialAttempt <= this.options.maxDialAttemptsForPeer) {
177
+ while (dialAttempt < this.options.maxDialAttemptsForPeer) {
122
178
  try {
123
- log(`Dialing peer ${peerId.toString()}`);
124
- await this.libp2pComponents.dial(peerId);
179
+ log(`Dialing peer ${peerId.toString()} on attempt ${dialAttempt + 1}`);
180
+ await this.libp2p.dial(peerId);
125
181
 
126
182
  const tags = await this.getTagNamesForPeer(peerId);
127
183
  // add tag to connection describing discovery mechanism
128
184
  // don't add duplicate tags
129
- this.libp2pComponents
130
- .getConnections(peerId)
131
- .forEach(
132
- (conn) => (conn.tags = Array.from(new Set([...conn.tags, ...tags])))
133
- );
185
+ this.libp2p.getConnections(peerId).forEach((conn) => {
186
+ conn.tags = Array.from(new Set([...conn.tags, ...tags]));
187
+ });
134
188
 
135
189
  this.dialAttemptsForPeer.delete(peerId.toString());
136
- return;
137
- } catch (e) {
138
- const error = e as AggregateError;
139
-
190
+ // Dialing succeeded, break the loop
191
+ break;
192
+ } catch (error) {
193
+ if (error instanceof AggregateError) {
194
+ // Handle AggregateError
195
+ log(`Error dialing peer ${peerId.toString()} - ${error.errors}`);
196
+ } else {
197
+ // Handle generic error
198
+ log(
199
+ `Error dialing peer ${peerId.toString()} - ${
200
+ (error as any).message
201
+ }`
202
+ );
203
+ }
140
204
  this.dialErrorsForPeer.set(peerId.toString(), error);
141
- log(`Error dialing peer ${peerId.toString()} - ${error.errors}`);
142
205
 
143
- dialAttempt = this.dialAttemptsForPeer.get(peerId.toString()) ?? 1;
144
- this.dialAttemptsForPeer.set(peerId.toString(), dialAttempt + 1);
145
-
146
- if (dialAttempt <= this.options.maxDialAttemptsForPeer) {
147
- log(`Reattempting dial (${dialAttempt})`);
148
- }
206
+ dialAttempt++;
207
+ this.dialAttemptsForPeer.set(peerId.toString(), dialAttempt);
149
208
  }
150
209
  }
151
210
 
152
- try {
153
- log(
154
- `Deleting undialable peer ${peerId.toString()} from peer store. Error: ${JSON.stringify(
155
- this.dialErrorsForPeer.get(peerId.toString()).errors[0]
156
- )}
157
- }`
158
- );
159
- this.dialErrorsForPeer.delete(peerId.toString());
160
- return await this.libp2pComponents.peerStore.delete(peerId);
161
- } catch (error) {
162
- throw `Error deleting undialable peer ${peerId.toString()} from peer store - ${error}`;
163
- } finally {
164
- this.currentActiveDialCount -= 1;
165
- this.processDialQueue();
211
+ // Always decrease the active dial count and process the dial queue
212
+ this.currentActiveDialCount--;
213
+ this.processDialQueue();
214
+
215
+ // If max dial attempts reached and dialing failed, delete the peer
216
+ if (dialAttempt === this.options.maxDialAttemptsForPeer) {
217
+ try {
218
+ const error = this.dialErrorsForPeer.get(peerId.toString());
219
+
220
+ let errorMessage;
221
+ if (error instanceof AggregateError) {
222
+ errorMessage = JSON.stringify(error.errors[0]);
223
+ } else {
224
+ errorMessage = error.message;
225
+ }
226
+
227
+ log(
228
+ `Deleting undialable peer ${peerId.toString()} from peer store. Error: ${errorMessage}`
229
+ );
230
+
231
+ this.dialErrorsForPeer.delete(peerId.toString());
232
+ await this.libp2p.peerStore.delete(peerId);
233
+ } catch (error) {
234
+ throw new Error(
235
+ `Error deleting undialable peer ${peerId.toString()} from peer store - ${error}`
236
+ );
237
+ }
166
238
  }
167
239
  }
168
240
 
169
- async dropConnection(peerId: PeerId): Promise<void> {
241
+ private async dropConnection(peerId: PeerId): Promise<void> {
170
242
  try {
171
- await this.libp2pComponents.hangUp(peerId);
243
+ this.keepAliveManager.stop(peerId);
244
+ await this.libp2p.hangUp(peerId);
172
245
  log(`Dropped connection with peer ${peerId.toString()}`);
173
246
  } catch (error) {
174
247
  log(
@@ -177,7 +250,7 @@ export class ConnectionManager {
177
250
  }
178
251
  }
179
252
 
180
- private async processDialQueue(): Promise<void> {
253
+ private processDialQueue(): void {
181
254
  if (
182
255
  this.pendingPeerDialQueue.length > 0 &&
183
256
  this.currentActiveDialCount < this.options.maxParallelDials
@@ -191,14 +264,14 @@ export class ConnectionManager {
191
264
  }
192
265
 
193
266
  private startPeerDiscoveryListener(): void {
194
- this.libp2pComponents.peerStore.addEventListener(
195
- "peer",
267
+ this.libp2p.addEventListener(
268
+ "peer:discovery",
196
269
  this.onEventHandlers["peer:discovery"]
197
270
  );
198
271
  }
199
272
 
200
273
  private startPeerConnectionListener(): void {
201
- this.libp2pComponents.addEventListener(
274
+ this.libp2p.addEventListener(
202
275
  "peer:connect",
203
276
  this.onEventHandlers["peer:connect"]
204
277
  );
@@ -217,7 +290,7 @@ export class ConnectionManager {
217
290
  * >this event will **only** be triggered when the last connection is closed.
218
291
  * @see https://github.com/libp2p/js-libp2p/blob/bad9e8c0ff58d60a78314077720c82ae331cc55b/doc/API.md?plain=1#L2100
219
292
  */
220
- this.libp2pComponents.addEventListener(
293
+ this.libp2p.addEventListener(
221
294
  "peer:disconnect",
222
295
  this.onEventHandlers["peer:disconnect"]
223
296
  );
@@ -237,41 +310,77 @@ export class ConnectionManager {
237
310
  }
238
311
 
239
312
  private onEventHandlers = {
240
- "peer:discovery": async (evt: CustomEvent<PeerInfo>): Promise<void> => {
241
- const { id: peerId } = evt.detail;
242
-
243
- this.attemptDial(peerId).catch((err) =>
244
- log(`Error dialing peer ${peerId.toString()} : ${err}`)
245
- );
313
+ "peer:discovery": (evt: CustomEvent<PeerInfo>): void => {
314
+ void (async () => {
315
+ const { id: peerId } = evt.detail;
316
+
317
+ const isBootstrap = (await this.getTagNamesForPeer(peerId)).includes(
318
+ Tags.BOOTSTRAP
319
+ );
320
+
321
+ this.dispatchEvent(
322
+ new CustomEvent<PeerId>(
323
+ isBootstrap
324
+ ? EPeersByDiscoveryEvents.PEER_DISCOVERY_BOOTSTRAP
325
+ : EPeersByDiscoveryEvents.PEER_DISCOVERY_PEER_EXCHANGE,
326
+ {
327
+ detail: peerId,
328
+ }
329
+ )
330
+ );
331
+
332
+ try {
333
+ await this.attemptDial(peerId);
334
+ } catch (error) {
335
+ log(`Error dialing peer ${peerId.toString()} : ${error}`);
336
+ }
337
+ })();
246
338
  },
247
- "peer:connect": async (evt: CustomEvent<Connection>): Promise<void> => {
248
- const { remotePeer: peerId } = evt.detail;
249
-
250
- this.keepAliveManager.start(
251
- peerId,
252
- this.libp2pComponents.ping.bind(this)
253
- );
254
-
255
- const isBootstrap = (await this.getTagNamesForPeer(peerId)).includes(
256
- Tags.BOOTSTRAP
257
- );
258
-
259
- if (isBootstrap) {
260
- const bootstrapConnections = this.libp2pComponents
261
- .getConnections()
262
- .filter((conn) => conn.tags.includes(Tags.BOOTSTRAP));
263
-
264
- // If we have too many bootstrap connections, drop one
265
- if (
266
- bootstrapConnections.length > this.options.maxBootstrapPeersAllowed
267
- ) {
268
- await this.dropConnection(peerId);
339
+ "peer:connect": (evt: CustomEvent<PeerId>): void => {
340
+ void (async () => {
341
+ const peerId = evt.detail;
342
+
343
+ this.keepAliveManager.start(peerId, this.libp2p.services.ping);
344
+
345
+ const isBootstrap = (await this.getTagNamesForPeer(peerId)).includes(
346
+ Tags.BOOTSTRAP
347
+ );
348
+
349
+ if (isBootstrap) {
350
+ const bootstrapConnections = this.libp2p
351
+ .getConnections()
352
+ .filter((conn) => conn.tags.includes(Tags.BOOTSTRAP));
353
+
354
+ // If we have too many bootstrap connections, drop one
355
+ if (
356
+ bootstrapConnections.length > this.options.maxBootstrapPeersAllowed
357
+ ) {
358
+ await this.dropConnection(peerId);
359
+ } else {
360
+ this.dispatchEvent(
361
+ new CustomEvent<PeerId>(
362
+ EPeersByDiscoveryEvents.PEER_CONNECT_BOOTSTRAP,
363
+ {
364
+ detail: peerId,
365
+ }
366
+ )
367
+ );
368
+ }
369
+ } else {
370
+ this.dispatchEvent(
371
+ new CustomEvent<PeerId>(
372
+ EPeersByDiscoveryEvents.PEER_CONNECT_PEER_EXCHANGE,
373
+ {
374
+ detail: peerId,
375
+ }
376
+ )
377
+ );
269
378
  }
270
- }
379
+ })();
271
380
  },
272
381
  "peer:disconnect": () => {
273
- return (evt: CustomEvent<Connection>): void => {
274
- this.keepAliveManager.stop(evt.detail.remotePeer);
382
+ return (evt: CustomEvent<PeerId>): void => {
383
+ this.keepAliveManager.stop(evt.detail);
275
384
  };
276
385
  },
277
386
  };
@@ -282,19 +391,19 @@ export class ConnectionManager {
282
391
  * 2. If the peer is not a bootstrap peer
283
392
  */
284
393
  private async shouldDialPeer(peerId: PeerId): Promise<boolean> {
285
- const isConnected = this.libp2pComponents.getConnections(peerId).length > 0;
394
+ const isConnected = this.libp2p.getConnections(peerId).length > 0;
286
395
 
287
396
  if (isConnected) return false;
288
397
 
289
- const isBootstrap = (await this.getTagNamesForPeer(peerId)).some(
290
- (tagName) => tagName === Tags.BOOTSTRAP
291
- );
398
+ const tagNames = await this.getTagNamesForPeer(peerId);
399
+
400
+ const isBootstrap = tagNames.some((tagName) => tagName === Tags.BOOTSTRAP);
292
401
 
293
402
  if (isBootstrap) {
294
- const currentBootstrapConnections = this.libp2pComponents
403
+ const currentBootstrapConnections = this.libp2p
295
404
  .getConnections()
296
405
  .filter((conn) => {
297
- conn.tags.find((name) => name === Tags.BOOTSTRAP);
406
+ return conn.tags.find((name) => name === Tags.BOOTSTRAP);
298
407
  }).length;
299
408
  if (currentBootstrapConnections < this.options.maxBootstrapPeersAllowed)
300
409
  return true;
@@ -309,9 +418,12 @@ export class ConnectionManager {
309
418
  * Fetches the tag names for a given peer
310
419
  */
311
420
  private async getTagNamesForPeer(peerId: PeerId): Promise<string[]> {
312
- const tags = (await this.libp2pComponents.peerStore.getTags(peerId)).map(
313
- (tag) => tag.name
314
- );
315
- return tags;
421
+ try {
422
+ const peer = await this.libp2p.peerStore.get(peerId);
423
+ return Array.from(peer.tags.keys());
424
+ } catch (error) {
425
+ log(`Failed to get peer ${peerId}, error: ${error}`);
426
+ return [];
427
+ }
316
428
  }
317
429
  }
@@ -1,5 +1,4 @@
1
1
  import { Stream } from "@libp2p/interface-connection";
2
- import type { Libp2p } from "@libp2p/interface-libp2p";
3
2
  import type { PeerId } from "@libp2p/interface-peer-id";
4
3
  import type { Peer } from "@libp2p/interface-peer-store";
5
4
  import type { IncomingStreamData } from "@libp2p/interface-registrar";
@@ -9,9 +8,10 @@ import type {
9
8
  IAsyncIterator,
10
9
  IDecodedMessage,
11
10
  IDecoder,
12
- IFilterV2,
11
+ IFilter,
13
12
  IProtoMessage,
14
13
  IReceiver,
14
+ Libp2p,
15
15
  PeerIdStr,
16
16
  ProtocolCreateOptions,
17
17
  ProtocolOptions,
@@ -25,8 +25,8 @@ import all from "it-all";
25
25
  import * as lp from "it-length-prefixed";
26
26
  import { pipe } from "it-pipe";
27
27
 
28
- import { BaseProtocol } from "../../base_protocol.js";
29
- import { DefaultPubSubTopic } from "../../constants.js";
28
+ import { BaseProtocol } from "../base_protocol.js";
29
+ import { DefaultPubSubTopic } from "../constants.js";
30
30
 
31
31
  import {
32
32
  FilterPushRpc,
@@ -41,7 +41,7 @@ type SubscriptionCallback<T extends IDecodedMessage> = {
41
41
  callback: Callback<T>;
42
42
  };
43
43
 
44
- const FilterV2Codecs = {
44
+ const FilterCodecs = {
45
45
  SUBSCRIBE: "/vac/waku/filter-subscribe/2.0.0-beta1",
46
46
  PUSH: "/vac/waku/filter-push/2.0.0-beta1",
47
47
  };
@@ -225,7 +225,7 @@ class Subscription {
225
225
  }
226
226
  }
227
227
 
228
- class FilterV2 extends BaseProtocol implements IReceiver {
228
+ class Filter extends BaseProtocol implements IReceiver {
229
229
  private readonly options: ProtocolCreateOptions;
230
230
  private activeSubscriptions = new Map<string, Subscription>();
231
231
 
@@ -245,18 +245,12 @@ class FilterV2 extends BaseProtocol implements IReceiver {
245
245
  return subscription;
246
246
  }
247
247
 
248
- constructor(public libp2p: Libp2p, options?: ProtocolCreateOptions) {
249
- super(
250
- FilterV2Codecs.SUBSCRIBE,
251
- libp2p.peerStore,
252
- libp2p.getConnections.bind(libp2p)
253
- );
248
+ constructor(libp2p: Libp2p, options?: ProtocolCreateOptions) {
249
+ super(FilterCodecs.SUBSCRIBE, libp2p.components);
254
250
 
255
- this.libp2p
256
- .handle(FilterV2Codecs.PUSH, this.onRequest.bind(this))
257
- .catch((e) => {
258
- log("Failed to register ", FilterV2Codecs.PUSH, e);
259
- });
251
+ libp2p.handle(FilterCodecs.PUSH, this.onRequest.bind(this)).catch((e) => {
252
+ log("Failed to register ", FilterCodecs.PUSH, e);
253
+ });
260
254
 
261
255
  this.activeSubscriptions = new Map();
262
256
 
@@ -312,7 +306,7 @@ class FilterV2 extends BaseProtocol implements IReceiver {
312
306
  ): Promise<Unsubscribe> {
313
307
  const subscription = await this.createSubscription(undefined, opts?.peerId);
314
308
 
315
- subscription.subscribe(decoders, callback);
309
+ await subscription.subscribe(decoders, callback);
316
310
 
317
311
  const contentTopics = Array.from(
318
312
  groupByContentTopic(
@@ -371,10 +365,10 @@ class FilterV2 extends BaseProtocol implements IReceiver {
371
365
  }
372
366
  }
373
367
 
374
- export function wakuFilterV2(
368
+ export function wakuFilter(
375
369
  init: Partial<ProtocolCreateOptions> = {}
376
- ): (libp2p: Libp2p) => IFilterV2 {
377
- return (libp2p: Libp2p) => new FilterV2(libp2p, init);
370
+ ): (libp2p: Libp2p) => IFilter {
371
+ return (libp2p: Libp2p) => new Filter(libp2p, init);
378
372
  }
379
373
 
380
374
  async function pushMessage<T extends IDecodedMessage>(
@@ -390,24 +384,17 @@ async function pushMessage<T extends IDecodedMessage>(
390
384
  return;
391
385
  }
392
386
 
393
- let didDecodeMsg = false;
394
- // We don't want to wait for decoding failure, just attempt to decode
395
- // all messages and do the call back on the one that works
396
- // noinspection ES6MissingAwait
397
- decoders.forEach(async (dec: IDecoder<T>) => {
398
- if (didDecodeMsg) return;
399
- const decoded = await dec.fromProtoObj(
400
- pubSubTopic,
401
- message as IProtoMessage
387
+ try {
388
+ const decodePromises = decoders.map((dec) =>
389
+ dec
390
+ .fromProtoObj(pubSubTopic, message as IProtoMessage)
391
+ .then((decoded) => decoded || Promise.reject("Decoding failed"))
402
392
  );
403
- // const decoded = await dec.fromProtoObj(pubSubTopic, message);
404
- if (!decoded) {
405
- log("Not able to decode message");
406
- return;
407
- }
408
- // This is just to prevent more decoding attempt
409
- // TODO: Could be better if we were to abort promises
410
- didDecodeMsg = Boolean(decoded);
411
- await callback(decoded);
412
- });
393
+
394
+ const decodedMessage = await Promise.any(decodePromises);
395
+
396
+ await callback(decodedMessage);
397
+ } catch (e) {
398
+ log("Error decoding message", e);
399
+ }
413
400
  }
@@ -1,18 +1,14 @@
1
1
  import type { PeerId } from "@libp2p/interface-peer-id";
2
2
  import type { IRelay } from "@waku/interfaces";
3
+ import type { KeepAliveOptions } from "@waku/interfaces";
3
4
  import debug from "debug";
4
- import type { Libp2p } from "libp2p";
5
+ import type { PingService } from "libp2p/ping";
5
6
 
6
7
  import { createEncoder } from "../index.js";
7
8
 
8
9
  export const RelayPingContentTopic = "/relay-ping/1/ping/null";
9
10
  const log = debug("waku:keep-alive");
10
11
 
11
- export interface KeepAliveOptions {
12
- pingKeepAlive: number;
13
- relayKeepAlive: number;
14
- }
15
-
16
12
  export class KeepAliveManager {
17
13
  private pingKeepAliveTimers: Map<string, ReturnType<typeof setInterval>>;
18
14
  private relayKeepAliveTimers: Map<PeerId, ReturnType<typeof setInterval>>;
@@ -26,7 +22,7 @@ export class KeepAliveManager {
26
22
  this.relay = relay;
27
23
  }
28
24
 
29
- public start(peerId: PeerId, libp2pPing: Libp2p["ping"]): void {
25
+ public start(peerId: PeerId, libp2pPing: PingService): void {
30
26
  // Just in case a timer already exist for this peer
31
27
  this.stop(peerId);
32
28
 
@@ -37,7 +33,7 @@ export class KeepAliveManager {
37
33
 
38
34
  if (pingPeriodSecs !== 0) {
39
35
  const interval = setInterval(() => {
40
- libp2pPing(peerId).catch((e) => {
36
+ libp2pPing.ping(peerId).catch((e) => {
41
37
  log(`Ping failed (${peerIdStr})`, e);
42
38
  });
43
39
  }, pingPeriodSecs * 1000);
@@ -1,9 +1,9 @@
1
- import type { Libp2p } from "@libp2p/interface-libp2p";
2
1
  import type { PeerId } from "@libp2p/interface-peer-id";
3
2
  import {
4
3
  IEncoder,
5
4
  ILightPush,
6
5
  IMessage,
6
+ Libp2p,
7
7
  ProtocolCreateOptions,
8
8
  ProtocolOptions,
9
9
  SendError,
@@ -33,8 +33,8 @@ export { PushResponse };
33
33
  class LightPush extends BaseProtocol implements ILightPush {
34
34
  options: ProtocolCreateOptions;
35
35
 
36
- constructor(public libp2p: Libp2p, options?: ProtocolCreateOptions) {
37
- super(LightPushCodec, libp2p.peerStore, libp2p.getConnections.bind(libp2p));
36
+ constructor(libp2p: Libp2p, options?: ProtocolCreateOptions) {
37
+ super(LightPushCodec, libp2p.components);
38
38
  this.options = options || {};
39
39
  }
40
40
 
@@ -47,21 +47,21 @@ export const fleets = {
47
47
  "wakuv2.prod": {
48
48
  "waku-websocket": {
49
49
  "node-01.ac-cn-hongkong-c.wakuv2.prod":
50
- "/dns4/node-01.ac-cn-hongkong-c.wakuv2.prod.statusim.net/tcp/443/wss/p2p/16Uiu2HAm4v86W3bmT1BiH6oSPzcsSr24iDQpSN5Qa992BCjjwgrD",
50
+ "/dns4/node-01.ac-cn-hongkong-c.wakuv2.prod.statusim.net/tcp/8000/wss/p2p/16Uiu2HAm4v86W3bmT1BiH6oSPzcsSr24iDQpSN5Qa992BCjjwgrD",
51
51
  "node-01.do-ams3.wakuv2.prod":
52
- "/dns4/node-01.do-ams3.wakuv2.prod.statusim.net/tcp/443/wss/p2p/16Uiu2HAmL5okWopX7NqZWBUKVqW8iUxCEmd5GMHLVPwCgzYzQv3e",
52
+ "/dns4/node-01.do-ams3.wakuv2.prod.statusim.net/tcp/8000/wss/p2p/16Uiu2HAmL5okWopX7NqZWBUKVqW8iUxCEmd5GMHLVPwCgzYzQv3e",
53
53
  "node-01.gc-us-central1-a.wakuv2.prod":
54
- "/dns4/node-01.gc-us-central1-a.wakuv2.prod.statusim.net/tcp/443/wss/p2p/16Uiu2HAmVkKntsECaYfefR1V2yCR79CegLATuTPE6B9TxgxBiiiA",
54
+ "/dns4/node-01.gc-us-central1-a.wakuv2.prod.statusim.net/tcp/8000/wss/p2p/16Uiu2HAmVkKntsECaYfefR1V2yCR79CegLATuTPE6B9TxgxBiiiA",
55
55
  },
56
56
  },
57
57
  "wakuv2.test": {
58
58
  "waku-websocket": {
59
59
  "node-01.ac-cn-hongkong-c.wakuv2.test":
60
- "/dns4/node-01.ac-cn-hongkong-c.wakuv2.test.statusim.net/tcp/443/wss/p2p/16Uiu2HAkvWiyFsgRhuJEb9JfjYxEkoHLgnUQmr1N5mKWnYjxYRVm",
60
+ "/dns4/node-01.ac-cn-hongkong-c.wakuv2.test.statusim.net/tcp/8000/wss/p2p/16Uiu2HAkvWiyFsgRhuJEb9JfjYxEkoHLgnUQmr1N5mKWnYjxYRVm",
61
61
  "node-01.do-ams3.wakuv2.test":
62
- "/dns4/node-01.do-ams3.wakuv2.test.statusim.net/tcp/443/wss/p2p/16Uiu2HAmPLe7Mzm8TsYUubgCAW1aJoeFScxrLj8ppHFivPo97bUZ",
62
+ "/dns4/node-01.do-ams3.wakuv2.test.statusim.net/tcp/8000/wss/p2p/16Uiu2HAmPLe7Mzm8TsYUubgCAW1aJoeFScxrLj8ppHFivPo97bUZ",
63
63
  "node-01.gc-us-central1-a.wakuv2.test":
64
- "/dns4/node-01.gc-us-central1-a.wakuv2.test.statusim.net/tcp/443/wss/p2p/16Uiu2HAmJb2e28qLXxT5kZxVUUoJt72EMzNGXB47Rxx5hw3q4YjS",
64
+ "/dns4/node-01.gc-us-central1-a.wakuv2.test.statusim.net/tcp/8000/wss/p2p/16Uiu2HAmJb2e28qLXxT5kZxVUUoJt72EMzNGXB47Rxx5hw3q4YjS",
65
65
  },
66
66
  },
67
67
  },