I have a two webservers both running https with the same certificates, I have a main shard that the user connects to example.com, they retrieve some data and try to connect to an ip address on the 2nd shard via websocket.
But no matter what I configure I get an Error 1006 on the client side when connecting to the 2nd shard. Firefox devtooling gives me multiple errors - ssl_error_bad_cert_domain, SSL_ERROR_RX_RECORD_TOO_LONG.
The certificates are issued and signed, I was wondering where I should go from here. Thanks :)
SHARD2
const options = {
key: './server.key',
cert: './server.cert'
};
var https = require('https').Server(options);
https.listen(443, function () {
// console.log('Https listening on *: 443');
});
let WebSocket = require('ws');
let socket = new WebSocket.Server({ server:https });
socket.on('connection', function (ws, req) {
ws.on('message', (msgRaw) =>{
});
ws.on('close', function(code, reason) {
});
ws.on('error', function(error) {
console.log(error);
ws.close();
});
});
CLIENT
function connect() {
"use strict";
window.WebSocket = window.WebSocket || window.MozWebSocket;
if (!window.WebSocket) {
alert('Your browser doesn\'t support WebSocket');
return;
}
wss = new WebSocket('wss://123.123.123.120/:443');
wss.onmessage = function(event) {
};
wss.onerror = function(event) {
console.log(`wss error: ${JSON.stringify(event)}`);
};
wss.onclose = function(event) {
};
}
Useful sys diagram?
Related
I am using nodejs to run the server, there is no log file
This is my server.js
const https = require('https');
const fs = require('fs');
const ws = require('ws');
const options = {
key: fs.readFileSync('key.pem'),
cert: fs.readFileSync('cert.pem')
};
const wss = new ws.Server({noServer: true});
function accept(req, res) {
// all incoming requests must be websockets
if (!req.headers.upgrade || req.headers.upgrade.toLowerCase() != 'websocket') {
res.end();
return;
}
// can be Connection: keep-alive, Upgrade
if (!req.headers.connection.match(/\bupgrade\b/i)) {
res.end();
return;
}
wss.handleUpgrade(req, req.socket, Buffer.alloc(0), onConnect);
}
function onConnect(ws) {
ws.on('message', function (message) {
let name = message.match(/([\p{Alpha}\p{M}\p{Nd}\p{Pc}\p{Join_C}]+)$/gu) || "Guest";
ws.send(`${name}!`);
//setTimeout(() => ws.close(1000, "Bye!"), 5000);
});
}
https.createServer(options, function (req, res) {
res.writeHead(200);
res.end("hello world\n");
}).listen(8000);
This is my code in react
componentDidMount() {
var connection = new WebSocket('wss://localhost:8000/');
connection.onopen = function(e) {
connection.send("add people");
};
connection.onmessage = function(event) {
// alert(`[message] Data received from server: ${event.data}`);
console.log("output ", event.data);
};
}
While I am trying to connect with web-socket with my jsx file its give me an error which is Firefox can’t establish a connection to the server at wss://localhost:8000/.
Your implementaion needs some changes. In the backend server, you forgot to call the onConnect function. So your ws.on method will never call.
Also, you imported the ws and create a WebSocket server wss, but you add some event listener on ws wrongly, you should add listener on your Websocket instance (wss):
// rest of the codes ...
const was = new ws.Server({noServer: true})
wss.on('connection`) {
// do something here ...
}
// rest of the codes ...
https.createServer(options, () => {
// do something here ...
})
There are some examples of how to create the WebSocket server along with the HTTP server on ws npm page.
I tried to build a chat box server by node.js. When the browser requestes the page, it workes well at first. But when I refresh the page, the Server crashes.
Below is the error message:
events.js:183
throw er; // Unhandled 'error' event
^
Error: read ECONNRESET
at _errnoException (util.js:1022:11)
at TCP.onread (net.js:615:25)
I used the node --inspect index.js, but could not find the point.
Below is the code of index.js:
const http = require('http');
const fs = require('fs');
const extract = require('./extract');
const wss = require('./websockets-server');
var handleError = function (err,res) {
res.writeHead(404);
res.end();
}
var server = http.createServer(function (req, res) {
console.log("Responding to a request.");
var filePath = extract(req.url);
console.log("filePath:"+filePath);
fs.readFile(filePath,function (err,data) {
if(err){
handleError(err,res);
return;
}else {
res.end(data);
}
})
})
server.listen(3000);
When I comment the 4th line, the import of websockets-server. Server works well when I refresh the page. Maybe it's about the websocket while it works without websocket.
Below is code of websockets-server.js:
const WebSocket = require('ws');
var WebSocketServer = WebSocket.Server;
var port = 3001;
var ws = new WebSocketServer({
port:port
});
var message = [];
console.log('websockets server started');
ws.on('connection', function (socket) {
console.log('client connection established');
message.forEach(function (msg) {
socket.send(msg);
})
socket.on('message', function (data) {
console.log('message received: ' + data);
message.push(data);
ws.clients.forEach(function (clientSocket) {
clientSocket.send(data);
});
});
});
Does the problem is about the websocket? Whether should I do process when the client shutdown the connection with the server while refreshing the page.
extract.js below:
const path = require('path');
var extractFilePath = function (url) {
var filePath;
var fileName = 'index.html';
if(url.length > 1){
fileName = url.substring(1);
}
console.log('The fileName is: ' + fileName);
filePath = path.resolve(__dirname, 'app', fileName);
return filePath;
}
module.exports = extractFilePath;
I guess that you maybe execute var ws = new WebSocket("ws://localhost:3001"); in html file. I haven't figured out exact reason about your error as I'm not proficient in WebSocket. But there is a solution:
window.onbeforeunload = function () {
ws.close();
}
close connection before reload, then the error will not reappear.
You need to add an error listener on the socket. Error listener only on the websocket instance does not help in this case.
socket.on('error', function(e){
console.log(e);
});
The ECONNRESET error means that the other side (browser) closed the connection abruptly. On browser refresh, browser simple killed the connection with the websocket server.
To solve this, you have to listen for the error event on the websocket server instance.
// listen for "error" event so that the whole app doesn't crash
wss.on("error", function(error){
console.log(error);
}
I was having the same problem, but it resolved after this command:
npm install #ionic/app-scripts#nightly --save-dev
I have 2 clients, I need client1 gives information to client2 and this receive an alert of it, I'm implementing Websocket "ws" with NodeJS for this.
Client1 web page receive an answer via AJAX and send information to server.js in JSON format, like this example:
/mysite_folder/client1/client1.php
<script>
var userorder = $("#user").val(); //client2 username who will receive information
$.post("myscript.php",{
my: variables
}).done(function(response){
var wsUri = "wss://www.mysite.com:3000/sockets/";
var output;
websocket = new WebSocket(wsUri);
websocket.onopen = onOpen;
websocket.onclose = onClose;
websocket.onmessage = onMessage;
websocket.onerror = onError;
function onOpen(evt){
output = {
"status": "ASSIGNED",
"user": userorder
};
doSend(JSON.stringify(output));
}
function doSend(message){
websocket.send(message);
websocket.close();
}
function onMessage(evt){
}
function onClose(evt){
location.reload();
}
function onError(evt){
}
});
</script>
After client1 send information, connection closes and refresh client1 page. My server receives this JSON information like this: /mysite_folder/sockets/server.js
var WebSocketServer = require('ws').Server,
fs = require('fs');
var cfg = {
ssl: true,
port: 3000,
ssl_key: '/path/of/sslkey',
ssl_cert: '/path/of/sslcert'
};
var httpServ = ( cfg.ssl ) ? require('https') : require('http');
var app = null;
var processRequest = function( req, res ) {
res.writeHead(200);
res.end("All glory to WebSockets!\n");
};
if ( cfg.ssl ) {
app = httpServ.createServer({
// providing server with SSL key/cert
key: fs.readFileSync( cfg.ssl_key ),
cert: fs.readFileSync( cfg.ssl_cert )
}, processRequest ).listen( cfg.port );
} else {
app = httpServ.createServer( processRequest ).listen( cfg.port );
}
var wss = new WebSocketServer( { server: app } );
wss.on('connection', function connection(ws){
console.log("User connected");
ws.on('message', function incoming(message){
var info = JSON.parse(message); //receive client1 info
if(info.status=="ASSIGNED"){
ws.send(info.user); //send client2 username
}
});
});
Parsing JSON and comparing that information status is "ASSIGNED" I need "info.user" send to client2 page displaying an alert message, so in client2 I wrote like this example: /mysite_folder/client2/client2.php
$(document).ready(function(){
var user = $("#user").val(); //client2 username
var wsUri = "wss://www.mysite.com:3000/sockets/";
var output;
websocket = new WebSocket(wsUri);
websocket.onopen = onOpen;
websocket.onclose = onClose;
websocket.onmessage = onMessage;
websocket.onerror = onError;
function onOpen(evt){
}
function doSend(message){
}
function onMessage(evt){
if(user==evt){ //if client2 username sent by server is the same with client2 username logged in the page, make an alert
alert("Your order was ASSIGNED");
}
websocket.close();
}
function onClose(evt){
}
function onError(evt){
}
});
Connections works fine, client1 is working well, but in client2 doesn't happen anything, how can I make client2 get this alert?
UPDATE
On server.js I added a broadcast method like this:
var wss = new WebSocketServer( { server: app } );
// Broadcast to all.
wss.broadcast = function broadcast(data) {
wss.clients.forEach(function each(client) {
if ( client.readyState == WebSocketServer.OPEN) {
client.send(data);
}
});
};
wss.on('connection', function connection(ws){
console.log("User connected");
ws.on('message', function incoming(message){
//Broadcast to everyone else
var info = JSON.parse(message);
console.log(info.user); //shows username in console
wss.clients.forEach(function each(client) {
if (client !== ws && client.readyState === WebSocketServer.OPEN) {
if(info.status=="ASSIGNED"){
client.send(info.user);
}
}
});
});
});
But client2 is still doesn't receiving message from server and not displaying the alert.
I would like some help.
The issue is your sending data back down the same socket connection you receive the message i.e. ws.send(info.user), ws refers to that client connection only.
The server has a broadcast method you can use which sends the message to all active connections
wss.broadcast(info.user);
Currently I am writing a NS app that will communicate with a WebSocket over SSL. Here is server's code (server.js):
var fs = require('fs');
var cfg = {
port: 8082,
ssl_key: fs.readFileSync('keys/server.key'),
ssl_cert: fs.readFileSync('keys/server.crt'),
ca: fs.readFileSync('keys/ca.crt')
};
var httpServ = require('https');
var WebSocketServer = require('ws').Server;
var app = null;
// dummy request processing
var processRequest = function( req, res ) {
res.writeHead(200);
res.end("All glory to WebSockets!\n");
};
app = httpServ.createServer({
// providing server with SSL key/cert
key: cfg.ssl_key,
cert: cfg.ssl_cert,
ca: cfg.ssl.ca,
passphrase: '1234',
requestCert: true,
rejectUnauthorized: false,
}, processRequest ).listen( cfg.port );
var wss = new WebSocketServer( { server: app } );
wss.on('connection', function(ws) {
console.log("Connected!");
ws.on('message', function(message) {
console.log('received: %s', message);
});
ws.send('something');
});
Server is running well without problem. Below is the client code (wsclient.js):
const WebSocket = require('ws');
const ws = new WebSocket('wss://localhost:8082');
ws.on('open', function open() {
ws.send("dummy");
ws.on('error', function(evt) {
console.log("The socket had an error", evt.error);
});
});
When I ran the client by typing node wsclient.js, it throw the following error:
Error: unable to verify the first certificate
Obviously, the error was caused by not providing the certificate info to the request. But I have no idea how to get this done in my client code. Thanks a lot for any clues or suggestions.
Finally I found the answer:
const WebSocket = require('ws');
const ws = new WebSocket('wss://localhost:8082',{
key: fs.readFileSync('./keys/client.key'),
cert: fs.readFileSync('./keys/client.crt'),
ca: fs.readFileSync('./keys/ca.crt')
});
ws.on('open', function open() {
ws.send("dummy");
ws.on('error', function(evt) {
console.log("The socket had an error", evt.error);
});
});
Now it works!
I have the simple node.js server that receives udp packages and prints them in the console:
var PORT = 19777;
var MULTICAST_GROUP = "224.0.0.251";
var dgram = require("dgram");
var payload = new Buffer('A wild message appears');
var client = dgram.createSocket("udp4");
client.on("message", function(message, rinfo) {
console.log("received: ",message);
});
client.on("listening", function() {
console.log("listening on ",client.address());
client.setBroadcast(true);
client.setTTL(64);
client.setMulticastTTL(64);
client.setMulticastLoopback(true);
client.addMembership(MULTICAST_GROUP);
client.send(payload, 0, payload.length, PORT, MULTICAST_GROUP, function(err,bytes) {
console.log("err: "+err+" bytes: "+bytes);
// client.close();
});
});
client.on("close", function() {
console.log("closed");
});
client.on("error", function(err) {
console.log("error: ",err);
});
client.bind(19777);
it works remotely on my server. I want to present the received data to each client that will turn on his browser and enter the address of my server. How could I do that?