Skip to content

fix: use @fastify/error for forbidden path errors - #624

Merged
mcollina merged 1 commit into
fastify:mainfrom
SkySails:fix/forbidden-path-fastify-error
Nov 4, 2026
Merged

mcollina merged 1 commit into
fastify:mainfrom
SkySails:fix/forbidden-path-fastify-error

Conversation

@SkySails

@SkySails SkySails commented Nov 2, 2026

Copy link
Copy Markdown
Contributor

Since 10.1.1, @fastify/static rejects forbidden request paths such as //foobar.html or /static/../index.js with a plain Error that has status and statusCode set to 403. Every other error in the plugin uses @fastify/error since #599, so the intention seems clear.

Fastify itself responds to both kinds of errors with a 403, but frameworks that handle Fastify errors themselves may not. NestJS 12.0.2 and later (nestjs/nest#17709) only treat a FastifyError or an http-errors error as an HTTP error. This means that a plain Error with a statusCode (such as this one) becomes a 500 and is logged as an unhandled exception.

This affects NestJS apps that serve files with @fastify/static, including the Swagger UI from @nestjs/swagger.

NestJS app with @fastify/static, GET /static/../index.js Response
@nestjs/core 12.0.1 403
@nestjs/core 12.0.2 … 12.3.2, @fastify/static 10.1.8 500, logged as an error
@nestjs/core 12.3.2, this PR 403

Fix

  • A new FST_STATIC_FORBIDDEN_PATH error (403, message Forbidden) in lib/errors.js following the pattern as #599
  • Return the new error from forbiddenPathError(), replacing the plain error

The default error response gets the same code field as the other errors of the plugin:

-{"statusCode":403,"error":"Forbidden","message":"Forbidden"}
+{"statusCode":403,"code":"FST_STATIC_FORBIDDEN_PATH","error":"Forbidden","message":"Forbidden"}

The error no longer has a status property, like the other @fastify/error errors of the plugin. Nothing in the plugin reads it.

Tests

  • The existing //foobar.html 403 test now also checks for code: 'FST_STATIC_FORBIDDEN_PATH'.
  • The other 403 tests pass unchanged.
  • npm test passes with 100% coverage on Node 20, 22, 24 and 26 on Linux. The type tests and npm run lint pass. There is no benchmark script.

Checklist

@SameRainbows SameRainbows left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Solid improvement and clean alignment with Fastify error conventions.

A few key points verified:

  • Standardizing on @fastify/error ensures frameworks and custom error handlers (like NestJS's HttpException mapper) properly recognize the error code and 403 HTTP status rather than falling back to unhandled 500s.
  • Creating FST_STATIC_FORBIDDEN_PATH in lib/errors.js matches the existing plugin error conventions (#599).
  • Updating forbiddenPathError() simplifies creation while preserving the expected 403 Forbidden response format.
  • JSDoc annotations and README.md error table are cleanly synchronized.
  • Verified test suite passes with full statement and branch coverage, and all 15 CI matrix checks are green. Ready for maintainer merge.

@mcollina mcollina left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Lgtm

@mcollina
mcollina merged commit 3677646 into fastify:main Nov 4, 2026
17 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants