webpeerjs 0.0.9 → 0.0.10

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.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "webpeerjs",
3
- "version": "0.0.9",
3
+ "version": "0.0.10",
4
4
  "description": "Simple peer-to-peer with IPFS",
5
5
  "main": "./dist/umd/webpeerjs.js",
6
6
  "module": "./src/webpeerjs.js",
@@ -18,6 +18,7 @@
18
18
  "scripts": {
19
19
  "start": "npm run dev",
20
20
  "dev": "vite serve test",
21
+ "demo": "vite serve demo",
21
22
  "eslint": "eslint ./src",
22
23
  "eslint:fix": "eslint ./src --fix",
23
24
  "removedir": "node -e \"var fs = require('fs'); try{process.argv.slice(1).map((fpath) => fs.rmdirSync(fpath, { recursive: true }))}catch(err){console.log(`Dist not found`)}; process.exit(0);\"",
@@ -58,6 +59,7 @@
58
59
  "@libp2p/peer-id": "^4.1.2",
59
60
  "@libp2p/pubsub-peer-discovery": "^10.0.2",
60
61
  "@libp2p/simple-metrics": "^1.0.2",
62
+ "@libp2p/websockets": "^8.1.0",
61
63
  "@libp2p/webtransport": "^4.0.32",
62
64
  "datastore-idb": "^2.1.9",
63
65
  "libp2p": "^1.6.0"
package/src/config.js CHANGED
@@ -16,20 +16,23 @@ export const CONFIG_DELEGATED_API = 'https://delegated-ipfs.dev'
16
16
  export const CONFIG_DNS_RESOLVER = 'https://dns.google/resolve'
17
17
  export const CONFIG_KNOWN_BOOTSTRAP_DNS = '_dnsaddr.bootstrap.libp2p.io'
18
18
  export const CONFIG_JOIN_ROOM_VERSION = 1
19
+ export const CONFIG_TIMEOUT_DIAL_KNOWN_PEERS = 15000
20
+
21
+ // this list comes from https://github.com/ipfs/kubo/blob/196887cbe5fbcd41243c1dfb0db681a1cc2914ff/config/bootstrap_peers.go
22
+ export const CONFIG_KNOWN_DEFAULT_BOOTSTRAP_ADDRESSES = [
23
+ "/dnsaddr/bootstrap.libp2p.io/p2p/QmNnooDu7bfjPFoTZYxMNLWUQJyrVwtbZg5gBMjTezGAJN",
24
+ "/dnsaddr/bootstrap.libp2p.io/p2p/QmQCU2EcMqAqQPR2i9bChDtGNJchTbq5TbXJJ16u19uLTa",
25
+ "/dnsaddr/bootstrap.libp2p.io/p2p/QmbLHAnMoJPWSCR5Zhtx6BHJX9KiKNN6tpvbUcqanj75Nb",
26
+ "/dnsaddr/bootstrap.libp2p.io/p2p/QmcZf59bWwK5XFi76CZX8cbJ4BhTzzA3gU1ZjYZcYW3dwt",
27
+ "/ip4/104.131.131.82/tcp/4001/p2p/QmaCpDMGvV2BGHeYERUEnRQAwe3N8SzbUtfsmvsqQLuvuJ",
28
+ "/ip4/104.131.131.82/udp/4001/quic/p2p/QmaCpDMGvV2BGHeYERUEnRQAwe3N8SzbUtfsmvsqQLuvuJ"
29
+ ]
19
30
 
20
31
  export const CONFIG_KNOWN_BOOTSTRAP_PUBLIC_IDS = [
21
32
  'QmNnooDu7bfjPFoTZYxMNLWUQJyrVwtbZg5gBMjTezGAJN',
22
33
  'QmbLHAnMoJPWSCR5Zhtx6BHJX9KiKNN6tpvbUcqanj75Nb',
23
34
  'QmcZf59bWwK5XFi76CZX8cbJ4BhTzzA3gU1ZjYZcYW3dwt',
24
- 'QmaCpDMGvV2BGHeYERUEnRQAwe3N8SzbUtfsmvsqQLuvuJ',
25
- '12D3KooWPEDBmt7vm6FNNYuqaA4n2qMUZ6wPK5NcRc8t6KpqgRkV',
26
- '12D3KooWSHbugDEQeWm2LjtRRMpNgLu6oZ8zkX8XcTwYMAewVekP',
27
- '12D3KooWASoxFpwwy8JDdu4Tm57mhESsnbFPogam9VVmhR95FGXr',
28
- '12D3KooWHh98YpAkJsn3ULjMjK1n9QVkXmi8Sb3gTDMatHxCmDP5',
29
- '12D3KooWS79EhkPU7ESUwgG4vyHHzW9FDNZLoWVth9b5N5NSrvaj',
30
- '12D3KooWBbkCD5MpJhMc1mfPAVGEyVkQnyxPKGS7AHwDqQM2JUsk',
31
- '12D3KooWKLdecs31Zmo2pLBjR9HY2vWo3VwM4eBm21Czeucbe6FL',
32
- '12D3KooWBdF3g6vSJFRPoZQo7BNnkNzaWb59gpyaVzsgtNTVeu8H'
35
+ 'QmaCpDMGvV2BGHeYERUEnRQAwe3N8SzbUtfsmvsqQLuvuJ'
33
36
  ]
34
37
 
35
38
  export const CONFIG_KNOWN_BOOTSTRAP_HYBRID_IDS = [
@@ -39,4 +42,40 @@ export const CONFIG_KNOWN_BOOTSTRAP_HYBRID_IDS = [
39
42
  export const CONFIG_KNOWN_BOOTSTRAP_PEERS_IDS = CONFIG_KNOWN_BOOTSTRAP_PUBLIC_IDS.concat(CONFIG_KNOWN_BOOTSTRAP_HYBRID_IDS)
40
43
 
41
44
  export const CONFIG_KNOWN_BOOTSTRAP_PEERS_ADDRS = [
45
+ {
46
+ "Peers": [
47
+ {
48
+ "Addrs": [
49
+ "/dns6/sv15.bootstrap.libp2p.io/tcp/443/wss",
50
+ "/dns4/sv15.bootstrap.libp2p.io/tcp/443/wss"
51
+ ],
52
+ "ID": "QmNnooDu7bfjPFoTZYxMNLWUQJyrVwtbZg5gBMjTezGAJN",
53
+ "Schema": "peer"
54
+ }
55
+ ]
56
+ },
57
+ {
58
+ "Peers": [
59
+ {
60
+ "Addrs": [
61
+ "/dns4/am6.bootstrap.libp2p.io/tcp/443/wss",
62
+ "/dns6/am6.bootstrap.libp2p.io/tcp/443/wss"
63
+ ],
64
+ "ID": "QmbLHAnMoJPWSCR5Zhtx6BHJX9KiKNN6tpvbUcqanj75Nb",
65
+ "Schema": "peer"
66
+ }
67
+ ]
68
+ },
69
+ {
70
+ "Peers": [
71
+ {
72
+ "Addrs": [
73
+ "/dns6/sg1.bootstrap.libp2p.io/tcp/443/wss",
74
+ "/dns4/sg1.bootstrap.libp2p.io/tcp/443/wss"
75
+ ],
76
+ "ID": "QmcZf59bWwK5XFi76CZX8cbJ4BhTzzA3gU1ZjYZcYW3dwt",
77
+ "Schema": "peer"
78
+ }
79
+ ]
80
+ }
42
81
  ]
package/src/peer.js CHANGED
@@ -1,8 +1,5 @@
1
- /* eslint-disable import/export */
2
- /* eslint-disable complexity */
3
- /* eslint-disable @typescript-eslint/no-namespace */
4
- /* eslint-disable @typescript-eslint/no-unnecessary-boolean-literal-compare */
5
- /* eslint-disable @typescript-eslint/no-empty-interface */
1
+ //this code comes from https://github.com/libp2p/js-libp2p-pubsub-peer-discovery/blob/9d0da565f70e9b2403251c9d11dfc0b9b52babfa/src/peer.ts
2
+
6
3
  import { decodeMessage, encodeMessage, message } from 'protons-runtime';
7
4
  import { alloc as uint8ArrayAlloc } from 'uint8arrays/alloc';
8
5
  export var Peer;
package/src/webpeerjs.js CHANGED
@@ -20,6 +20,7 @@ import { createDelegatedRoutingV1HttpApiClient } from '@helia/delegated-routing-
20
20
  import { createLibp2p } from 'libp2p'
21
21
  import { IDBDatastore } from 'datastore-idb'
22
22
  import { webTransport } from '@libp2p/webtransport'
23
+ import { webSockets } from '@libp2p/websockets'
23
24
  import { noise } from '@chainsafe/libp2p-noise'
24
25
  import { yamux } from '@chainsafe/libp2p-yamux'
25
26
  import { pubsubPeerDiscovery } from '@libp2p/pubsub-peer-discovery'
@@ -152,7 +153,7 @@ class webpeerjs{
152
153
  const addr = connect.addr
153
154
 
154
155
  if(config.CONFIG_KNOWN_BOOTSTRAP_PEERS_IDS.includes(id)){
155
- if(!this.#connections.has(id)&&addr.includes('webtransport')){
156
+ if((!this.#connections.has(id) || (this.#connections.get(id).includes('/wss/')))&&addr.includes('webtransport')){
156
157
  await this.#dbstore.put(new Key(id), new TextEncoder().encode(addr))
157
158
  }
158
159
  }
@@ -449,6 +450,7 @@ class webpeerjs{
449
450
  //if this disconnected peer is known bootstrap redial it
450
451
  else if(this.#dialedKnownBootstrap.has(id)){
451
452
  const addr = this.#connections.get(id)
453
+ if(addr.includes('/wss/'))return
452
454
  let mddrs = []
453
455
  const addrs = multiaddr(addr)
454
456
  mddrs.push(addrs)
@@ -491,8 +493,29 @@ class webpeerjs{
491
493
  this.#ping()
492
494
  })
493
495
 
494
- this.#libp2p.addEventListener('peer:identify', (evt) => {
496
+ this.#libp2p.addEventListener('peer:identify', async (evt) => {
495
497
  //console.log('peer:identify '+evt.detail.peerId.toString(),evt.detail)
498
+
499
+ const id = evt.detail.peerId.toString()
500
+
501
+ if(config.CONFIG_KNOWN_BOOTSTRAP_PUBLIC_IDS.includes(id)){
502
+ const remoteAddr = evt.detail.connection.remoteAddr.toString()
503
+ if(remoteAddr.includes('/wss/')){
504
+ let addrs = []
505
+ let mddrs = []
506
+ for(const peer of evt.detail.listenAddrs){
507
+ if(!peer.toString().includes('webtransport'))continue
508
+ const addr = peer.toString()+'/p2p/'+id
509
+ const mddr = multiaddr(addr)
510
+ addrs.push(addr)
511
+ mddrs.push(mddr)
512
+ }
513
+ this.#dialedKnownBootstrap.set(id,addrs)
514
+ await this.#libp2p.hangUp(peerIdFromString(id))
515
+ this.#dialMultiaddress(mddrs)
516
+ }
517
+ }
518
+
496
519
  if(evt.detail.protocols.includes(config.CONFIG_PROTOCOL)){
497
520
  //console.log('peer:identify '+evt.detail.peerId.toString(),evt)
498
521
 
@@ -877,37 +900,39 @@ class webpeerjs{
877
900
  }
878
901
  }
879
902
 
880
- #findHybridPeer(){
881
- setTimeout(async()=>{
882
- for(const target of config.CONFIG_KNOWN_BOOTSTRAP_HYBRID_IDS){
883
- if(!this.#isConnected(target) && !this.#connections.has(target) && this.#isDialEnabled ){
884
- //console.log('findPeer',target)
885
- const peerId = peerIdFromString(target)
886
- //const peerInfo = await this.#libp2p.services.aminoDHT.findPeer(peerId)
887
-
888
- //console.info(peerInfo)
889
- for await (const event of this.#libp2p.services.aminoDHT.findPeer(peerId)){
890
- //console.info('findPeer',event)
891
- if (event.name === 'FINAL_PEER'){
892
- //console.log(event.peer.id.toString(),event.peer.multiaddrs.toString())
893
- let mddrs = []
894
- let addrs = []
895
- const id = event.peer.id.toString()
896
- for(const mddr of event.peer.multiaddrs){
897
- const peeraddr = mddr.toString()+'/p2p/'+id
898
- const peermddr = multiaddr(peeraddr)
899
- addrs.push(peeraddr)
900
- mddrs.push(peermddr)
901
- }
902
- this.#dialedKnownBootstrap.set(id,addrs)
903
- if(!this.#isConnected(id)){
904
- this.#dialMultiaddress(mddrs)
905
- }
903
+ async #findHybridPeer(){
904
+
905
+ if(!navigator.onLine)return
906
+ if(!this.#isDialEnabled)return
907
+
908
+ for(const target of config.CONFIG_KNOWN_BOOTSTRAP_HYBRID_IDS){
909
+ if(!this.#isConnected(target) && !this.#connections.has(target)){
910
+ //console.log('findPeer',target)
911
+ const peerId = peerIdFromString(target)
912
+ //const peerInfo = await this.#libp2p.services.aminoDHT.findPeer(peerId)
913
+
914
+ //console.info(peerInfo)
915
+ for await (const event of this.#libp2p.services.aminoDHT.findPeer(peerId)){
916
+ //console.info('findPeer',event)
917
+ if (event.name === 'FINAL_PEER'){
918
+ //console.log(event.peer.id.toString(),event.peer.multiaddrs.toString())
919
+ let mddrs = []
920
+ let addrs = []
921
+ const id = event.peer.id.toString()
922
+ for(const mddr of event.peer.multiaddrs){
923
+ const peeraddr = mddr.toString()+'/p2p/'+id
924
+ const peermddr = multiaddr(peeraddr)
925
+ addrs.push(peeraddr)
926
+ mddrs.push(peermddr)
927
+ }
928
+ this.#dialedKnownBootstrap.set(id,addrs)
929
+ if(!this.#isConnected(id)){
930
+ this.#dialMultiaddress(mddrs)
906
931
  }
907
932
  }
908
933
  }
909
934
  }
910
- },60e3)
935
+ }
911
936
  }
912
937
 
913
938
 
@@ -1251,69 +1276,47 @@ class webpeerjs{
1251
1276
  if(peers == 0){
1252
1277
  this.#dialKnownPeers()
1253
1278
  }
1254
- },60*1000)
1279
+ },120*1000)
1255
1280
  }
1256
1281
 
1257
1282
 
1258
1283
  //dial to all known bootstrap peers and DNS
1259
1284
  #dialKnownPeers(){
1260
- //this.#dialKnownBootstrap()
1261
1285
  setTimeout(()=>{
1262
1286
  this.#dialSavedKnownID()
1263
- this.#findHybridPeer()
1264
1287
  setTimeout(()=>{this.#dialUpdateSavedKnownID()},50000)
1288
+ setTimeout(()=>{this.#findHybridPeer()},60000)
1265
1289
  setTimeout(()=>{
1266
1290
  const peers = this.#libp2p.getPeers().length
1267
1291
  if(peers == 0){
1268
1292
  this.#dialKnownID()
1269
- this.#findHybridPeer()
1293
+ setTimeout(()=>{this.#findHybridPeer()},60000)
1270
1294
  setTimeout(()=>{
1271
1295
  const peers = this.#libp2p.getPeers().length
1272
1296
  if(peers == 0){
1273
- //currently not needed
1274
- //this.#dialKnownDNS()
1297
+ this.#dialKnownBootstrap()
1298
+ setTimeout(()=>{this.#findHybridPeer()},15000)
1275
1299
  setTimeout(()=>{
1276
1300
  const peers = this.#libp2p.getPeers().length
1277
1301
  if(peers == 0){
1278
- //currently not needed
1279
- //this.#dialKnownDNSonly()
1302
+ this.#dialKnownDNS()
1303
+ setTimeout(()=>{this.#findHybridPeer()},15000)
1304
+ setTimeout(()=>{
1305
+ const peers = this.#libp2p.getPeers().length
1306
+ if(peers == 0){
1307
+ this.#dialKnownDNSonly()
1308
+ setTimeout(()=>{this.#findHybridPeer()},15000)
1309
+ }
1310
+ },config.CONFIG_TIMEOUT_DIAL_KNOWN_PEERS)
1280
1311
  }
1281
- },15000)
1312
+ },config.CONFIG_TIMEOUT_DIAL_KNOWN_PEERS)
1282
1313
  }
1283
- },15000)
1314
+ },config.CONFIG_TIMEOUT_DIAL_KNOWN_PEERS)
1284
1315
  }
1285
- },15000)
1316
+ },config.CONFIG_TIMEOUT_DIAL_KNOWN_PEERS)
1286
1317
  },5000)
1287
1318
  }
1288
1319
 
1289
-
1290
- //dial based on known bootsrap peers address
1291
- #dialKnownBootstrap(){
1292
-
1293
- if(!navigator.onLine)return
1294
- if(!this.#isDialEnabled)return
1295
-
1296
- const bootstrap = config.CONFIG_KNOWN_BOOTSTRAP_PEERS_ADDRS
1297
- for(const peer of bootstrap){
1298
- const address = peer.Peers[0].Addrs
1299
- const id = peer.Peers[0].ID
1300
- let mddrs = []
1301
- let addrs = []
1302
- for(const addr of address){
1303
- const peeraddr = addr+'/p2p/'+id
1304
- const peermddr = multiaddr(peeraddr)
1305
- addrs.push(peeraddr)
1306
- mddrs.push(peermddr)
1307
- }
1308
-
1309
- this.#dialedKnownBootstrap.set(id,addrs)
1310
- if(!this.#isConnected(id)){
1311
- this.#dialMultiaddress(mddrs)
1312
- }
1313
-
1314
- }
1315
- }
1316
-
1317
1320
  async #dialSavedKnownID(){
1318
1321
 
1319
1322
  if(!navigator.onLine)return
@@ -1434,10 +1437,43 @@ class webpeerjs{
1434
1437
  }
1435
1438
  }
1436
1439
  }
1437
-
1440
+
1441
+
1442
+ //dial based on known bootsrap peers address using Websocket expected
1443
+ #dialKnownBootstrap(){
1444
+
1445
+ if(!navigator.onLine)return
1446
+ if(!this.#isDialEnabled)return
1447
+
1448
+ const bootstrap = config.CONFIG_KNOWN_BOOTSTRAP_PEERS_ADDRS
1449
+ for(const peer of bootstrap){
1450
+ const address = peer.Peers[0].Addrs
1451
+ const id = peer.Peers[0].ID
1452
+ let mddrs = []
1453
+ let addrs = []
1454
+ for(const addr of address){
1455
+ if(!addr.includes('wss'))continue
1456
+ const peeraddr = addr+'/p2p/'+id
1457
+ const peermddr = multiaddr(peeraddr)
1458
+ addrs.push(peeraddr)
1459
+ mddrs.push(peermddr)
1460
+ }
1461
+
1462
+ this.#dialedKnownBootstrap.set(id,addrs)
1463
+ this.#isDialWebsocket = true
1464
+ if(!this.#isConnected(id)){
1465
+ this.#dialMultiaddress(mddrs)
1466
+ }
1467
+
1468
+ }
1469
+ }
1438
1470
 
1439
1471
  //dial based on known bootstrap DNS
1440
- /*async #dialKnownDNS(){
1472
+ async #dialKnownDNS(){
1473
+
1474
+ if(!navigator.onLine)return
1475
+ if(!this.#isDialEnabled)return
1476
+
1441
1477
  const dnsresolver = config.CONFIG_DNS_RESOLVER
1442
1478
  const bootstrapdns = config.CONFIG_KNOWN_BOOTSTRAP_DNS
1443
1479
  const response = await fetch(dnsresolver+'?name='+bootstrapdns+'&type=txt')
@@ -1466,16 +1502,21 @@ class webpeerjs{
1466
1502
  }
1467
1503
 
1468
1504
  this.#dialedKnownBootstrap.set(id,addrs)
1505
+ this.#isDialWebsocket = true
1469
1506
  if(!this.#isConnected(id)){
1470
1507
  this.#dialMultiaddress(mddrs)
1471
1508
  }
1472
1509
  }
1473
1510
 
1474
- }*/
1511
+ }
1475
1512
 
1476
1513
 
1477
1514
  //dial based on known bootstrap DNS using DNS resolver only
1478
- /*async #dialKnownDNSonly(){
1515
+ async #dialKnownDNSonly(){
1516
+
1517
+ if(!navigator.onLine)return
1518
+ if(!this.#isDialEnabled)return
1519
+
1479
1520
  const dnsresolver = config.CONFIG_DNS_RESOLVER
1480
1521
  const bootstrapdns = config.CONFIG_KNOWN_BOOTSTRAP_DNS
1481
1522
  const response = await fetch(dnsresolver+'?name='+bootstrapdns+'&type=txt')
@@ -1488,11 +1529,11 @@ class webpeerjs{
1488
1529
  const dnsaddr = '_dnsaddr.'+arr[2]
1489
1530
  this.#dialDNSWebsocketWebtransport(id,dnsaddr)
1490
1531
  }
1491
- }*/
1532
+ }
1492
1533
 
1493
1534
 
1494
1535
  //dial DNS with webtransport and websocket
1495
- /*async #dialDNSWebsocketWebtransport(id,dnsaddr){
1536
+ async #dialDNSWebsocketWebtransport(id,dnsaddr){
1496
1537
  const dnsresolver = config.CONFIG_DNS_RESOLVER
1497
1538
  const response = await fetch(dnsresolver+'?name='+dnsaddr+'&type=txt')
1498
1539
  const json = await response.json()
@@ -1516,41 +1557,34 @@ class webpeerjs{
1516
1557
  this.#dialMultiaddress(mddrs)
1517
1558
  this.#dialWebsocket(mddrs)
1518
1559
  }
1519
- }*/
1560
+ }
1520
1561
 
1521
1562
 
1522
1563
  //dial only webtransport multiaddrs
1523
1564
  async #dialWebtransport(multiaddrs){
1524
1565
  const webTransportMadrs = multiaddrs.filter((maddr) => maddr.protoNames().includes('webtransport')&&maddr.protoNames().includes('certhash'))
1525
- for (const addr of webTransportMadrs) {
1566
+ for (const mddr of webTransportMadrs) {
1526
1567
  try {
1527
- //console.log(`attempting to dial webtransport multiaddr: %o`, addr.toString())
1528
- await this.#libp2p.dial(addr)
1568
+ //console.log(`attempting to dial webtransport multiaddr: %o`, mddr.toString())
1569
+ await this.#libp2p.dial(mddr)
1529
1570
  return // if we succeed dialing the peer, no need to try another address
1530
1571
  } catch (error) {
1531
- //console.log(`failed to dial webtransport multiaddr: %o`, addr.toString())
1572
+ //console.log(`failed to dial webtransport multiaddr: %o`, mddr.toString())
1532
1573
  mkDebug(error)
1533
1574
  }
1534
1575
  }
1535
1576
  }
1536
-
1537
- //dial only webtransport multiaddrs
1538
- /*#dialWebtransport1(multiaddrs){
1539
- const webTransportMadrs = multiaddrs.filter((maddr) => maddr.protoNames().includes('webtransport')&&maddr.protoNames().includes('certhash'))
1540
- if(webTransportMadrs.length == 0)return
1541
- this.#libp2p.dial(webTransportMadrs).then((data)=>{console.warn(data)},(data)=>{console.warn(data)})
1542
- }*/
1543
1577
 
1544
1578
  //dial only websocket multiaddrs
1545
1579
  async #dialWebsocket(multiaddrs){
1546
1580
  const webSocketMadrs = multiaddrs.filter((maddr) => maddr.protoNames().includes('wss'))
1547
- for (const addr of webSocketMadrs) {
1581
+ for (const mddr of webSocketMadrs) {
1548
1582
  try {
1549
- //console.log(`attempting to dial websocket multiaddr: %o`, addr)
1550
- await this.#libp2p.dial(addr)
1583
+ //console.log(`attempting to dial websocket multiaddr: %o`, mddr)
1584
+ await this.#libp2p.dial(mddr)
1551
1585
  return // if we succeed dialing the peer, no need to try another address
1552
1586
  } catch (error) {
1553
- //console.log(`failed to dial websocket multiaddr: %o`, addr)
1587
+ //console.log(`failed to dial websocket multiaddr: %o`, mddr)
1554
1588
  mkDebug(error)
1555
1589
  }
1556
1590
  }
@@ -1591,7 +1625,8 @@ class webpeerjs{
1591
1625
  ],
1592
1626
  },
1593
1627
  transports:[
1594
- webTransport(),
1628
+ webTransport(),
1629
+ webSockets(),
1595
1630
  circuitRelayTransport({
1596
1631
  discoverRelays: config.CONFIG_DISCOVER_RELAYS,
1597
1632
  reservationConcurrency: 1,