Socket.io is causing the error 'Error: Can't set headers after they are sent.'
Socket.io is causing the error 'Error: Can't set headers after they are sent.'
我正在尝试使用 Angular 2、node.js、express 和 mongo 将节点 Web 应用程序部署到 ibm-cloud。
我的应用程序在不添加 socket.io 要求行的情况下工作正常:
const io = require("socket.io")(server);
但是,每次我尝试添加 socket.io 并执行容器时,控制台记录(针对每个请求):
Error: Can't set headers after they are sent.
at SendStream.headersAlreadySent
(/app/node_modules/send/index.js:390:13)
at SendStream.send (/app/node_modules/send/index.js:618:10)
at onstat (/app/node_modules/send/index.js:730:10)
at FSReqWrap.oncomplete (fs.js:153:5)
Error: Can't set headers after they are sent.
at SendStream.headersAlreadySent
(/app/node_modules/send/index.js:390:13)
at SendStream.send (/app/node_modules/send/index.js:618:10)
at onstat (/app/node_modules/send/index.js:730:10)
at FSReqWrap.oncomplete (fs.js:153:5)
Error: Can't set headers after they are sent.
at SendStream.headersAlreadySent
(/app/node_modules/send/index.js:390:13)
at SendStream.send (/app/node_modules/send/index.js:618:10)
at onstat (/app/node_modules/send/index.js:730:10)
at FSReqWrap.oncomplete (fs.js:153:5)
这是我的代码
// 取消注释以启用 zipkin 跟踪,根据您的网络配置进行定制:
// var appzip = require('appmetrics-zipkin')({
// 主机:'localhost',
//端口:9411,
// 服务名称:'frontend'
// });
require('appmetrics-dash').attach();
require('appmetrics-prometheus').attach();
const appName = require('./../package').name;
const http = require('http');
const express = require('express');
const log4js = require('log4js');
const localConfig = require('./config/local.json');
const path = require('path');
const logger = log4js.getLogger(appName);
logger.level = process.env.LOG_LEVEL || 'info'
const app = express();
const server = http.createServer(app);
const io = require("socket.io")(server);
app.use(log4js.connectLogger(logger, { level: logger.level }));
require('./routers/index')(app, server);
// Add your code here
const bodyParser = require('body-parser');
var cors = require('cors');
const jwt = require("jsonwebtoken");
const { mongoose } = require("./database");
app.use(cors());
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({
extended: true
}));
app.use("/auth", require("./routes/auth.routes"));
app.use(
"/usuarios",
(req, res, next) => {
const bearerHeader = req.headers["authorization"];
if (typeof bearerHeader !== "undefined") {
const bearer = bearerHeader.split(" ");
const bearerToken = bearer[1];
jwt.verify(bearerToken, "loremipsum", (err, authData) => {
if (err) return res.sendStatus(403);
authData.rol == "admin" ? next() : res.sendStatus(403);
return;
});
} else {
res.sendStatus(403);
}
},
require("./routes/usuarios.routes")
);
app.use("/api", (req, res, next) => {
const bearerHeader = req.headers["authorization"];
console.log(bearerHeader);
if (typeof bearerHeader !== "undefined") {
const bearer = bearerHeader.split(" ");
const bearerToken = bearer[1];
jwt.verify(bearerToken, "loremipsum", (err, authData) => {
if (err) return res.sendStatus(403);
req.authData = authData;
next();
});
} else {
res.sendStatus(403);
}
});
app.use("/api/turnos", require("./routes/turns.routes"));
app.use("/api/estado", require("./routes/estados.routes"));
app.use("/api/incidencias", require("./routes/incidencia.routes"));
app.use("/movil/api", require("./routes/movil.data.routes"));
app.use("/movil/estadisticas", require("./routes/cola.routes"));
app.use('/*', (req,res,next) => {
res.sendFile(path.join(__dirname, '../public', 'index.html'));
return;
} )
//end my code
const port = process.env.PORT || localConfig.port;
server.listen(port,'0.0.0.0', function(){
logger.info(`tfgbff listening on http://localhost:${port}/appmetrics-dash`);
logger.info(`OpenAPI (Swagger) spec is available at http://localhost:${port}/swagger/api`);
logger.info(`Swagger UI is available at http://localhost:${port}/explorer`);
});
const turno = require("./controllers/turnos.controller");
const io = require('socket.io')(server);
io.on("connection", socket => {
console.log("conectao!");
turno.nextSubject.subscribe(turnos => {
turnos = turnos.filter(t => t.atendido == false);
const infoTurno = turnos.map(t => {
return {
incidenciaId: t.incidenciaId,
turno: t.turno,
siendoAtendido: t.siendoAtendido
};
});
console.log(infoTurno);
io.emit("socket-turnos", infoTurno);
});
socket.on("disconnect", () => console.log("desconectao!"));
});
// app.use(function (req, res, next) {
// res.sendFile(path.join(__dirname, '../public', '404.html'));
// });
// app.use(function (err, req, res, next) {
// res.sendFile(path.join(__dirname, '../public', '500.html'));
// });
module.exports = server;
非常感谢!
我知道这是旧问题,但我刚刚遇到了完全相同的问题,并且刚刚发现它是由 appmetrics 库引起的。
一旦我弄清楚如何让它工作,我会更新它。
编辑:
OK 设法让它与 appmetrics-dash 一起工作。您需要使用 monitor() 而不是 attach() 并将监视器移动到路线的末尾。我调查了 appmetrics-prometheus,现阶段它只有一个 attach(),所以不能使用:
const dash = require('appmetrics-dash');
const express = require('express');
const history = require('connect-history-api-fallback');
const app = express();
const server = require('http').Server(app);
require('./routers/index')(app, server);
require('./services/index')(app);
// Add your code here
dash.monitor({server});
// catch 404 and forward to error handler
app.use(function(req, res) {
res.status(404).send('Not Found');
});
// error handler
app.use(function(err, req, res) {
res.status(err.status || 500).send('Error');
});
server.listen(env.port, () => {
logger.info(`${env.name} listening on ${env.url}/appmetrics-dash`);
logger.info(`${env.name} listening on ${env.url}`);
});
我正在尝试使用 Angular 2、node.js、express 和 mongo 将节点 Web 应用程序部署到 ibm-cloud。 我的应用程序在不添加 socket.io 要求行的情况下工作正常:
const io = require("socket.io")(server);
但是,每次我尝试添加 socket.io 并执行容器时,控制台记录(针对每个请求):
Error: Can't set headers after they are sent. at SendStream.headersAlreadySent (/app/node_modules/send/index.js:390:13) at SendStream.send (/app/node_modules/send/index.js:618:10) at onstat (/app/node_modules/send/index.js:730:10) at FSReqWrap.oncomplete (fs.js:153:5) Error: Can't set headers after they are sent. at SendStream.headersAlreadySent (/app/node_modules/send/index.js:390:13) at SendStream.send (/app/node_modules/send/index.js:618:10) at onstat (/app/node_modules/send/index.js:730:10) at FSReqWrap.oncomplete (fs.js:153:5) Error: Can't set headers after they are sent. at SendStream.headersAlreadySent (/app/node_modules/send/index.js:390:13) at SendStream.send (/app/node_modules/send/index.js:618:10) at onstat (/app/node_modules/send/index.js:730:10) at FSReqWrap.oncomplete (fs.js:153:5)
这是我的代码 // 取消注释以启用 zipkin 跟踪,根据您的网络配置进行定制: // var appzip = require('appmetrics-zipkin')({ // 主机:'localhost', //端口:9411, // 服务名称:'frontend' // });
require('appmetrics-dash').attach();
require('appmetrics-prometheus').attach();
const appName = require('./../package').name;
const http = require('http');
const express = require('express');
const log4js = require('log4js');
const localConfig = require('./config/local.json');
const path = require('path');
const logger = log4js.getLogger(appName);
logger.level = process.env.LOG_LEVEL || 'info'
const app = express();
const server = http.createServer(app);
const io = require("socket.io")(server);
app.use(log4js.connectLogger(logger, { level: logger.level }));
require('./routers/index')(app, server);
// Add your code here
const bodyParser = require('body-parser');
var cors = require('cors');
const jwt = require("jsonwebtoken");
const { mongoose } = require("./database");
app.use(cors());
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({
extended: true
}));
app.use("/auth", require("./routes/auth.routes"));
app.use(
"/usuarios",
(req, res, next) => {
const bearerHeader = req.headers["authorization"];
if (typeof bearerHeader !== "undefined") {
const bearer = bearerHeader.split(" ");
const bearerToken = bearer[1];
jwt.verify(bearerToken, "loremipsum", (err, authData) => {
if (err) return res.sendStatus(403);
authData.rol == "admin" ? next() : res.sendStatus(403);
return;
});
} else {
res.sendStatus(403);
}
},
require("./routes/usuarios.routes")
);
app.use("/api", (req, res, next) => {
const bearerHeader = req.headers["authorization"];
console.log(bearerHeader);
if (typeof bearerHeader !== "undefined") {
const bearer = bearerHeader.split(" ");
const bearerToken = bearer[1];
jwt.verify(bearerToken, "loremipsum", (err, authData) => {
if (err) return res.sendStatus(403);
req.authData = authData;
next();
});
} else {
res.sendStatus(403);
}
});
app.use("/api/turnos", require("./routes/turns.routes"));
app.use("/api/estado", require("./routes/estados.routes"));
app.use("/api/incidencias", require("./routes/incidencia.routes"));
app.use("/movil/api", require("./routes/movil.data.routes"));
app.use("/movil/estadisticas", require("./routes/cola.routes"));
app.use('/*', (req,res,next) => {
res.sendFile(path.join(__dirname, '../public', 'index.html'));
return;
} )
//end my code
const port = process.env.PORT || localConfig.port;
server.listen(port,'0.0.0.0', function(){
logger.info(`tfgbff listening on http://localhost:${port}/appmetrics-dash`);
logger.info(`OpenAPI (Swagger) spec is available at http://localhost:${port}/swagger/api`);
logger.info(`Swagger UI is available at http://localhost:${port}/explorer`);
});
const turno = require("./controllers/turnos.controller");
const io = require('socket.io')(server);
io.on("connection", socket => {
console.log("conectao!");
turno.nextSubject.subscribe(turnos => {
turnos = turnos.filter(t => t.atendido == false);
const infoTurno = turnos.map(t => {
return {
incidenciaId: t.incidenciaId,
turno: t.turno,
siendoAtendido: t.siendoAtendido
};
});
console.log(infoTurno);
io.emit("socket-turnos", infoTurno);
});
socket.on("disconnect", () => console.log("desconectao!"));
});
// app.use(function (req, res, next) {
// res.sendFile(path.join(__dirname, '../public', '404.html'));
// });
// app.use(function (err, req, res, next) {
// res.sendFile(path.join(__dirname, '../public', '500.html'));
// });
module.exports = server;
非常感谢!
我知道这是旧问题,但我刚刚遇到了完全相同的问题,并且刚刚发现它是由 appmetrics 库引起的。
一旦我弄清楚如何让它工作,我会更新它。
编辑:
OK 设法让它与 appmetrics-dash 一起工作。您需要使用 monitor() 而不是 attach() 并将监视器移动到路线的末尾。我调查了 appmetrics-prometheus,现阶段它只有一个 attach(),所以不能使用:
const dash = require('appmetrics-dash');
const express = require('express');
const history = require('connect-history-api-fallback');
const app = express();
const server = require('http').Server(app);
require('./routers/index')(app, server);
require('./services/index')(app);
// Add your code here
dash.monitor({server});
// catch 404 and forward to error handler
app.use(function(req, res) {
res.status(404).send('Not Found');
});
// error handler
app.use(function(err, req, res) {
res.status(err.status || 500).send('Error');
});
server.listen(env.port, () => {
logger.info(`${env.name} listening on ${env.url}/appmetrics-dash`);
logger.info(`${env.name} listening on ${env.url}`);
});