Peerjs: Run peerjs client in a node.js application?

Created on 6 Nov 2013  ·  65Comments  ·  Source: peers/peerjs

Would it possible run a peer.js client in a node.js application instead of the browser?

I'm creating a peer-to-peer network consisting of (programmatic) peers living both in browsers and in node.js applications. They have to send data to each other, no video/audio. WebRTC would be a great solution to resolve the routing and communication between the peers without the need for a centralistic client/server structure. But WebRTC seems to be supported only in the browser.

See also this question: http://stackoverflow.com/questions/18872712/node-js-webrtc-client

Most helpful comment

Overview
Hi, I see this is old, but you or anyone might need this. I am working on my thesis and I have made some steps forward. I have tried many things and simplepeer has no signalling implemented. Sending messages over datachannel (nodejs peerjs webrtc) - over network on Raspberry Pi 2 (ARM, Raspbian Jessie, but should work everywhere) using deployed signalling server (peerserver) is now working. The other client is a firefox browser in windows enviroment. I wouldn`t have made it without your discussion here, so I am giving back to the community.

Key things about what (not) to do:
-dont use selenium, its not fast enough, at least for my application
-xvfb didnt work out for me, well it did
-you must not require peerjs module
-on Raspberry at least - use electron-webrtc, as wrtc isn`t available for arm anyway
-dont use serialization

Having to do everything by yourself is hard, so here is the code:
window = global
window.BlobBuilder = require("BlobBuilder")
location = {protocol: 'http'}

BinaryPack = require("binary-pack")
XMLHttpRequest = require("xmlhttprequest").XMLHttpRequest;
var wrtc = require('electron-webrtc')()
//var Peer = require('peerjs')

RTCPeerConnection = wrtc.RTCPeerConnection;
RTCSessionDescription = wrtc.RTCSessionDescription;
RTCIceCandidate = wrtc.RTCIceCandidate;

WebSocket = require('ws')
require('/home/pi/node_modules/peerjs/lib/exports.js');

var peer = new Peer(
...
})

var conn=peer.connect('id')
conn.serialization='none'
conn.send('hello from nodejs!')

That`s it, regards, JP

All 65 comments

I found an initiative by @helloIAmPau to create a node.js implementation of WebRTC: https://github.com/helloIAmPau/node-rtc/. Maybe it is possible to bundle forces?

Hey Jos,

I'll keep an eye on it. When there is a reliable webrtc node client it
should be trivial to port peerjs over.

On Wed, Nov 6, 2013 at 6:46 AM, Jos de Jong [email protected]:

I found an initiative by @helloIAmPau https://github.com/helloIAmPau to
create a node.js implementation of WebRTC:
https://github.com/helloIAmPau/node-rtc/. Maybe it is possible to bundle
forces?


Reply to this email directly or view it on GitHubhttps://github.com/peers/peerjs/issues/103#issuecomment-27878686
.

510-691-3951
http://ericzhang.com

See https://github.com/modeswitch/node-webrtc aswell. I think node-rtc is being replaced by it.

Thanks Eric, that would be great.

This would also enable a node.js application working as an MCU to control video/audio streams for a group of peers (conference call), in a star architecture as explained by Justin Uberti on the last Google I/O on WebRTC (from 23:19). Node.js is good at dealing with streams so that could be a great fit.

@ericz what is the reason to close this issue? Support for node.js would be really awesome and powerful.

Hey josdejong,

I closed it because there's no action item but I'll reopen it so we can keep tabs on the feature :)

ok thanks. Feel free to adjust the title to something like "node.js support" and give the issue a proper label...

:+1: This would be a pretty helpful feature.

:+1: Upvoting for this too.

:+1: much needed

+1

I managed to mock some objects and get peerjs running on node.js

window={};
window.BlobBuilder = require("BlobBuilder");
location={};
location.protocol="http";

BinaryPack = require("binary-pack");
XMLHttpRequest = require("xmlhttprequest").XMLHttpRequest;

var wrtc = require("wrtc");
RTCPeerConnection = wrtc.RTCPeerConnection;
RTCSessionDescription = wrtc.RTCSessionDescription;
RTCIceCandidate = wrtc.RTCIceCandidate;

WebSocket = require('ws');
var peerClient =require("./peer.js");

I managed to get peerjs setting up connections and server get connections. However, when I try to send data I get follow error

[Error: Connection is not open. You should listen for the open event before sending messages.]

Here is the complete gist

https://gist.github.com/piyushranjan/1204bc579b7c1f5a3e84

And these npm packages must be installed

npm install BlobBuilder
npm install binary-pack
npm install ws
npm install xmlhttprequest
npm install wrtc

Ah, this is really awesome! Will take a look :).

Michelle

On Tue, May 6, 2014 at 7:37 AM, Piyush Ranjan [email protected]:

I managed to mock some objects and get peerjs running on node.js

window={};
window.BlobBuilder = require("BlobBuilder");
location={};
location.protocol="http";

BinaryPack = require("binary-pack");
XMLHttpRequest = require("xmlhttprequest").XMLHttpRequest;

var wrtc = require("wrtc");
RTCPeerConnection = wrtc.RTCPeerConnection;
RTCSessionDescription = wrtc.RTCSessionDescription;
RTCIceCandidate = wrtc.RTCIceCandidate;

WebSocket = require('ws');
var peerClient =require("./peer.js");

I managed to get peerjs setting up connections and server get connections.
However, when I try to send data I get follow error

[Error: Connection is not open. You should listen for the open event
before sending messages.]

Here is the complete gist

https://gist.github.com/piyushranjan/1204bc579b7c1f5a3e84

And these npm packages must be installed

npm install BlobBuilder
npm install binary-pack
npm install ws
npm install xmlhttprequest
npm install wrtc


Reply to this email directly or view it on GitHubhttps://github.com/peers/peerjs/issues/103#issuecomment-42292282
.

@michelle any luck with this already? I tried, and opening a connection seems to work but sent messages are never received.

:+1: for this feature

:+1: for this feature

:+1:

:+1::+1::+1:

I was wondering what the status of this was? It would be awesome if this was supported?

There is a node module for peerjs, but I think it doesn't work yet. When I require it, I get window is not defined, which is a fair objection.
https://www.npmjs.org/package/peerjs#readme

So I am curious: is there something going on? Would be so awesome to have it! ;)

This node module is for the browser code :).

Michelle

On Thu, Oct 23, 2014 at 11:37 AM, Lixissimus [email protected]
wrote:

There is a node module for peerjs, but I think it doesn't work yet. When I
require it, I get window is not defined, which is a fair objection.
https://www.npmjs.org/package/peerjs#readme

So I am curious: is there something going on? Would be so awesome to have
it! ;)


Reply to this email directly or view it on GitHub
https://github.com/peers/peerjs/issues/103#issuecomment-60287567.

So what is it supposed to do?

I don't know if I am just confused about node, but seems strange to have an npm module for peerjs, if the peerjs module itself can only be used from the browser?

Sorry, this was before we began publishing the library on bower.

Michelle

On Thu, Oct 23, 2014 at 11:51 AM, Alan Chusuei [email protected]
wrote:

I don't know if I am just confused about node, but seems strange to have
an npm module for peerjs, if the peerjs module itself can only be used from
the browser?


Reply to this email directly or view it on GitHub
https://github.com/peers/peerjs/issues/103#issuecomment-60289790.

@AChusuei I don't see any problem in having browser specific libraries in npm, or isomorphic libraries. For my full stack JS web applications I like to have to deal with npm only, rather than having to fetch half of the Iibraries from npm and the other half from bower.

@michelle I really hope peerjs will get support for a node.js client!!

@josdejong, I guess you could do it that way. I am still new to the node world, open to doing things differently!

:+1:

Until this issue is resolved, there might be possible workarounds with headless browsers. I haven't tested them by myself:

i'll give the second one a try.

:+1:

+2^56 for the feature!

:+1:

:+1:

:+1:

+1

The hack posted by @piyushranjan doesn't seem to work with the current stable version, as it doesn't export anything globally (and all the modules are in one file).

The workaround for this seems to be to use the non "compiled"/concatenated version.

Thus, clone the repository, and then do something like this:

window = global;
location = {protocol: 'http'};

XMLHttpRequest = require("xmlhttprequest").XMLHttpRequest;

var wrtc = require("wrtc");
RTCPeerConnection = wrtc.RTCPeerConnection;
RTCSessionDescription = wrtc.RTCSessionDescription;
RTCIceCandidate = wrtc.RTCIceCandidate;

WebSocket = require('ws');

require('./peerjs/lib/exports.js');

var peer = new Peer({
  // snip...
});

Pay special attention to the require line near the bottom, which handles loading all the separate parts for you, into the global/window object.

Still a nasty hack, but it seems to work, at least for very basic tests.

Note: Same caveats apply, you still need to install some packages first:

npm install BlobBuilder binary-pack ws xmlhttprequest wrtc

@lewiseason Did you actually got a connection up and running and be able to send some data for example?

I didn't succeed in this so far. It looks like I can open a connection, but there is no data channel created.

This is what I tried:

  1. Installation

sudo apt-get install libnss3-dev libexpat1-dev npm install peerjs BlobBuilder binary-pack ws xmlhttprequest wrtc

  1. Create an html file peer1.html connecting a client peer with id 'peer1':

``` html



peer1






```

  1. Create a node.js script peer3.js:

``` js
window = global;
window.BlobBuilder = require("BlobBuilder");
location = {protocol: 'http'};

BinaryPack = require("binary-pack");
XMLHttpRequest = require("xmlhttprequest").XMLHttpRequest;

var wrtc = require("wrtc");
RTCPeerConnection = wrtc.RTCPeerConnection;
RTCSessionDescription = wrtc.RTCSessionDescription;
RTCIceCandidate = wrtc.RTCIceCandidate;

WebSocket = require('ws');

require('peerjs/lib/exports.js');

var peer = new Peer('peer3', {key: 'lwjd5qra8257b9', debug: true});

peer.on('open', function () {
console.log('peer open');
var conn = peer.connect('peer1');

 conn.on('data', function(data) {
   console.log('Received', data);
 });

 conn.on('error', function (err) {
   console.log('Error', err);
 });

 conn.on('open', function () {
   console.log('connection open');
   conn.send('Hello from ' + peer.id + '!');
 });

});
```

  1. Open the file peer1.html in your browser
  2. Run the node.js script peer3.js

Looking at the debug output, it looks like peer3 is succesfully connected to peer1, but it does not establish a data channel: peer1 outputs "new connection to peer3", but there are no messages received.

I'm afraid I didn't get very far with testing it - seemed a bit to Frankenstein to use in production, so I ended up leaving it. Sorry :(

:+1:

:+1:

Any update on this?

@josdejong the issue lies with the signalling data. It seems no STUN data is being attached to the offer/answer. Without this data no actual connection can be made. The following does make a connection between browser and node but without peerjs signaling.

https://github.com/cjb/serverless-webrtc

+1

+1

Anyone wanna open a bounty?

As this has been open for more than two years: Is there any (other) known package that works P2P in browser & node?

I haven't had time to check it out, but https://github.com/feross/simple-peer says it works in both node.js and the browser.

Is this what you're looking for? https://github.com/socketio/socket.io-p2p

from the readme:

"This module provides an easy and reliable way to setup a WebRTC connection between peers and communicate using events (the socket.io-protocol).

Socket.IO is used to transport signalling data and as a fallback for clients where WebRTC PeerConnection is not supported."

As far as I am concerned, it doesn't work on Node. That's why I ran into this thread.

Hmm. Could you be more specific? I'm using it right now, using a node server to connect peers which then establish webRTC connections to each other and/or the node server's machine.

using a node server to connect peers which then establish webRTC connections to each other

So, you're _not_ running it as a client. You're running it on a server that connects _other_ clients (which you don't mention to be node apps - if they are, I'd be interested how you set them up).
This thread is about using peerjs (or potentially anything else) as a peer (client) in a node application.

webRTC connections to each other and/or the node server's machine

The second part of that seems like exactly what is being discussing here. Can anyone else confirm this?

No, the issue is using NodeJS as a WebRTC client. Ie. connect from a NodeJS instance that is not necessarily the server.

Oh, apologies. SimplePeer will do that. But it requires the server platform to have certain webrtc capabilities installed. The 'wrtc' module provides this on most machines. Notably _not_ on a raspberry pi right now, in case that matters to you (it does to me!)

snippet from their readme.md:

in node

To use this library in node, pass in opts.wrtc as a parameter:

var SimplePeer = require('simple-peer')
var wrtc = require('wrtc')

var peer1 = new SimplePeer({ initiator: true, wrtc: wrtc })
var peer2 = new SimplePeer({ wrtc: wrtc })

+1 this would be a nice feature

Check out electron-webrtc, or webrtc-native. I use electron-webrtc for my node.js instance to connect with browsers (using the datachannel specifically)

Overview
Hi, I see this is old, but you or anyone might need this. I am working on my thesis and I have made some steps forward. I have tried many things and simplepeer has no signalling implemented. Sending messages over datachannel (nodejs peerjs webrtc) - over network on Raspberry Pi 2 (ARM, Raspbian Jessie, but should work everywhere) using deployed signalling server (peerserver) is now working. The other client is a firefox browser in windows enviroment. I wouldn`t have made it without your discussion here, so I am giving back to the community.

Key things about what (not) to do:
-dont use selenium, its not fast enough, at least for my application
-xvfb didnt work out for me, well it did
-you must not require peerjs module
-on Raspberry at least - use electron-webrtc, as wrtc isn`t available for arm anyway
-dont use serialization

Having to do everything by yourself is hard, so here is the code:
window = global
window.BlobBuilder = require("BlobBuilder")
location = {protocol: 'http'}

BinaryPack = require("binary-pack")
XMLHttpRequest = require("xmlhttprequest").XMLHttpRequest;
var wrtc = require('electron-webrtc')()
//var Peer = require('peerjs')

RTCPeerConnection = wrtc.RTCPeerConnection;
RTCSessionDescription = wrtc.RTCSessionDescription;
RTCIceCandidate = wrtc.RTCIceCandidate;

WebSocket = require('ws')
require('/home/pi/node_modules/peerjs/lib/exports.js');

var peer = new Peer(
...
})

var conn=peer.connect('id')
conn.serialization='none'
conn.send('hello from nodejs!')

That`s it, regards, JP

Hi @jeryfast , thanks for your solutions, I was looking for something like that 👍

I test it on a mac (not on the raspberry yet) and was getting the error "Failed to set the 'binary Type' property on 'RTCDataChannel': Blob support not implemented yet"

After some search, found that on file utils, on path node_modules/peerjs/lib around line 116:

try {
        dc.binaryType = 'blob';
        binaryBlob = true;
      } catch (e) {
      }

that is causing the error and the app to crash.

If the code is commented the app works and it behaves as a browser client, just beautiful. But is a dirty hack, so I was looking a way to "configure" or do something that don't be change code from the lib, but until now I don't found any.

The challenge resides in when that piece of code is executed, that is on the module Load process, when the require of the exports is done:

require('./node_modules/peerjs/lib/exports.js');

Any one has and ideia or suggestion on how to correct this?

Regards

Nice, if you use 'none' serialization, it works also, without changing anythings in a library. Regards

Hi again @jeryfast it works on the Raspberry as you said. The issue on my last post is related with to OS X.

Well the thing is great work 👍

No lets start the fun 💃

Hello
I am getting this error.
```
global.postMessage(messageName, '*');
^

TypeError: global.postMessage is not a function
at Object.setZeroTimeoutPostMessage [as setZeroTimeout] (

@crosogf, that error looks to me like a symptom of a larger problem. It appears that the only place postMessage is used is in error-handling code. My guess would be that it has something to do with binary blob support detection in lib/util.js (the code @nuno-nlfsoftware says to comment out). I noticed that there are two places that code is present, in dist/peer.js or dist/peer.min.js, and in lib/util.js. For me, only modifications to the latter were effectual (due to @jeryfast's hack of requiring lib/exports.js).

I'm just gonna leave this here https://www.npmjs.com/package/peerjs-nodejs

Also, the connection serialization doesn't have to be set to none. You can use any other option besides binary, you just need to set it since binary is the default. I set it to json which works just fine.

I'm just gonna leave this here https://www.npmjs.com/package/peerjs-nodejs

Thanks, I think it should be a part of PeerJS.

here is my code after test jeryfast & peerjs-nodejs

const peerJs = require('peerjs-nodejs');
const peer = peerJs("myPeerId", {
host: '192.168.137.231',
port: 9000,
pingInterval: 5000,
path: '/myapp',
debug: 3, 
iceTransportPolicy: 'relay',
config: {
'iceServers': [
    { urls: "stun:stun.l.google.com:19302" },
    {
        urls: "turn:34.192.149.24:5678?transport=udp",
        username: "USER", credential: "PASS"
    }
]
}
});

let conn = peer.connect('myPeerJS', {
    reliable: true
});


setTimeout(()=>{
 // NOT JSON
 // conn.serialization='none';
 // conn.send('hello from nodejs!');  

 // JSON WAY
 conn.serialization = 'json';
 conn.send({ value: 'hello from nodejs!' });

}, 3000);

setTimeout(()=>{
  conn.close();
  console.log("CONN CLOSE");
  process.exit();
}, 10000);

Hello, I'm getting this error, as soon as I create a Peer instance (using peerjs-nodejs) on the NodeJS server. I'm not even creating a connection to a remote Peer at the moment. Does somebody has solved it?

server.js

const Peer = require('peerjs-nodejs')

...

this.peer = Peer('webRTC-webinar-plugin', {
      host: '/',
      path: 'peer-js',
      port: (useHTTPS) ? 8443 : 8080,
      secure: (useHTTPS) ? true : false
})
/Users/federico/Documents/webRTC-webinar-plugin/node_modules/peerjs-nodejs/node_modules/peerjs/lib/util.js:234

      global.postMessage(messageName, '*');
             ^
TypeError: global.postMessage is not a function
    at Object.setZeroTimeoutPostMessage [as setZeroTimeout] (/Users/federico/Documents/webRTC-webinar-plugin/node_modules/peerjs-nodejs/node_modules/peerjs/lib/util.js:234:14)
    at Peer.disconnect (/Users/federico/Documents/webRTC-webinar-plugin/node_modules/peerjs-nodejs/node_modules/peerjs/lib/peer.js:420:8)
    at Socket.<anonymous> (/Users/federico/Documents/webRTC-webinar-plugin/node_modules/peerjs-nodejs/node_modules/peerjs/lib/peer.js:120:12)
    at Socket.emit (/Users/federico/Documents/webRTC-webinar-plugin/node_modules/peerjs-nodejs/node_modules/eventemitter3/index.js:71:35)
    at exports.XMLHttpRequest._http.onerror (/Users/federico/Documents/webRTC-webinar-plugin/node_modules/peerjs-nodejs/node_modules/peerjs/lib/socket.js:91:12)
    at exports.XMLHttpRequest.dispatchEvent (/Users/federico/Documents/webRTC-webinar-plugin/node_modules/xmlhttprequest/lib/XMLHttpRequest.js:591:25)
    at exports.XMLHttpRequest.handleError (/Users/federico/Documents/webRTC-webinar-plugin/node_modules/xmlhttprequest/lib/XMLHttpRequest.js:533:10)
    at ClientRequest.errorHandler (/Users/federico/Documents/webRTC-webinar-plugin/node_modules/xmlhttprequest/lib/XMLHttpRequest.js:459:14)
    at ClientRequest.emit (events.js:310:20)
    at Socket.socketErrorListener (_http_client.js:426:9)

Can somebody help? Thanks.

Was this page helpful?
0 / 5 - 0 ratings