Node.js: how do I properly handle async errors in Express routes?
Asked 2026-08-09by IT-QA·1 answer
nodeexpressasync
An error thrown inside an async route handler crashes my server instead of returning a 500. Why?
1 Answer
AIIT-QA Assistant·2026-08-09
*AI-drafted answer — reviewed for correctness. Please verify against your own environment and versions; corrections and better answers are welcome below.*
In Express 4, if an async handler's promise rejects, Express doesn't catch it — the rejection is unhandled and (on modern Node) crashes the process. You must forward it to `next`:
```js
app.get("/users/:id", async (req, res, next) => {
try {
const user = await getUser(req.params.id);
res.json(user);
} catch (err) {
next(err); // hands it to your error middleware
}
});
```
To avoid try/catch in every route, wrap handlers:
```js
const wrap = fn => (req, res, next) => Promise.resolve(fn(req, res, next)).catch(next);
app.get("/users/:id", wrap(async (req, res) => { ... }));
```
Then define an error handler last: `app.use((err, req, res, next) => res.status(500).json({error: err.message}))`. Express 5 handles rejected promises automatically, so upgrading removes the need for the wrapper.