19

我正在尝试为我的快速应用程序设置错误处理并遇到以下问题。

我定义了一个错误中间件并将其添加为最后一个中间件:

// error handler
app.use(function(err, req, res, next) {

    console.log('JUST TESTING. ERROR HANLDER HAS BEEN CALLED...');
    next(err);
});

现在我希望每当发生错误时都会调用这个中间件:

app.get('/datenschutz', function(req, res, next){
        return next(new Error('Just testing')); // handle everything here
    });

但是我的中间件永远不会被调用!但是,浏览器确实会显示堆栈跟踪。这似乎有另一个中间件正在捕获此错误并在我对此进行任何处理之前对其进行处理。

问题是我不知道可以在哪里定义这个中间件,因为我有一个非常简单的设置:

// setup ssl for local testing
var
    app = express();

app.
    use(express.static(__dirname + '/public')).
    use(express.bodyParser()).
    use(express.cookieParser());

为什么我的错误处理中间件没有被调用?这种“默认”错误处理发生在哪里?

谢谢!

* 编辑 * 我看到中间件确实在工作。但是,如果我从另一个中间件函数调用它,就会出现这种情况。但是,如果错误发生在定义为快速路由(GET、POST 等)的函数内部,则不会调用它。这很奇怪。如果我将错误中间件添加到路由回调中,它就会起作用:

app.get('/testError', function(req, res, next){
        return next(new Error('Just testing')); // handle everything here
    }, function(err,req,res,next) {
        console.log('This error handler is called!!');
        return next();
    });

* 编辑 2 - 找到可接受的解决方法 ** 我很惊讶它必须以这种方式完成。正如我在 express 中阅读了许多有关错误处理的条目/问题,但从未发现提到过这种可能性。但是,如果在路由回调中发生错误,则常规错误中间件处理程序似乎不会拾取它。您将需要在路由级别定义错误处理程序。

app.all('*', function(err,req,res,next) {
        console.log('This is a global error handler at route level....');
        return next(err);
    });
4

4 回答 4

3

我也遇到了这个问题,但是即使我在app.user(app.router). 事实证明,我已经有一个我不知道的错误处理程序。

具体来说,如果你像我一样使用 express cli 生成一个应用程序,它会自动添加这个:

if ('development' == app.get('env')) {
  app.use(express.errorHandler());
}

对我来说不幸的是,我在我的应用程序中添加了更多中间件,从而掩盖了这个声明,从而阻止了我的自定义错误处理程序被调用。

只需删除它,然后它应该可以正常工作。

在旁注中,我应该提到原始解决方案仍然有效 - 即使使用app.use(express.errorHandler()).

app.all('*', function(err,req,res,next) {
    console.log('This is a global error handler at route level....');
    return next(err);
});
于 2014-02-16T09:08:06.513 回答
3

从 Express 4 文档更新 Express 4 用户的答案。请参阅下面文档中的示例。请注意,app.router已弃用且不再使用。我还添加了一条虚拟路线以使排序清晰:

“在其他 app.use() 和路由调用之后,您最后定义错误处理中间件;例如:

var bodyParser = require('body-parser');

app.use(bodyParser());
app.get('/', function(req, res) {
    res.send('hello world');
})
app.use(function(err, req, res, next) {
  // logic
});

"

于 2015-03-05T05:34:51.847 回答
1

编辑 2 (sabtioagoIT) 有效。但只是对于那些错过它的人,emostar 的解决方案也有效。我知道将错误处理“使用”调用移到最后,但似乎有一个更简单的选项,正如 emoster 所建议的那样,使用 app.router (在错误处理“使用”调用之前)。

于 2013-01-30T13:41:37.857 回答
0

而不是制作

app.get('/datenschutz', function(req, res, next){
        return next(new Error('Just testing')); // handle everything here
    });

你可以安装express-async-errors

只是让

app.get('/datenschutz', function(req, res){
       throw new Error('Just testing');
    });

它按预期工作

于 2020-11-04T16:49:38.950 回答