Call socket.io from dgram socket udp4 - json

I'm having some problems with a small aplications that I'm developing.
I have an Arduino with a temperature sensor, I wanted to send the values to a nodejs service, and show it to a webpage. I wanted to use socket.io, but I'm just able to use UDP connection from arduino to server (ethernet). Just to keep the sensor value refreshed, seems that I have to call a io socket from the UDP service, but I can't.
My socket.io that works when I call it from a webpage.
var io = require('socket.io').listen(3000);
io.sockets.on('connection', function (socket) {
socket.on('message', function (message) {
console.log("Got message: " + message);
io.sockets.emit('SensorList', { 'temperature': temp });
});
});
This is the UDP service that reads the arduino packets:
var dgram = require("dgram");
var server = dgram.createSocket("udp4");
var fs = require('fs');
**var io = require('socket.io');**
var crlf = new Buffer(2);
crlf[0] = 0xD; //CR - Carriage return character
crlf[1] = 0xA; //LF - Line feed character
server.on("message", function (msg, rinfo) { //every time new data arrives do this:
console.log("server got: " + msg.readUInt16LE(0) + " from " + rinfo.address + ":" + rinfo.port); // you can comment this line out
**var socket = io.connect('http://localhost:3000');
socket.on('connect', function () {
socket.send(msg.readUInt16LE(0));
});**
});
server.on("listening", function () {
var address = server.address();
console.log("server listening " + address.address + ":" + address.port);
});
server.bind(6000); //listen to udp traffic on port 6000
The error is:
var socket = io.connect('http://localhostit.is:3000'); ^
TypeError: Object # has no method 'connect'
at Socket. (/Users/xfr/Documents/nodejs/temp1/app2.js:15:19)
at Socket.EventEmitter.emit (events.js:98:17)
at UDP.onMessage (dgram.js:437:8)
If I erase all the io part, I'm able to see the values in console.
If there is another way to mix 2 services in one.. tell me some clues and I'll do the search.
Thanks.

Made it!
2 in 1...
var http = require('http'),
dgram = require('dgram'),
socketio = require('socket.io');
var fs = require('fs');
var app = http.createServer(),
io = socketio.listen(app),
socket = dgram.createSocket('udp4');
var crlf = new Buffer(2);
crlf[0] = 0xD; //CR - Carriage return character
crlf[1] = 0xA; //LF - Line feed character
socket.on('message', function(content, rinfo) {
console.log('got message', content.readUInt16LE(0), 'from', rinfo.address, rinfo.port);
io.sockets.emit('udp message', content.readUInt16LE(0));
});
socket.bind(6000);
app.listen(8000);
On the webpage side:
src="socket.io.min.js"
src="jquery.min.js"
<script>
var socket = io.connect('http://local_host.com:8000');
socket.on('udp message', function(msg) {
console.log(msg) ;
temperature = msg/100;
$('#temperature h1').html(temperature+'°C');
});
</script>
bind/listen newbie issues.

Related

To forward a JSON file to other Address with Express js

Just starting to learn express. Would wish to forward a json file to another location for processing/ingestion that i recieved from a request from webhook using POST url endpoint.
I am planning to pass this json file to a cpp program
I have the following code
var request = require('request'),,
express = require('express'),
path = require('path');
http = require('http');
const port = 5000;
var app = express();
// for json parser
app.use(express.json());
app.post('/gethub', function(req, res) {
console.log("Got response: " + res.statusCode);
console.log("Got header: " + res.getHeaderNames());
console.log("Got status Message: " + res.statusMessage );
var data = req.body;
var name = data.pusher.name;
var node_id = data.sender.node_id;
res.status(200).send(res.json( { name : name,
Nodeid : node_id });
});
var server = app.listen(app.get('port'), function() {
var host = server.address().address
var portid = server.address().port
console.log('App listening at http://%s:%s', host, portid)
console.log("App listening on port " + app.get('port'));
});
THanks for your help
Think of Express as a framework that behaves as a web server. What you really are doing is writing an API listening in the port 5000 in your case. The function seems ok so it will be accesible while making a HTTP request using the POST method.
Express docs about routing

socket.io Updating all the open pages

I am trying to create a chat website, something like a discord clone. I am using socket.io to connect my front end and back-end but I cant figure out how to make it that when someone enters a message that message to be displayed on all currently open browser pages
Server.js (My server file I use):
const express = require("express");
const app = express();
const http = require("http").Server(app);
const port = 4000;
const io = require("socket.io")(http);
app.get("/", (req, res) => {
res.sendFile("ChatRoom.html", {"root": __dirname});
});
io.on("connection", (socket) => {
console.log("A user has connected");
socket.on("messageSend", (data) =>{
console.log(data);
io.emit("chatUpdate", data);
});
});
http.listen(port, () => {
console.log("Server.js listening on port " + port );
});
And my Javascript code in the HTML file:
var socket = io();
document.addEventListener('keydown', InputText);
function InputText(e)
{
//Checks if the pressed button is Enter and if the input box is empty
if( e.keyCode == 13 && document.getElementById("chat_input").value != "")
{
//Gets the div which the message will be ridden to
var parent = document.getElementById("chat");
//Current date to be used when displaying the exact time of sending the
messgae
let d = new Date()//.getTimezoneOffset();
//Getting the properties of the input
var value = document.getElementById("chat_input");
//Telling the server that a message has been sent - function
emitter(parent, value.value, d);
//Setting the text box back to blank
value.value = "";
}
}
//Function
function emitter(holder, text, date){
socket.emit("messageSend", text);
socket.once("chatUpdate", (message) => {
var z = document.createElement("p");
z.innerText = date.getHours() +":"+ date.getMinutes() + " | " +
message;
z.style = 'border-top: 1px solid Black;border-bottom: 1px solid
Black;font-size:20px; margin: 0;padding: 10px;';
holder.appendChild(z);
});
}
Once you have emitted the message you need to be listening for it in the client, if the action you are trying to achieve is sending the message to another user that has the socket currently open on their window. Because you are sending it to a user not the server, so you would need to be connecting to the socket so it's very possible your socket might need to be defined more like this.
var socket = io.connect('Your:/url/of/windowlocation/whileonsocket/here')
Hope this helps!

sensor data is not uploading on artik cloud

I am trying to send sensor data to artik cloud via node.js. (using web socket and serial port). But its sending null. Anyone knows the reason? I just copied the code from tutorial so there is no syntax error.
var webSocketUrl = "wss://api.artik.cloud/v1.1/websocket?ack=true";
var device_id = "####";
var device_token = "#####";
var isWebSocketReady = false;
var ws = null;
var serialport = require("serialport");
var portName = 'COM5';
var sp= new serialport.SerialPort(portName, {
baudRate: 9600,
parser: serialport.parsers.readline("\r\n")
});
var WebSocket = require('ws');
/**
* Gets the current time in millis
*/
function getTimeMillis(){
return parseInt(Date.now().toString());
}
/**
* Create a /websocket bi-directional connection
*/
function start() {
//Create the websocket connection
isWebSocketReady = false;
ws = new WebSocket(webSocketUrl);
ws.on('open', function() {
console.log("Websocket connection is open ....");
register();
});
ws.on('message', function(data, flags) {
console.log("Received message: " + data + '\n');
});
ws.on('close', function() {
console.log("Websocket connection is closed ....");
});
}
/**
* Sends a register message to the websocket and starts the message flooder
*/
function register(){
console.log("Registering device on the websocket connection");
try{
var registerMessage = '{"type":"register", "sdid":"'+device_id+'", "Authorization":"bearer '+device_token+'", "cid":"'+getTimeMillis()+'"}';
console.log('Sending register message ' + registerMessage + '\n');
ws.send(registerMessage, {mask: true});
isWebSocketReady = true;
}
catch (e) {
console.error('Failed to register messages. Error in registering message: ' + e.toString());
}
}
/**
* Send one message to ARTIK Cloud
*/
function sendData(temperature){
try{
// ts = ', "ts": '+getTimeMillis();
var data = {
"temp": temperature
};
var payload = '{"sdid":"'+device_id+'", "data": '+JSON.stringify(data)+', "cid":"'+getTimeMillis()+'"}';
console.log('Sending payload ' + payload);
ws.send(payload, {mask: true});
} catch (e) {
console.error('Error in sending a message: ' + e.toString());
}
}
/**
* All start here
*/
start(); // create websocket connection
sp.on("open", function () {
sp.on('data', function(data) {
if (!isWebSocketReady){
console.log("WebSocket is not ready. Skip sending data to ARTIK Cloud (data:" + data +")");
return;
}
console.log("Serial port received data:" + data);
//var parsedStrs = data.split(",");
var temperature = parseInt(data);
sendData(temperature);
});
});
If you reference our First IoT Sample:
https://developer.artik.cloud/documentation/tutorials/your-first-iot-device.html
The node.js sample sends the value from the temperature sensor. As a dependency it requires a connected Arduino, Raspberry Pi, and a DHT temperature sensor located at the right pin. If you are seeing null "before" sending the data to ARTIK Cloud, you are not getting any value from the sensor.
In particular, output and print to console the "temperature" value from the following function in case of any parsing errors:
function sendData(temperature) //...
Email us at developer#artik.cloud if you need additional information.
Thanks!
In this line:
var temperature = parseInt(data);
If you're getting empty or non numeric data (you can verify this in the previous line where you're logging the variable's content), then temperature will be NaN (not a number). Then, when you build the JSON payload for Artik Cloud, you'll end up with something like:
{
"sdid": "cbd3f844967d464da3c4f4989f80f86c",
"data": {
"temp":null
},
"cid":"1495817841624"
}
Because the JSON.stringify of:
{"temp":NaN}
would be translated to:
{"temp":null}

Parse TCP JSON Stream and emit each object via Socket.io

I am working with a data feed that sends a JSON stream over a TCP socket and I'm using node.js/socket.io to emit the stream to a browser client.
Everything is working except I need each JSON object to emitted as a separate message from the socket.io server. In the client the messages are received like this:
//Message 1:
{"type":"TYPE_1","odds":[{"eventId":"foo","odds":[{"oddId":foo,"oddType":"LIVE","source":"foo"}]}]}
//Message 2:
{"type":"TYPE_2","odds":[{"eventId":"foo","odds":[{"oddId":foo,"oddType":"LIVE","source":"foo"}]}]}
{"type":"TYPE_3","odds":[{"eventId":"foo","odds":[{"oddId":foo,"oddType":"LIVE","source":"foo"}]}]}
//Message 3:
{"type":"TYPE_4","odds":[{"eventId":"foo","od
//Message 4:
ds":[{"oddId":foo,"oddType":"LIVE","source":"foo"}]}]}
The data feed docs state: "All messages sending to your application will form a JSON stream (no delimiter between messages), so you may need a decoder that support JSON stream."
So the stream is strictly correct but I need each object as separate message.
I have looked at https://www.npmjs.com/package/JSONStream and others but am very new to nodejs and socketio and am not sure how to implement them in to the server.
Have also read How can I parse the first JSON object on a stream in JS, nodejs JSON.parse(data_from_TCP_socket), http://www.sebastianseilund.com/json-socket-sending-json-over-tcp-in-node.js-using-sockets.
I think it's something to do with buffer chunk lengths and them being too big so the messages get split but that could be wrong! I'm guessing I need a delimiter check that balances brackets but not sure how to go about it or if the right approach.
My Server Script:
var app = require('express')();
var http = require('http').Server(app);
var io = require('socket.io')(http);
var net = require('net');
var port = 8992; // Datafeed port
var host = '127.0.0.1'; // Datafeed IP address
//Whenever someone connects this gets executed
io.on('connection', function(socket){
console.log('A user connected to me the server');
//Whenever someone disconnects this piece of code executed
socket.on('disconnect', function () {
console.log('A user disconnected');
});
});
//Create a TCP socket to read data from datafeed
var socket = net.createConnection(port, host);
socket.on('error', function(error) {
console.log("Error Connecting");
});
socket.on('connect', function(connect) {
console.log('connection established');
socket.write('{"type":"SUBSCRIBE"}');
});
socket.on('data', function(data) {
//console.log('DATA ' + socket.remoteAddress + ': ' + data);
var data = data.toString();
io.sockets.emit('event', JSON.stringify(data));
});
http.listen(3000, function(){
console.log('listening on *:3000');
});
My Client:
<!DOCTYPE html>
<html>
<head><title>Hello world</title></head>
<script src="https://cdn.socket.io/socket.io-1.4.5.js"></script>
<script src="http://code.jquery.com/jquery-1.11.1.js"></script>
<script>
var socket = io.connect('http://localhost:3000');
</script>
<body>
<form action="">
<input id="m" autocomplete="off" /><button>Send</button>
</form>
<ul id="messages"></ul>
<script>
socket.on('event', function(data){
var t = JSON.parse(data.toString('utf8'));
$('#messages').prepend($('<li>').text(t));
console.log('Got event from Server:', t);
});
</script>
</body>
</html>
Any help or guidance would be amazing as really struggling with this.
A common delimiter to use is a newline character (\n). If you have that appended to your JSON messages it will be very easy to parse the messages. For example:
var sockBuf = '';
socket.setEncoding('utf8');
socket.on('data', function(data) {
sockBuf += data;
var i;
var l = 0;
while ((i = sockBuf.indexOf('\n', l)) !== -1) {
io.sockets.emit('event', sockBuf.slice(l, i));
l = i + 1;
}
if (l)
sockBuf = sockBuf.slice(l);
});
or a more efficient, but slightly less simple solution:
var sockBuf = '';
socket.setEncoding('utf8');
socket.on('data', function(data) {
var i = data.indexOf('\n');
if (i === -1) {
sockBuf += data;
return;
}
io.sockets.emit('event', sockBuf + data.slice(0, i));
var l = i + 1;
while ((i = data.indexOf('\n', l)) !== -1) {
io.sockets.emit('event', data.slice(l, i));
l = i + 1;
}
sockBuf = data.slice(l);
});

How to convert the message in to a json object

I am using a client program called fire packets to fire some hexadecimal data on to a server program in which the server listening on a specified port. The server program works well and it receives the message from the client but need to convert the message into a json object in which results undefined when tried can any one please tell me how to do the conversion of the message into json object. Will attach the server program below,
var dgram = require('dgram');
var server = dgram.createSocket("udp4");
var fs = require('fs');
server.on("error", function(err) {
console.log("Error:" + err.stack);
server.close();
});
server.on("message", function(msg, rinfo) {
console.log("server got the message :" + msg + "from" + rinfo.address + "from the port" + rinfo.port);
fs.writeFile("packet.txt", msg.toString(), 'utf-8', function(err) {
//var jsonmess=JSON.parse(msg);
//console.log(jsonmess);
console.log("written on packet");
});
});
server.on("listening", function() {
var address = server.address();
console.log("Server listening on:" + address.address + "on the port:" + address.port);
});
server.bind(5432);
The message i send to through the client is
4500005100060000801116FB75610CFACF47D1F8501E5014003DD5C383051632426347010101020AC252F131AB52F131AB0776956F2CC65619000002CC0000000000000800005FFF970F07660001080100000032C8
When i stringify the JSON object the data has been shown as
[131,5,22,50,66,99,71,1,1,1,2,10,194,82,241,49,171,82,241,49,171,7,118,149,111,44,198,86,25,0,0,2,204,0,0,0,0,0,0,8,0,0,95,255,151,15,7,102,0,1,8,1,0,0,0,50,200]
How can i get the exact value that has been send through the client on a server json object