I spent my whole day trying to set up my app using peer but couldn't succeed so far.
Here's what my server js file looks like:
const path = require('path');
const express = require('express');
const { ExpressPeerServer } = require('peer');
const app = express();
const PORT = process.env.PORT || 3000;
// set your static server
app.use(express.static(path.resolve(`${__dirname}/public`)));
// views
app.get('/', (req, res) => {
res.sendFile(path.join(__dirname, 'views/index.html'));
});
// start listening
const server = app.listen(PORT);
console.log('Server is running localhost on port: ' + PORT);
// peerjs
const peerServer = ExpressPeerServer(server, {
debug: true,
});
app.use('/peerjs', peerServer);
// listeners
peerServer.on('connection', (client) => {
console.log("Server: Peer connected with ID:", client.id);
});
peerServer.on('disconnect', (client) => {
console.log("Server: Peer disconnected with ID:", client.id);
});
When I run the app, it says Server: Peer connected with ID: ff1b23c0-9b67-49e3-8461-35405397d3b2
but then a minute later it says Server: Peer disconnected with ID: ff1b23c0-9b67-49e3-8461-35405397d3b2
.
Also, I failed to make the server connect to the client. The peer.on('connection', function(conn) {}
function never gets called. I may be missing something.
So I'm trying to find an example code that works but so far I haven't found any example(using nodeJS, express, peerJS) that works.
Can anyone please introduce me to any working example of a node app that uses peer?
All I want is just to check the server-client connection as a first step. (without the connection being disconnected automatically)
I spent my whole day trying to set up my app using peer but couldn't succeed so far.
Here's what my server js file looks like:
const path = require('path');
const express = require('express');
const { ExpressPeerServer } = require('peer');
const app = express();
const PORT = process.env.PORT || 3000;
// set your static server
app.use(express.static(path.resolve(`${__dirname}/public`)));
// views
app.get('/', (req, res) => {
res.sendFile(path.join(__dirname, 'views/index.html'));
});
// start listening
const server = app.listen(PORT);
console.log('Server is running localhost on port: ' + PORT);
// peerjs
const peerServer = ExpressPeerServer(server, {
debug: true,
});
app.use('/peerjs', peerServer);
// listeners
peerServer.on('connection', (client) => {
console.log("Server: Peer connected with ID:", client.id);
});
peerServer.on('disconnect', (client) => {
console.log("Server: Peer disconnected with ID:", client.id);
});
When I run the app, it says Server: Peer connected with ID: ff1b23c0-9b67-49e3-8461-35405397d3b2
but then a minute later it says Server: Peer disconnected with ID: ff1b23c0-9b67-49e3-8461-35405397d3b2
.
Also, I failed to make the server connect to the client. The peer.on('connection', function(conn) {}
function never gets called. I may be missing something.
So I'm trying to find an example code that works but so far I haven't found any example(using nodeJS, express, peerJS) that works.
Can anyone please introduce me to any working example of a node app that uses peer?
All I want is just to check the server-client connection as a first step. (without the connection being disconnected automatically)
Share Improve this question asked Apr 25, 2020 at 15:46 Zack LeeZack Lee 3,1047 gold badges44 silver badges93 bronze badges 02 Answers
Reset to default 4 +50Here is a small working example, I have tried this myself.
Your backend Express Server:
const express = require('express');
const { ExpressPeerServer } = require('peer');
const cors = require('cors');
const app = express();
app.use(cors());
app.get('/', (req, res, next) => res.send('Hello world!'));
const server = app.listen(9000);
const peerServer = ExpressPeerServer(server, {
debug: true
});
app.use('/peerjs', peerServer);
peerServer.on('connection', (client) => { console.log('client connected');});
peerServer.on('disconnect', (client) => { console.log('client disconnected');});
And your frontend code to connect with above peer server:
<html>
<head>
<script src="https://cdn.jsdelivr/npm/[email protected]/dist/peer.min.js"></script>
</head>
<body>
<script>
const peer = new Peer('someid', {
host: 'localhost',
port: 9000,
path: '/peerjs'
});
</script>
</body>
</html>
I just mitted a plete working example of peerjs working with nodejs at github here:
. I wasted a lot of time trying to follow many tutorials and none seem to work for me. By playing with it and reading in the peerjs client telegram's group that people were making the applications work by adding delays at random places with code blocking sleep functions, I knew it was a timing issue. But funny enough how my brain works, as usual I woke up in the middle of the night with the solution.
Here is what was happening to me with most of the tutorials. To respond to the calls they need to first set up the event listener peer.on('call',(call) => {...})
, and then they need to answer the call with call.answer(stream)
inside that function.
Since they require the local stream to answer the call, all the examples I found call the
navigator.mediaDevices.getUserMedia(constraints)
.then(function(stream) {
/* use the stream */
})
.catch(function(err) {
/* handle the error */
});
or they use the async/await construct and call:
async function getMedia(constraints) {
let stream = null;
try {
stream = await navigator.mediaDevices.getUserMedia(constraints);
/* use the stream */
} catch(err) {
/* handle the error */
}
}
And then after the promise is returned in the case of .then or after the nonblocking await in the case of the async function, they start the event listener as in this example from a tutorial that doesn't work for my setup:
navigator.mediaDevices
.getUserMedia({
audio: true,
video: true,
})
.then((stream) => {
myVideoStream = stream;
addVideoStream(myVideo, stream);
peer.on(“call”, (call) => {
call.answer(stream);
const video = document.createElement(“video”);
call.on(“stream”, (userVideoStream) => {
addVideoStream(video, userVideoStream);
});
});
socket.on(“user-connected”, (userId) => {
connectToNewUser(userId, stream);
});
});
What is the problem? Simple, when the destination client answers to the originator client it first informs the peer server that it wants to connect to the same room, the signaling mechanism to inform the originator client that a destination client wants to connect arrives to the originator client at its own speed. The response from the originator client is to call the destination using the id that the peer server gave through the signaling mechanism. The originator client needs its video/audio stream object for making the call, something it already has obtained, when it first created the room, way before receiving a notification through the signaling mechanism that there is somebody else in the room to call. Thus the call can happen very fast (or very slow if the signaling is slow, for the sake of this discussion we will assume the signaling is very fast), therefore the call is made to the destination client from the originator client in a few milliseconds. But, there is no guarantee that the originator client is ready to receive this call, it could well be in a situation where it just started, connected to the peer server to get and id and is now waiting for the promise of the getUserMedia() method to return. Thus there is NO guarantee that the call will arrive after the destination client has gotten its stream available and thus the 'call' event handler set up. Therefore the event can be received before a handler exists. Then, the destination client would keep on waiting forever (as happened to me with the tutorials), making it seem nothing works. What I changed to make it work, was to make the peer.on('call', async (call) => {... immediately, therefore, starting the 'call' event handler before any server connection took place. Then, inside the event handler, await for the return of the stream like this:
peer.on("call", async (call) => {
let stream = null;
console.log('*** "call" event received, calling call.answer(strem)');
// Obtain the stream object
try {
stream = await navigator.mediaDevices.getUserMedia(
{
audio: true,
video: true,
});
// Set up event listener for a peer media call -- peer.call, returns a mediaConnection that I name call
// Answer the call by sending this clients video stream --myVideo-- to calling remote user
call.answer(stream);
// Create new DOM element to place the remote user video when it es
const video = document.createElement('video');
// Set up event listener for a stream ing from the remote user in response to this client answering its call
call.on("stream", (userVideoStream) => {
console.log('***"stream" event received, calling addVideoStream(UserVideoStream)');
// Add remote user video stream to this client's active videos in the DOM
addVideoStream(video, userVideoStream);
});
} catch (err) {
/* handle the error */
console.log('*** ERROR returning the stream: ' + err);
};
});
Hope this helps so that nobody else has to go through this again!