Как использовать socket.io для отражения изменений одного API в другом API без загрузки? - PullRequest
0 голосов
/ 08 ноября 2019

У меня есть узел API (POST), в котором датчик продолжает отправлять данные в MongoDB. Теперь у меня есть API (GET), который выбирает данные из базы данных и отображается на приборной панели. Чтобы получить непрерывный поток данных, я хочу использовать модуль SOCKET.IO. Но проблема в том, как я могу получить недавно сохраненную запись из БД и показать ее на панели инструментов без перезагрузки страницы. Пожалуйста, посмотрите на мой код.

SERVER.JS

var app = require('express')();
var http = require('http').createServer(app);
var io = require('socket.io')(http);
// and manything like router, middleware, etc...    

io.on('connection', function(socket){
    console.log('a user connected');
});
http.listen(3000, function(){
    console.log('listening on port:3000');
});

ФАЙЛ МАРШРУТОВ

var router = require("express").Router();
router.post("/upload/device/data/:tempId", TemplateController.AddDeviceData); //To insert the data to the DB
router.get("/view/template/device/logs/:tempUniqID", TemplateController.deviceLogs);  //To get the data from DB

ФАЙЛ КОНТРОЛЛЕРА ШАБЛОНА

module.exports={
    AddDeviceData:async function(req, res){ //Controller to post data
       let err, deviceLog;

       [err, deviceLog]=await     
    to(TemplateService.AddDeviceLogs(req.params.tempId, req.body));
        if(err) return res.serverError(err.message);
        if(deviceLog&&deviceLog!==false){
            return res.ok(deviceLog);
        }else{
            res.badRequest("Sorry cannot add Device log data");
        }
    },

    deviceLogs: async function(req, res){ //Controller to fetch data
        let err, logs;
        let deviceId = req.query.device;
        [err, logs]=await to(TemplateService.displayLogs(req.params.tempUniqID, deviceId));
        if(err) return res.serverError(err.message);
        if(logs&&logs!==false){
            return res.ok(logs);
        }else{
            res.badRequest("Sorry cannot add Device log data");
        }
    }
}

ФАЙЛ ОБСЛУЖИВАНИЯ ШАБЛОНОВ

module.exports={
    //Service to post data
    AddDeviceLogs:async function(templateId, payload){
        let err, deviceData;
        payload.template=templateId;
        const myCollection=templateId;

        [err, deviceData]=await to(mongoose.connection.db.collection(myCollection).insert(payload));
        if(err) TE(err.message, true);
        socket.emit('data', deviceData);
        return (deviceData)? deviceData.result:false;
    },

    //Service to get data
    displayLogs:async function(tempUniqID, deviceID){
        let err, respData;

        var Query = (deviceID)? {"template": tempUniqID, "deviceId": deviceID}:{template: tempUniqID};
        [err, respData]=await to(mongoose.connection.db.collection(tempUniqID).find(Query).sort({_id: -1}).limit(20).toArray())
        if(err) {TE(err, true);}
        return (respData)? respData:false;
    }
}

Теперь я хочу получить последние сохраненные данные в GET API, используя сокет, без перезагрузки страницы или без выполнения GETмаршрут-апи. Я не получаю, в каком сервисе я должен использовать событие серверного сокета-emit и как.

1 Ответ

0 голосов
/ 09 ноября 2019

Вы можете запустить node и ваш сокет io в одном и том же порту, в следующем примере используются express и socket.io. Я также создал сенсорный код для представления этого решения:

Вы должны использовать свой файл маршрута следующим образом:

ФАЙЛ МАРШРУТОВ

var router = require("express").Router();
router.post("/upload/device/data/:tempId", TemplateController.AddDeviceData);
router.get("/", function (req, res, next) {
    res.sendFile('C:/Users/user/Desktop/data.html');
})

В MVCу вас будет корневой файл, объявляющий все работы, вы должны отсрочить свой сокет здесь.

Поскольку в вашей кодовой базе каждый раз, когда вы вызываете функцию AddDeviceLogs, она повторно объявляет websocket, а ваш клиент сокетов в html-файле будетотключите, поэтому он работает только в первый раз.

Тогда вы должны объявить его глобальным, например:

server.js

var app = require('express')();
var http = require('http').createServer(app);
var io = require('socket.io')(http);
// and manything like router, middleware, etc...    

io.on('connection', function(socket){
    console.log('a user connected');
});
http.listen(3000, function(){
    console.log('listening on port:3000');
});

ФАЙЛ ОБСЛУЖИВАНИЯ ШАБЛОНОВ

module.exports={
    AddDeviceLogs:async function(templateId, payload){
        let err, deviceData;
        payload.template=templateId;
        const myCollection=templateId;

        io.emit('data', payload)  // emit to all client

        [err, deviceData]=await to(mongoose.connection.db.collection(myCollection).insert(payload));
        if(err) TE(err.message, true);
        return (deviceData)? deviceData.result:false;
    }
}

data.html

<html>
    <head>
        <script src="/socket.io/socket.io.js"></script>
       <script src="https://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.js"></script>
    </head>
    <body>
        <script>
        var socket = io.connect("http://localhost:3000/",{"forceNew": true});
        socket.on('data', function(data){
            if (data) {
                $('#deviceid').text(data.deviceId);
                $('#heat').text(data.heat);
                $('#humidity').text(data.humidity);
            }
        });

        </script>
        <h4>Welcome to socket.io testing program!</h4>
        <div id="deviceid"></div>
        <div id="heat"></div>
        <div id="humidity"></div>
    </body>
</html>
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...