Node.js › Express & Middleware
How do you write custom Express middleware that needs to perform asynchronous work, like checking a value against a database, before calling next()?
AdvancedAnswer
An async middleware function performs its await-based work and then calls next() to continue the chain, or next(err) to forward an error -- because Express (pre-v5) doesn't automatically catch a rejected promise from an async middleware, any error thrown inside it needs to be explicitly caught and passed to next(err), typically using the same asyncHandler wrapper pattern used for async route handlers.
const asyncHandler = (fn) => (req, res, next) => Promise.resolve(fn(req, res, next)).catch(next);
const checkRateLimit = asyncHandler(async (req, res, next) => {
const requestCount = await redis.incr(`rate:${req.ip}`);
if (requestCount > 100) return res.status(429).json({ error: 'Too many requests' });
next();
});
app.use(checkRateLimit);Real-world example A rate-limiting middleware that queries Redis asynchronously before deciding whether to allow a request through is wrapped in an asyncHandler utility, ensuring that if the Redis call itself fails, the error is properly forwarded to Express's error-handling middleware rather than crashing the process.