fix: [nestjs integration] fastify HTTP adapter detection now works correctly for response headers (#938)

* fix: [nestjs integration] fastify HTTP adapter detection now works correctly for response headers

- fixed a bug where Fastify responses were incorrectly processed as Express due to overlapping method names.
- introduced type guards to differentiate between Express and Fastify response objects.
- bumping @trigger.dev/nestjs patch version to 2.3.19

* fix TS type check build error
This commit is contained in:
Eugene Yaroslavtsev
2024-03-22 23:41:21 +09:00
committed by GitHub
parent a49b659701
commit cd8f6b9af0
2 changed files with 43 additions and 9 deletions
+5
View File
@@ -0,0 +1,5 @@
---
"@trigger.dev/nestjs": patch
---
fix: [nestjs integration] fastify HTTP adapter detection now works correctly for response headers
+38 -9
View File
@@ -16,7 +16,7 @@ import {
} from "@nestjs/common";
import { Headers as StandardHeaders, Request as StandardRequest } from "@remix-run/web-fetch";
import { TriggerClient, TriggerClientOptions } from "@trigger.dev/sdk";
import type { Response } from "express";
import type { Response as ExpressResponse } from "express";
import type { FastifyReply } from "fastify";
const { ConfigurableModuleClass, MODULE_OPTIONS_TOKEN, OPTIONS_TYPE, ASYNC_OPTIONS_TYPE } =
@@ -192,15 +192,24 @@ function createControllerByPath(customProvider: InjectionToken, path: string) {
throw new NotFoundException({ error: "Not found" });
}
if (typeof res.status === "function") {
// express
(res as Response).status(response.status);
(res as Response).set(response.headers);
} else if (typeof res.code === "function") {
// fastify
(res as FastifyReply).code(response.status);
/**
* NestJS users mostly use either Express or Fastify, but they have
* different response object APIs, so we need to figure out which one
* is being used and set the status code and headers accordingly.
*/
if (isExpressResponse(res)) {
res.status(response.status);
if (response.headers) {
(res as FastifyReply).headers(response.headers);
// Merges the headers, so no need to iterate over them
res.set(response.headers);
}
} else if (isFastifyReply(res)) {
res.code(response.status);
if (response.headers) {
// Same merge behaviour as Express
res.headers(response.headers);
}
} else {
throw new InternalServerErrorException(
@@ -214,3 +223,23 @@ function createControllerByPath(customProvider: InjectionToken, path: string) {
return TriggerDevController;
}
/**
* Type guard for Express with unique checks
*/
function isExpressResponse(res: unknown): res is ExpressResponse {
return (
typeof (res as ExpressResponse)?.status === "function" &&
typeof (res as ExpressResponse)?.render === "function"
);
}
/**
* Type guard for Fastify with unique checks
*/
function isFastifyReply(res: unknown): res is FastifyReply {
return (
typeof (res as FastifyReply)?.code === "function" &&
typeof (res as FastifyReply)?.headers === "function"
);
}