how to go from net module to ws module - node.js

here is my current code
'use strict';
var _ = require('underscore'),
util = require('util'),
events = require('events'),
net = require('net'),
colors = require('colors');
// Chatango Socket connection handler, for both Rooms and PM
// Available events: onconnect, data, error, timeout, close, write ( Note: exceptions must be handled! )
function Socket(host, port)
{
this._host = host;
this._port = port || 443;
this._socket = new net.Socket();
this._pingTask = false;
this._connected = false;
this._firstCommand = true;
this._writeLock = false;
this._writeBuffer = [];
this._buffer = '';
this.connect();
}
util.inherits(Socket, events.EventEmitter);
Socket.prototype.connect = function()
{
if(this._socket._connecting) return;
var self = this;
if(this._socket.destroyed){
var reconnecting = true;
console.log('[SOCKET] reconnecting to '+this._host+':'+this._port);
}else{
var reconnecting = false;
console.log('[SOCKET] connecting to '+this._host+':'+this._port);
}
this._writeLock = true;
if(this._socket._events.connect){
this._socket.connect(this._port, this._host);
}else{
this._socket.connect(this._port, this._host, function() {
self._connected = true;
self._writeLock = false;
self._pingTask = setInterval(function() {
if(self._connected) {
self.write(['']);
}
}, 30000);
self.emit('onconnect');
});
}
if(reconnecting) return;
this._socket.on('data', function(data) {
var buffer = data.toString('utf8');
if(buffer.substr(-1) !== '\x00')
{
self._buffer += buffer;
}
else
{
if(self._buffer != '')
{
buffer = self._buffer + buffer;
self._buffer = '';
}
var messages = buffer.split('\x00');
_.each(messages, function(message){
message = message.replace(/(\r|\n)/g, '');
if(message !== '')
self.emit('data', message);
});
}
});
this._socket.on('error', function(exception) {
self.emit('error', exception);
});
this._socket.on('timeout', function(exception) {
self.emit('timeout', exception);
});
this._socket.on('close', function() {
self._connected = false;
self._writeBuffer = [];
self._writeLock = false;
self._buffer = '';
self._firstCommand = true;
clearInterval(self._pingTask);
self.emit('close');
});
}
Socket.prototype.disconnect = function(){
this._socket.destroy();
}
Socket.prototype.setWriteLock = function(bool) {
this._writeLock = _.isBoolean(bool) && bool;
}
Socket.prototype.write = function(data) {
if(this._connected)
{
if(this._firstCommand)
{
var terminator = '\x00';
this._firstCommand = false;
}
else
var terminator = '\r\n\x00';
if(this._writeLock)
this._writeBuffer.push(data);
else
{
_.each(this._writeBuffer, function(value){
this.write(value);
}.bind(this));
if(data)
this.emit('write', data.join(':'));
this._socket.write(data.join(':') + terminator);
}
}
}
exports.Instance = Socket;
as you can see i am using the net module
i want to change to the ws module and do this using websockets https://github.com/einaros/ws
i've read all kinds of examples but none of them give me what i want
the lib im using is
https://github.com/MakuraYami/derplib

Related

Need to add try catch block

I am new to nodejs so below is my code, I need to add try-catch blocks for my below code need some help to do this because new to this things, below is my websocket code newly created I need to add try-catch blocks for this , please help me out anyone
var WebSocket = require('ws');
//var Stomp = require('stompjs');
function CustomWebSocketListener(config) {
RED.nodes.createNode(this,config);
var node = this;
node.on('input', function(msg) {
let temp =msg.payload;
let urllist = temp.url;
let urls=[]
if(global.websocket!=null || global.websocket!=undefined){
let connections=global.websocket;
console.log("global")
if(global.isAccessTokenExpired){
for(let k in connections) {
connections[k].close();
connections[k].reconnect=false
console.log('connection closed:::');
}
urls=urllist;
}
else{
for(let i=0;i<urllist.length;i++){
let group=urllist[i].split("/")[7].split("?");
if(!connections[group[0]]){
urls.push(urllist[i])
}
}
}
}
else{
urls=urllist;
}
console.log("urls.length::::"+urls.length)
if(urls.length > 0){
for(let i=0;i<urls.length;i++){
console.log(':::::::for loop:::::::')
console.log('url----'+urls[i])
function connect(urlIndex) {
let ws;
if(urlIndex!=undefined||urlIndex!=null){
ws = new WebSocket(urls[urlIndex]);
}
else{
ws = new WebSocket(urls[i]);
}
ws.index=i;
ws.reconnect=true;
ws.onopen = function() {
};
ws.onmessage = function(e) {
console.log('Message:', e.data);
console.log('Socket is closed. Reconnect will be attempted in 30 second.', e.reason);
setTimeout(function() {
console.log("onclose ----ws reconnect"+ws.reconnect)
if(ws.reconnect){
console.log("inside if reconnect")
connect(ws.index);
}
}, 30000);
};
ws.onerror = function(err) {
console.error('Socket encountered error: ', err.message, 'Closing socket');
ws.close();
};
if(global.websocket==null || global.websocket==undefined){
global.websocket={};
console.log(global.websocket)
global.websocket[urls[i]]=ws;
}
else{
global.websocket[urls[i]]=ws;
}
}
connect();
}
}
});
}
RED.nodes.registerType("custom-websocketlistener",CustomWebSocketListener);
}
Thanks for anyone who would help me out with this
you can directly use where you want like this...
try{
//whatever you want
}
catch(e){
//whatever you want
}
In your code you can use like this
try {
RED.nodes.createNode(this, config)
var node = this
node.on('input', function(msg) {
let temp = msg.payload
let urllist = temp.url
let urls = []
if (global.websocket != null || global.websocket != undefined) {
let connections = global.websocket
console.log('global')
if (global.isAccessTokenExpired) {
for (let k in connections) {
connections[k].close()
connections[k].reconnect = false
console.log('connection closed:::')
}
urls = urllist
} else {
for (let i = 0; i < urllist.length; i++) {
let group = urllist[i].split('/')[7].split('?')
if (!connections[group[0]]) {
urls.push(urllist[i])
}
}
}
} else {
urls = urllist
}
console.log('urls.length::::' + urls.length)
if (urls.length > 0) {
for (let i = 0; i < urls.length; i++) {
console.log(':::::::for loop:::::::')
console.log('url----' + urls[i])
function connect(urlIndex) {
let ws
if (urlIndex != undefined || urlIndex != null) {
ws = new WebSocket(urls[urlIndex])
} else {
ws = new WebSocket(urls[i])
}
ws.index = i
ws.reconnect = true
ws.onopen = function() {}
ws.onmessage = function(e) {
console.log('Message:', e.data)
console.log('Socket is closed. Reconnect will be attempted in 30 second.', e.reason)
setTimeout(function() {
console.log('onclose ----ws reconnect' + ws.reconnect)
if (ws.reconnect) {
console.log('inside if reconnect')
connect(ws.index)
}
}, 30000)
}
ws.onerror = function(err) {
console.error('Socket encountered error: ', err.message, 'Closing socket')
ws.close()
}
if (global.websocket == null || global.websocket == undefined) {
global.websocket = {}
console.log(global.websocket)
global.websocket[urls[i]] = ws
} else {
global.websocket[urls[i]] = ws
}
}
connect()
}
}
})
} catch (e) {
console.log(e)
}
}

How to use clearInterval?

I am new to nodejs and try to send message to the server.
When I input 1, it will set message to the server every 3 second. When I input 2, it will stop sending the message.
However, it keeps sending message to the server when I input 2. How should I use clearInterval
this is the script.
var WebSocket = require('ws');
var ws = new WebSocket("ws://localhost:8075");
ws.onopen = ('connect', function(connect) {
let obj={};
obj.body='connect';
ws.send(JSON.stringify(obj));
});
process.stdin.resume();
process.stdin.setEncoding('utf8');
process.stdin.on('data', function (message) {
if (message.trim() == '1') {
var setintv = setInterval(function () {
let obj2 = {};
obj2.name = 'data'
message = '123';
obj2.body = message;
ws.send(JSON.stringify(obj2), console.log.bind(null, 'Sent : ', message));
}, 3000);
}else if(message.trim() == '2') {
clearInterval(setintv);
}
else {
let obj = {};
obj.name = 'data'
message = message.trim();
obj.body = message;
ws.send(JSON.stringify(obj), console.log.bind(null, 'Sent : ', message));
}
});
The variable setintv will not be available in the block where you call clearInterval. If you however declare it as a global it will be, for example:
var WebSocket = require('ws');
var ws = new WebSocket("ws://localhost:8075");
ws.onopen = ('connect', function(connect) {
let obj={};
obj.body='connect';
ws.send(JSON.stringify(obj));
});
var setintv = null;
process.stdin.resume();
process.stdin.setEncoding('utf8');
process.stdin.on('data', function (message) {
if (message.trim() == '1') {
// Save for later use.
setintv = setInterval(function () {
let obj2 = {};
obj2.name = 'data'
message = '123';
obj2.body = message;
ws.send(JSON.stringify(obj2), console.log.bind(null, 'Sent : ', message));
}, 3000);
}else if(message.trim() == '2') {
if (setintv !== null) {
clearInterval(setintv);
setintv = null; // We're done with this now.
}
}
else {
let obj = {};
obj.name = 'data'
message = message.trim();
obj.body = message;
ws.send(JSON.stringify(obj), console.log.bind(null, 'Sent : ', message));
}
});

Network Error 12030 using Websockets

Hello there i am integrating Wowza Media Server with Temasys plugin(for crossbrowser support) and the code runs great on Chrome but on IE11+ its is giving me network error.Please see attached image and code for details.
const GO_BUTTON_START = "Publish";
const GO_BUTTON_STOP = "Stop";
var video = document.querySelector('video');
var peerConnection = null;
var peerConnectionConfig = {'iceServers': []};
var localStream = null;
var wsURL = "wss://localhost.streamlock.net/webrtc-session.json";
var wsConnection = null;
var streamInfo = {applicationName:"webrtc", streamName:"myStream", sessionId:"[empty]"};
var userData = {param1:"value1"};
var videoBitrate = 360;
var audioBitrate = 64;
var newAPI = false;
navigator.getUserMedia = navigator.getUserMedia || navigator.mozGetUserMedia || navigator.webkitGetUserMedia;
window.RTCPeerConnection = window.RTCPeerConnection || window.mozRTCPeerConnection || window.webkitRTCPeerConnection;
window.RTCIceCandidate = window.RTCIceCandidate || window.mozRTCIceCandidate || window.webkitRTCIceCandidate;
window.RTCSessionDescription = window.RTCSessionDescription || window.mozRTCSessionDescription || window.webkitRTCSessionDescription;
//var constraints = {
//audio: false,
//video: true
//};
function successCallback(stream) {
window.stream = stream; // make stream available to browser console
localStream=stream;
console.log(localStream);
video = attachMediaStream(video, stream);
}
function errorCallback(error) {
console.log('navigator.getUserMedia error: ', error);
}
function pageReady()
{
$("#buttonGo").attr('value', GO_BUTTON_START);
var constraints =
{
video: true,
audio: false,
};
//alert('here');
navigator.getUserMedia(constraints, successCallback, errorCallback);
console.log("newAPI: "+newAPI);
}
function wsConnect(url)
{
wsConnection = new WebSocket(url);
wsConnection.binaryType = 'arraybuffer';
wsConnection.onopen = function()
{
console.log("wsConnection.onopen");
peerConnection = new RTCPeerConnection(peerConnectionConfig);
peerConnection.onicecandidate = gotIceCandidate;
if (newAPI)
{
var localTracks = localStream.getTracks();
for(localTrack in localTracks)
{
console.log("video stream"+localStream);
peerConnection.addTrack(localTracks[localTrack], localStream);
}
}
else
{
console.log("video stream"+localStream);
peerConnection.addStream(localStream);
}
peerConnection.createOffer(gotDescription, errorHandler);
}
wsConnection.onmessage = function(evt)
{
console.log("wsConnection.onmessage: "+evt.data);
var msgJSON = JSON.parse(evt.data);
var msgStatus = Number(msgJSON['status']);
var msgCommand = msgJSON['command'];
if (msgStatus != 200)
{
$("#sdpDataTag").html(msgJSON['statusDescription']);
stopPublisher();
}
else
{
$("#sdpDataTag").html("");
var sdpData = msgJSON['sdp'];
if (sdpData !== undefined)
{
console.log('sdp: '+msgJSON['sdp']);
peerConnection.setRemoteDescription(new RTCSessionDescription(sdpData), function() {
//peerConnection.createAnswer(gotDescription, errorHandler);
}, errorHandler);
}
var iceCandidates = msgJSON['iceCandidates'];
if (iceCandidates !== undefined)
{
for(var index in iceCandidates)
{
console.log('iceCandidates: '+iceCandidates[index]);
peerConnection.addIceCandidate(new RTCIceCandidate(iceCandidates[index]));
}
}
}
if (wsConnection != null)
wsConnection.close();
wsConnection = null;
}
wsConnection.onclose = function(error)
{
console.log("wsConnection.onclose"+error);
}
wsConnection.onerror = function(evt)
{
console.log("wsConnection.onerror: "+JSON.stringify(evt));
$("#sdpDataTag").html('WebSocket connection failed: '+wsURL);
stopPublisher();
}
}
function startPublisher()
{
wsURL = $('#sdpURL').val();
streamInfo.applicationName = $('#applicationName').val();
streamInfo.streamName = $('#streamName').val();
videoBitrate = $('#videoBitrate').val();
audioBitrate = $('#audioBitrate').val();
$.cookie("webrtcPublishWSURL", wsURL, { expires: 365 });
$.cookie("webrtcPublishApplicationName", streamInfo.applicationName, { expires: 365 });
$.cookie("webrtcPublishStreamName", streamInfo.streamName, { expires: 365 });
$.cookie("webrtcPublishVideoBitrate", videoBitrate, { expires: 365 });
$.cookie("webrtcPublishAudioBitrate", audioBitrate, { expires: 365 });
console.log("startPublisher: wsURL:"+wsURL+" streamInfo:"+JSON.stringify(streamInfo));
wsConnect(wsURL);
$("#buttonGo").attr('value', GO_BUTTON_STOP);
}
function stopPublisher()
{
if (peerConnection != null)
peerConnection.close();
peerConnection = null;
if (wsConnection != null)
wsConnection.close();
wsConnection = null;
$("#buttonGo").attr('value', GO_BUTTON_START);
console.log("stopPublisher");
}
function btn_start()
{
alert('button clicked');
if (peerConnection == null)
startPublisher();
else
stopPublisher();
}
function gotIceCandidate(event)
{
if(event.candidate != null)
{
//console.log('gotIceCandidate: '+JSON.stringify({'ice': event.candidate}));
}
}
function gotDescription(description)
{
var enhanceData = new Object();
if (audioBitrate !== undefined)
enhanceData.audioBitrate = Number(audioBitrate);
if (videoBitrate !== undefined)
enhanceData.videoBitrate = Number(videoBitrate);
description.sdp = enhanceSDP(description.sdp, enhanceData);
console.log('gotDescription: '+JSON.stringify({'sdp': description}));
peerConnection.setLocalDescription(description, function () {
wsConnection.send('{"direction":"publish", "command":"sendOffer", "streamInfo":'+JSON.stringify(streamInfo)+', "sdp":'+JSON.stringify(description)+', "userData":'+JSON.stringify(userData)+'}');
console.log("stream info"+JSON.stringify(streamInfo));
console.log("stream description"+JSON.stringify(description));
console.log("stream userData"+JSON.stringify(userData));
}, function() {console.log('set description error')});
}
function enhanceSDP(sdpStr, enhanceData)
{
var sdpLines = sdpStr.split(/\r\n/);
var sdpSection = 'header';
var hitMID = false;
var sdpStrRet = '';
for(var sdpIndex in sdpLines)
{
var sdpLine = sdpLines[sdpIndex];
if (sdpLine.length <= 0)
continue;
sdpStrRet += sdpLine+'\r\n';
if (sdpLine.indexOf("m=audio") === 0)
{
sdpSection = 'audio';
hitMID = false;
}
else if (sdpLine.indexOf("m=video") === 0)
{
sdpSection = 'video';
hitMID = false;
}
if (sdpLine.indexOf("a=mid:") === 0)
{
if (!hitMID)
{
if ('audio'.localeCompare(sdpSection) == 0)
{
if (enhanceData.audioBitrate !== undefined)
{
sdpStrRet += 'b=AS:' + enhanceData.audioBitrate + '\r\n';
sdpStrRet += 'b=TIAS:' + (enhanceData.audioBitrate*1024) + '\r\n';
}
}
else if ('video'.localeCompare(sdpSection) == 0)
{
if (enhanceData.videoBitrate !== undefined)
{
sdpStrRet += 'b=AS:' + enhanceData.videoBitrate + '\r\n';
sdpStrRet += 'b=TIAS:' + (enhanceData.videoBitrate*1024) + '\r\n';
}
}
hitMID = true;
}
}
}
return sdpStrRet;
}
function errorHandler(error)
{
console.log(error);
}
Click here to see image

WebRTC video only works when computers share same connection

So I have set up a web RTC connection, nearly fully understand the steps and mechanisms involved and have a test out on the web with a full SSL certificate (so I can use it on chrome) but It doesn't ever seem to work with computers that are not under the same wireless connection/router.
In my test I have logged that there are ICE candidates generated and that the two browsers are communicating but I get no video feed except for when the two trying to communicate are under the same connection.
Browser Side to set up webRTC:
var socket = io.connect();
var isChannelReady;
var isInitiator = false;
var isStarted = false;
var localStream;
var pc;
var remoteStream;
var turnReady;
var pc_config = {'iceServers': [{'url': 'stun:stun.l.google.com:19302'}]};
var pc_constraints = {'optional': [{'DtlsSrtpKeyAgreement': true}]};
// Set up audio and video regardless of what devices are present.
// var sdpConstraints = {'mandatory': {
// 'OfferToReceiveAudio':true,
// 'OfferToReceiveVideo':true }};
var sdpConstraints = {
optional: [],
'mandatory': {
'OfferToReceiveAudio': true,
'OfferToReceiveVideo': true
}
};
function sendMessage(message){
console.log('Client sending message: ', message);
// if (typeof message === 'object') {
// message = JSON.stringify(message);
// }
socket.emit('message', message);
}
socket.on('message', function (message){
console.log('Client received message:', message);
if (message === 'got user media') {
maybeStart();
} else if (message.type === 'offer') {
if (!isInitiator && !isStarted) {
maybeStart();
}
pc.setRemoteDescription(new RTCSessionDescription(message), function(){doAnswer()});
} else if (message.type === 'answer' && isStarted) {
pc.setRemoteDescription(new RTCSessionDescription(message));
} else if (message.type === 'candidate' && isStarted) {
var candidate = new RTCIceCandidate({
sdpMLineIndex: message.label,
candidate: message.candidate
});
pc.addIceCandidate(candidate);
} else if (message === 'bye' && isStarted) {
handleRemoteHangup();
}
});
////////////////////////////////////////////////////
var localVideo = document.getElementById('localVideo');
var remoteVideo = document.getElementById('remoteVideo');
function handleUserMedia(stream) {
console.log('Adding local stream.');
console.log(localVideo);
localVideo.src = window.URL.createObjectURL(stream);
localStream = stream;
sendMessage('got user media');
if (isInitiator) {
maybeStart();
}
}
function handleUserMediaError(error){
console.log('getUserMedia error: ', error);
}
// window.onload = function () {
// var localVideo = document.getElementById('localVideo');
// var remoteVideo = document.getElementById('mehh');
// }
var constraints = {video: true};
navigator.getUserMedia(constraints, handleUserMedia, handleUserMediaError);
console.log('Getting user media with constraints', constraints);
if (location.hostname != "localhost") {
requestTurn('https://computeengineondemand.appspot.com/turn?username=41784574&key=4080218913');
}
function maybeStart() {
if (!isStarted && typeof localStream != 'undefined' && isChannelReady) {
createPeerConnection();
pc.addStream(localStream);
isStarted = true;
console.log('isInitiator', isInitiator);
if (isInitiator) {
doCall();
}
}
}
window.onbeforeunload = function(e){
sendMessage('bye');
}
/////////////////////////////////////////////////////////
function createPeerConnection() {
try {
pc = new RTCPeerConnection(null);
pc.onicecandidate = handleIceCandidate;
pc.onaddstream = handleRemoteStreamAdded;
pc.onremovestream = handleRemoteStreamRemoved;
console.log('Created RTCPeerConnnection');
} catch (e) {
console.log('Failed to create PeerConnection, exception: ' + e.message);
alert('Cannot create RTCPeerConnection object.');
return;
}
}
function handleIceCandidate(event) {
console.log('handleIceCandidate event: ', event);
if (event.candidate) {
sendMessage({
type: 'candidate',
label: event.candidate.sdpMLineIndex,
id: event.candidate.sdpMid,
candidate: event.candidate.candidate});
} else {
console.log('End of candidates.');
}
}
function handleRemoteStreamAdded(event) {
console.log('Remote stream added.');
remoteVideo.src = window.URL.createObjectURL(event.stream);
remoteStream = event.stream;
}
function handleCreateOfferError(event){
console.log('createOffer() error: ', e);
}
function doCall() {
console.log('Sending offer to peer');
pc.createOffer(setLocalAndSendMessage, handleCreateOfferError);
}
function doAnswer() {
console.log('Sending answer to peer.');
pc.createAnswer(setLocalAndSendMessage, function(err){if(err) throw err;}, sdpConstraints);
}
function setLocalAndSendMessage(sessionDescription) {
// Set Opus as the preferred codec in SDP if Opus is present.
sessionDescription.sdp = preferOpus(sessionDescription.sdp);
pc.setLocalDescription(sessionDescription);
console.log('setLocalAndSendMessage sending message' , sessionDescription);
sendMessage(sessionDescription);
}
function requestTurn(turn_url) {
var turnExists = false;
for (var i in pc_config.iceServers) {
if (pc_config.iceServers[i].url.substr(0, 5) === 'turn:') {
turnExists = true;
turnReady = true;
break;
}
}
if (!turnExists) {
console.log('Getting TURN server from ', turn_url);
// No TURN server. Get one from computeengineondemand.appspot.com:
var xhr = new XMLHttpRequest();
xhr.onreadystatechange = function(){
if (xhr.readyState === 4 && xhr.status === 200) {
var turnServer = JSON.parse(xhr.responseText);
console.log('Got TURN server: ', turnServer);
pc_config.iceServers.push({
'url': 'turn:' + turnServer.username + '#' + turnServer.turn,
'credential': turnServer.password
});
turnReady = true;
}
};
xhr.open('GET', turn_url, true);
xhr.send();
}
}
function handleRemoteStreamAdded(event) {
console.log('Remote stream added.');
remoteVideo.src = window.URL.createObjectURL(event.stream);
remoteStream = event.stream;
}
function handleRemoteStreamRemoved(event) {
console.log('Remote stream removed. Event: ', event);
}
function hangup() {
console.log('Hanging up.');
stop();
sendMessage('bye');
}
function handleRemoteHangup() {
// console.log('Session terminated.');
// stop();
// isInitiator = false;
}
function stop() {
isStarted = false;
// isAudioMuted = false;
// isVideoMuted = false;
pc.close();
pc = null;
}
///////////////////////////////////////////
// Set Opus as the default audio codec if it's present.
function preferOpus(sdp) {
var sdpLines = sdp.split('\r\n');
var mLineIndex;
// Search for m line.
for (var i = 0; i < sdpLines.length; i++) {
if (sdpLines[i].search('m=audio') !== -1) {
mLineIndex = i;
break;
}
}
if (mLineIndex === null || mLineIndex === undefined) {
return sdp;
}
// If Opus is available, set it as the default in m line.
for (i = 0; i < sdpLines.length; i++) {
if (sdpLines[i].search('opus/48000') !== -1) {
var opusPayload = extractSdp(sdpLines[i], /:(\d+) opus\/48000/i);
if (opusPayload) {
sdpLines[mLineIndex] = setDefaultCodec(sdpLines[mLineIndex], opusPayload);
}
break;
}
}
// Remove CN in m line and sdp.
sdpLines = removeCN(sdpLines, mLineIndex);
sdp = sdpLines.join('\r\n');
return sdp;
}
function extractSdp(sdpLine, pattern) {
var result = sdpLine.match(pattern);
return result && result.length === 2 ? result[1] : null;
}
// Set the selected codec to the first in m line.
function setDefaultCodec(mLine, payload) {
var elements = mLine.split(' ');
var newLine = [];
var index = 0;
for (var i = 0; i < elements.length; i++) {
if (index === 3) { // Format of media starts from the fourth.
newLine[index++] = payload; // Put target payload to the first.
}
if (elements[i] !== payload) {
newLine[index++] = elements[i];
}
}
return newLine.join(' ');
}
// Strip CN from sdp before CN constraints is ready.
function removeCN(sdpLines, mLineIndex) {
console.log(sdpLines[mLineIndex])
var mLineElements = sdpLines[mLineIndex].split(' ');
// Scan from end for the convenience of removing an item.
for (var i = sdpLines.length-1; i >= 0; i--) {
var payload = extractSdp(sdpLines[i], /a=rtpmap:(\d+) CN\/\d+/i);
if (payload) {
var cnPos = mLineElements.indexOf(payload);
if (cnPos !== -1) {
// Remove CN payload from m line.
mLineElements.splice(cnPos, 1);
}
// Remove CN line in sdp
sdpLines.splice(i, 1);
}
}
sdpLines[mLineIndex] = mLineElements.join(' ');
return sdpLines;
}
/////////////////////////////////////////////
room = prompt("Enter room name:");
var socket = io.connect();
if (room !== '') {
console.log('Create or join room', room);
socket.emit('create or join', room);
}
socket.on('created', function (room){
console.log('Created room ' + room);
isInitiator = true;
});
socket.on('full', function (room){
console.log('Room ' + room + ' is full');
});
socket.on('join', function (room){
console.log('Another peer made a request to join room ' + room);
console.log('This peer is the initiator of room ' + room + '!');
isChannelReady = true;
});
socket.on('joined', function (room){
console.log('This peer has joined room ' + room);
isChannelReady = true;
});
socket.on('log', function (array){
console.log.apply(console, array);
});
////////////////////////////////////////////////
And here is everything on the server side pertaining to webRTC (using socket io):
server.listen(port);
server.on('error', onError);
server.on('listening', onListening);
var io = require('socket.io').listen(server);
io.sockets.on('connection', function (socket){
console.log('connected');
// convenience function to log server messages on the client
function log(){
var array = [">>> Message from server: "];
for (var i = 0; i < arguments.length; i++) {
array.push(arguments[i]);
}
socket.emit('log', array);
}
socket.on('message', function (message) {
log('Got message:', message);
// for a real app, would be room only (not broadcast)
socket.broadcast.emit('message', message);
});
socket.on('create or join', function (room) {
//io.sockets.clients(room)
//io.of('/').in(room).clients
//io.sockets.adapter.rooms[room]
var numClients;
var ish = io.sockets.adapter.rooms[room];
(ish === undefined) ? numClients = 0 : numClients = ish.length
log('Room ' + room + ' has ' + numClients + ' client(s)');
log('Request to create or join room ' + room);
if (numClients === 0){
socket.join(room);
socket.emit('created', room);
} else if (numClients === 1) {
io.sockets.in(room).emit('join', room);
socket.join(room);
socket.emit('joined', room);
} else { // max two clients
socket.emit('full', room);
}
socket.emit('emit(): client ' + socket.id + ' joined room ' + room);
socket.broadcast.emit('broadcast(): client ' + socket.id + ' joined room ' + room);
});
});
I simply can't find any errors that prevent the streams from being sent...
More than willing to do a private chat so I can get moving on my project.

Nodejs streams writablestream drain event not firing

I am trying to read in a large file, do some computation and then write to a much bigger file. To prevent excessive memory consumption, I am using streams. The problem that I am facing is that the writestream is not firing the "drain" event, which signals that the writes have been flushed to disk. In order to prevent "back-pressure", I am waiting for the drain event to be fired before I start writing to the buffer again. While debugging I found that after a .write() call returns false and the line fvfileStream.once('drain', test) is executed, the program just stops and does not do anything.
Here is the code:
var fs = require('fs');
//a test function I created to see if the callback is called after drain.
var test = function(){
console.log("Done Draining");
}
fs.readFile('/another/file/to/be/read', {
encoding: "utf8"
}, function(err, data) {
if (err) throw err;
//Make an array containing tags.
var tags = data.split('\n');
//create a write stream.
var fvfileStream = fs.createWriteStream('/path/TagFeatureVectors.csv');
//read in the question posts
var qfileStream = fs.createReadStream('/Big/file/QuestionsWithTags.csv', {
encoding: "utf8"
});
var partialRow = null;
var writable = true;
var count = 0;
var doRead = function() {
var qData = qfileStream.read();
var questions = qData.split('\n');
if (partialRow != null) {
questions[0] = partialRow + questions[0];
partialRow = null;
}
var lastRow = questions[questions.length - 1];
if (lastRow.charAt(lastRow.length - 1) != '\n') {
partialRow = lastRow;
}
questions.forEach(function(row, index, array) {
count++;
var fields = row.split(',');
console.log("Processing question number: " + count + " id: " + fields[0]);
var tagString = fields[1];
var regex = new RegExp(/<([^>]+)>/g);
tags.forEach(function(tag, index, array) {
var found = false;
var questionTags;
while ((questionTags = regex.exec(tagString)) != null) {
var currentTag = questionTags[1]
if (currentTag === tag) {
found = true;
break;
}
};
//This is where the writestream is written to
if (found) {
writable = fvfileStream.write("1,", "utf8");
}else {
writable = fvfileStream.write("0,","utf8");
}
});
});
fvfileStream.write("\n");
}
qfileStream.on('readable', function() {
if (writable) {
doRead();
} else {
//Waiting for drain event.
fvfileStream.once('drain', test);
}
});
qfileStream.on('end', function() {
fvfileStream.end();
});
});
Updated
Based on advise provided by #loganfsmyth, I implemented transform streams, but still ran into the same issue. Here is my updated code:
var fs = require('fs');
var stream = require('stream');
var util = require('util');
var Transform = stream.Transform;
function FVCreator(options) {
// allow use without new
if (!(this instanceof FVCreator)) {
return new FVCreator(options);
}
// init Transform
Transform.call(this, options);
}
util.inherits(FVCreator, Transform);
var partialRow = null;
var count = 0;
var tags;
FVCreator.prototype._transform = function(chunk, enc, cb) {
var that = this;
var questions = chunk.toString().split('\n');
if (partialRow != null) {
questions[0] = partialRow + questions[0];
partialRow = null;
}
var lastRow = questions[questions.length - 1];
if (lastRow.charAt(lastRow.length - 1) != '\n') {
partialRow = lastRow;
questions.splice(questions.length - 1, 1);
}
questions.forEach(function(row, index, array) {
count++;
var fields = row.split(',');
console.log("Processing question number: " + count + " id: " + fields[0]);
var tagString = fields[1];
var regex = new RegExp(/<([^>]+)>/g);
tags.forEach(function(tag, index, array) {
var found = false;
var questionTags;
while ((questionTags = regex.exec(tagString)) != null) {
var currentTag = questionTags[1]
if (currentTag === tag) {
found = true;
break;
}
};
if (found) {
that.push("1,", "utf8");
} else {
that.push("0,", "utf8");
}
});
});
this.push("\n", "utf8");
cb();
};
fs.readFile('/another/file/to/be/read', {
encoding: "utf8"
}, function(err, data) {
if (err) throw err;
//Make an array containing tags.
tags = data.split('\n');
//write to a file.
var fvfileStream = fs.createWriteStream('/path/TagFeatureVectors.csv');
//read in the question posts
var qfileStream = fs.createReadStream('/large/file/to/be/read', {
encoding: "utf8"
});
var fvc = new FVCreator();
qfileStream.pipe(fvc).pipe(fvfileStream);
});
I am running this on OSX Yosemite.

Resources