errors-express
v2.1.0
Published
Central error handling for Express
Readme
Errors for Express
Easy error handling for Express APIs.
Installation
Install together with express
npm i express errors-express[!WARNING] From v2, this plugin is adapted to work with Express v5. For Express v4 compatibility, use v1.
Usage
Import the error handler middleware and place it at the end of the middleware stack. Any error (operational or not) thrown by a controller is handled and sent to the client.
Use the handler with a callback to perform extra actions such as logging. Callback receives the error and the request object.
Use guards to return a custom error response after not found or not allowed methods requests.
import express from 'express';
import errorHandler, { Errors, Guards } from 'errors-express';
const app = express();
app.get('/protected', async (req, res) => {
throw Errors.Unauthorized('You must first sign in');
});
app.all('*splat', Guards.NotFound());
app.use(errorHandler((error, req) => {
console.log(`[${req.method} ${req.url}] ${error.message}`);
}));
app.listen(process.env.PORT || 3000);Errors
The base error class used by the package is HttpError. Send optional error details, useful for providing context to error handling in frontend.
HttpError(statusCode, message, details?)
Details can be a string or an object that contains an error code, message and a free context object
Default errors are provided by the package, just include optional message and details.
import { HttpError, Errors } from 'errors-express';
throw new HttpError(400, 'Invalid request', 'MISSING_PSWD');
throw Errors.NotFound();
throw Errors.Forbidden('You cannot do this');
throw Errors.TooManyRequests('You reached the maximum limit or requests', {
code: 'REQUEST_LIMIT_REACHED';
message: 'You reached the maximum limit or requests';
ctx: {
maxRequests: 5,
retryIn: '1min',
};
});| Error | statusCode | Default message | | --- | --- | --- | | BadRequest | 400 | The request syntax is invalid | | Unauthorized | 401 | The authentication credentials are invalid | | Forbidden | 403 | You are not allowed to use this resource | | NotFound | 404 | This resource does not exist | | MethodNotAllowed | 405 | This method is not allowed for this resource | | Conflict | 409 | There is a conflict with the current state of the resource | | Unprocessable | 422 | The request is unprocessable | | TooManyRequests | 429 | The maximum number of requests has been exceeded | | InternalServer | 500 | An internal server error occurred |
Error Adapters
Use adapters to automatically convert domain or third-party errors into HTTP errors at the handler level, avoiding repetitive try/catch blocks.
import errorHandler, { Errors } from 'errors-express';
import { ZodError } from 'zod';
const zodAdapter = (error: Error) => error instanceof ZodError ? Errors.Unprocessable(error.message) : undefined;
app.use(errorHandler({
adapters: [zodAdapter],
callback: (error, req) => console.log(`[${req.method} ${req.url}] ${error.message}`),
}));Adapters receive any non-HttpError and return an HttpError if they handle it, or undefined to pass to the next adapter. Unhandled errors fall back to a generic 500.
Route Error Wrapper
Use withErrors to create reusable error mappers for route handlers. Define mappings once and apply them to multiple controllers that share the same error types.
import { withErrors, Errors } from 'errors-express';
class UserNotFoundError extends Error {}
class InvalidNameError extends Error {}
const userErrors = withErrors([
[UserNotFoundError, Errors.NotFound('User not found')],
[InvalidNameError, e => Errors.Unprocessable(e.message)],
]);
router.put('/:id', userErrors(async (req, res) => {
// ...
}));
router.delete('/:id', userErrors(async (req, res) => {
// ...
}));Mappings accept either a static HttpError instance or a factory (error: Error) => HttpError for dynamic messages. Unmatched errors pass through to the error handler.
Guards
Guards automatically return an error if none of the previous handlers are called.
import { Guards } from 'errors-express';
app.get('/resource', ResourceController);
app.use(Guards.MethodNotAllowed());
app.use(Guards.NotFound()),Only MethodNotAllowed and NotFound are available.
