npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2025 – Pkg Stats / Ryan Hefner

fastify-http-exceptions

v1.2.5

Published

A Fastify plugin and core utilities for typed HTTP exceptions and responses.

Readme

fastify-http-exceptions

NPM Package NPM Downloads Tests Coverage

fastify-http-exceptions is a small, opinionated Fastify plugin and core library for typed HTTP exceptions.

It lets you throw HTTP exceptions with structured error payloads in your route handlers and have them automatically converted into proper Fastify responses.
The core utilities are framework‑agnostic; the Fastify plugin was created out of real‑world need to simplify error handling in larger APIs.

Features

  • Typed HTTP exception hierarchy: BadRequestException, UnauthorizedException, ForbiddenException, NotFoundException, and many more.
  • Consistent JSON error bodies: 4xx/5xx errors are serialized as { error: string }.
  • Redirect support: throw TemporaryRedirectException or PermanentRedirectException to drive redirects from your domain logic.
  • Fastify integration: a single plugin wraps Fastify’s error handler and converts exceptions into responses.
  • Core-only helpers: use the exception model without Fastify in other Node.js frameworks.

Runtime requirements: Node.js >= 24 and Fastify ^5.0.0. This is an ESM-only package.

Usage Warning

  • You must configure this plugin ahead of most other plugins, otherwise they may consume the exceptions themselves.

Installation

pnpm add fastify-http-exceptions fastify

Basic Usage with Fastify

Register the plugin once, then throw HTTP exceptions from your routes:

import Fastify from 'fastify';
import { fastifyHttpExceptions } from 'fastify-http-exceptions';
import {
  NotFoundException,
  ForbiddenException,
} from 'fastify-http-exceptions/core';

const app = Fastify();

await app.register(fastifyHttpExceptions, {
  // Optional: log unhandled (non-HTTPException) errors via fastify.log.error
  logUnhandled: true,
});

app.get('/users/:id', async (request, reply) => {
  const id = (request.params as { id: string }).id;

  const user = await findUser(id);
  if (!user) {
    // Will become: 404 + { "error": "user not found" }
    throw new NotFoundException('user');
  }

  if (!canAccessUser(request, user)) {
    // Will become: 403 + { "error": "Access denied to user: missing permission" }
    throw new ForbiddenException('user', 'missing permission');
  }

  return reply.send(user);
});

Redirects from Handlers

You can also throw redirect exceptions and let the plugin turn them into Fastify redirect() calls:

import { TemporaryRedirectException } from 'fastify-http-exceptions/core';

app.get('/old-endpoint', async () => {
  throw new TemporaryRedirectException('/new-endpoint');
});

This results in a redirect response using the appropriate HTTP status code.


Error Response Shape

When an HTTPException (or compatible error) is thrown inside a Fastify route:

  • Redirect exceptions (TemporaryRedirectException, PermanentRedirectException) are translated into Fastify redirects.
  • For 4xx/5xx HTTP error codes, responses are shaped as:
{
  "error": "Human-readable message"
}

The conversion logic is handled by httpExceptionToResponse, which is used internally by the Fastify plugin.


Core-Only Usage (No Fastify)

If you want to reuse the typed HTTP exceptions without the Fastify plugin, import from the core entry:

import {
  HTTPException,
  NotFoundException,
  ForbiddenException,
  httpExceptionToResponse,
  isHTTPException,
} from 'fastify-http-exceptions/core';

function getUserOrThrow(id: string) {
  const user = findUserSync(id);
  if (!user) {
    throw new NotFoundException('user');
  }
  return user;
}

try {
  const user = getUserOrThrow('123');
  // ...
} catch (err) {
  if (isHTTPException(err)) {
    const response = httpExceptionToResponse(err);
    // Integrate with your own HTTP server / framework here
  } else {
    // Fallback: log or convert to 500, etc.
  }
}

This works in any Node.js HTTP framework or even in pure Node HTTP servers.


Fastify Plugin Options

The fastify-http-exceptions plugin accepts a small options object:

  • logUnhandled?: boolean
    • When true, non-HTTPException errors are logged via fastify.log.error before being passed to the original Fastify error handler.
    • Default: false.

Example:

await app.register(fastifyHttpExceptions, {
  logUnhandled: true,
});

Monorepo Layout

This repository is a small monorepo:

  • packages/fastify-http-exceptions: core library and Fastify plugin.
  • demos/basic-example: a demo Fastify app that uses the plugin.

You generally only need the published fastify-http-exceptions package, but the demo and tests live here as reference.


Plugin Development (for Contributors)

If you want to contribute or run the plugin locally:

# from the repo root
pnpm install

# type-check all packages
pnpm tsc

# run Biome checks (format + lint)
pnpm check

# build all packages
pnpm build

To run the demo app:

pnpm dev          # run all dev targets in parallel
pnpm start        # start the basic-example demo

You can also work directly inside the package:

cd packages/fastify-http-exceptions

pnpm tsc         # one-off type-check
pnpm dev         # watch mode
pnpm vitest      # run unit tests

Publishing

IMPORTANT: Always publish via the monorepo root using the release script, not via pnpm publish directly inside the package directory.

From the repository root:

pnpm run release

This will:

  • Build the package.
  • Copy LICENSE and this root README.md into the package’s publish folder.
  • Publish the package to npm with the correct metadata and README.

After publishing, remember to push commits and tags:

git push
git push --tags

Motivation

This plugin was born out of the practical need to standardize HTTP error handling in Fastify APIs:

  • Application code should be able to express failures with simple, typed exceptions.
  • The HTTP layer should consistently return structured JSON responses without repetitive boilerplate.
  • The same exception model should be useful inside and outside of Fastify.

If you have suggestions, issues, or ideas for additional exception helpers, please open an issue or PR.