diff --git a/doc/CONFIGURATION.md b/doc/CONFIGURATION.md index 527ee35733..4105551796 100644 --- a/doc/CONFIGURATION.md +++ b/doc/CONFIGURATION.md @@ -651,6 +651,35 @@ const node = await Libp2p.create({ }) ``` +During Libp2p startup, transport listeners will be created for the configured listen multiaddrs. Some transports support custom listener options and you can set them using the `listenerOptions` in the transport configuration. For example, [libp2p-webrtc-star](https://github.com/libp2p/js-libp2p-webrtc-star) transport listener supports the configuration of its underlying [simple-peer](https://github.com/feross/simple-peer) ice server(STUN/TURN) config as follows: + +```js +const transportKey = WebRTCStar.prototype[Symbol.toStringTag] +const node = await Libp2p.create({ + modules: { + transport: [WebRTCStar], + streamMuxer: [MPLEX], + connEncryption: [NOISE] + }, + addresses: { + listen: ['/dns4/your-wrtc-star.pub/tcp/443/wss/p2p-webrtc-star'] // your webrtc dns multiaddr + }, + config: { + transport: { + [transportKey]: { + listenerOptions: { + config: { + iceServers: [ + {"urls": ["turn:YOUR.TURN.SERVER:3478"], "username": "YOUR.USER", "credential": "YOUR.PASSWORD"}, + {"urls": ["stun:YOUR.STUN.SERVER:3478"], "username": "", "credential": ""}] + } + } + } + } + } +}) +``` + ## Configuration examples As libp2p is designed to be a modular networking library, its usage will vary based on individual project needs. We've included links to some existing project configurations for your reference, in case you wish to replicate their configuration: diff --git a/src/transport-manager.js b/src/transport-manager.js index e18841bf02..f9cf8629c5 100644 --- a/src/transport-manager.js +++ b/src/transport-manager.js @@ -20,6 +20,7 @@ class TransportManager { this.upgrader = upgrader this._transports = new Map() this._listeners = new Map() + this._listenerOptions = new Map() this.faultTolerance = faultTolerance } @@ -47,6 +48,7 @@ class TransportManager { }) this._transports.set(key, transport) + this._listenerOptions.set(key, transportOptions.listenerOptions || {}) if (!this._listeners.has(key)) { this._listeners.set(key, []) } @@ -154,7 +156,7 @@ class TransportManager { // For each supported multiaddr, create a listener for (const addr of supportedAddrs) { log('creating listener for %s on %s', key, addr) - const listener = transport.createListener({}, this.onConnection) + const listener = transport.createListener(this._listenerOptions.get(key), this.onConnection) this._listeners.get(key).push(listener) // We need to attempt to listen on everything diff --git a/test/transports/transport-manager.node.js b/test/transports/transport-manager.node.js index 1036230acb..cd1e6fb8b5 100644 --- a/test/transports/transport-manager.node.js +++ b/test/transports/transport-manager.node.js @@ -10,6 +10,7 @@ const TransportManager = require('../../src/transport-manager') const Transport = require('libp2p-tcp') const multiaddr = require('multiaddr') const mockUpgrader = require('../utils/mockUpgrader') +const sinon = require('sinon') const addrs = [ multiaddr('/ip4/127.0.0.1/tcp/0'), multiaddr('/ip4/127.0.0.1/tcp/0') @@ -40,7 +41,9 @@ describe('Transport Manager (TCP)', () => { }) it('should be able to listen', async () => { - tm.add(Transport.prototype[Symbol.toStringTag], Transport) + tm.add(Transport.prototype[Symbol.toStringTag], Transport, { listenerOptions: { listen: 'carefully' } }) + const transport = tm._transports.get(Transport.prototype[Symbol.toStringTag]) + const spyListener = sinon.spy(transport, 'createListener') await tm.listen() expect(tm._listeners).to.have.key(Transport.prototype[Symbol.toStringTag]) expect(tm._listeners.get(Transport.prototype[Symbol.toStringTag])).to.have.length(addrs.length) @@ -48,6 +51,7 @@ describe('Transport Manager (TCP)', () => { expect(tm.getAddrs().length).to.equal(addrs.length) await tm.close() expect(tm._listeners.get(Transport.prototype[Symbol.toStringTag])).to.have.length(0) + expect(spyListener.firstCall.firstArg).to.deep.equal({ listen: 'carefully' }) }) it('should be able to dial', async () => { diff --git a/test/transports/transport-manager.spec.js b/test/transports/transport-manager.spec.js index b32b280725..f91de4afde 100644 --- a/test/transports/transport-manager.spec.js +++ b/test/transports/transport-manager.spec.js @@ -125,7 +125,10 @@ describe('libp2p.transportManager', () => { const spy = sinon.spy() const key = spy.prototype[Symbol.toStringTag] = 'TransportSpy' const customOptions = { - another: 'value' + another: 'value', + listenerOptions: { + listen: 'carefully' + } } libp2p = new Libp2p({ peerId, @@ -143,6 +146,7 @@ describe('libp2p.transportManager', () => { expect(libp2p.transportManager).to.exist() // Our transport and circuit relay expect(libp2p.transportManager._transports.size).to.equal(2) + expect(libp2p.transportManager._listenerOptions.size).to.equal(2) expect(spy).to.have.property('callCount', 1) expect(spy.getCall(0)).to.have.deep.property('args', [{ ...customOptions,