我产生了以下孩子:var spw = spawn('ping', ['-n','10', '127.0.0.1'])我希望在客户端( 浏览器 )上 一个接一个地 而不是整体接收ping结果。
var spw = spawn('ping', ['-n','10', '127.0.0.1'])
到目前为止,我已经尝试过了:
app.get('/path', function(req, res) { ... spw.stdout.on('data', function (data) { var str = data.toString(); res.write(str + "\n"); }); ... }
然后:
... spw.stdout.pipe(res); ...
在这两种情况下,浏览器都将等待10次ping操作,然后将结果整体打印出来。我想让他们一个接一个,如何实现呢?
(客户只是在拨打电话.../path并用console.log记录结果)
.../path
编辑: 尽管我确实相信websockets是实现这一点所必需的,但我只是想知道是否还有其他方法。我看到了几个令人困惑的SO答案,并且博客文章(在这篇文章中,在第一步中,OP将日志发送到浏览器中)没有帮助,因此我决定悬赏一笔以引起注意。
这是使用SSE(服务器发送的事件)的完整示例。这适用于Firefox,也可能适用于Chrome:
var cp = require("child_process"), express = require("express"), app = express(); app.configure(function(){ app.use(express.static(__dirname)); }); app.get('/msg', function(req, res){ res.writeHead(200, { "Content-Type": "text/event-stream", "Cache-control": "no-cache" }); var spw = cp.spawn('ping', ['-c', '100', '127.0.0.1']), str = ""; spw.stdout.on('data', function (data) { str += data.toString(); // just so we can see the server is doing something console.log("data"); // Flush out line by line. var lines = str.split("\n"); for(var i in lines) { if(i == lines.length - 1) { str = lines[i]; } else{ // Note: The double-newline is *required* res.write('data: ' + lines[i] + "\n\n"); } } }); spw.on('close', function (code) { res.end(str); }); spw.stderr.on('data', function (data) { res.end('stderr: ' + data); }); }); app.listen(4000);
和客户端HTML:
<!DOCTYPE Html> <html> <body> <ul id="eventlist"> </ul> <script> var eventList = document.getElementById("eventlist"); var evtSource = new EventSource("http://localhost:4000/msg"); var newElement = document.createElement("li"); newElement.innerHTML = "Messages:"; eventList.appendChild(newElement); evtSource.onmessage = function(e) { console.log("received event"); console.log(e); var newElement = document.createElement("li"); newElement.innerHTML = "message: " + e.data; eventList.appendChild(newElement); }; evtSource.onerror = function(e) { console.log("EventSource failed."); }; console.log(evtSource); </script> </body> </html>
运行node index.js并将您的浏览器指向http://localhost:4000/client.html。请注意,由于我正在运行OSX,因此必须使用“ -c”选项而不是“ -n”。
node index.js
http://localhost:4000/client.html