Reputation: 2951
I am trying to add a custom header to my request, but it must be modified/implemented in the interface.
The default Request
interface references IncomingHttpHeaders
. So I am attempting to extend this interface with my own custom token header.
import { IncomingHttpHeaders } from 'http';
declare module 'express-serve-static-core' {
interface IncomingHttpHeaders {
"XYZ-Token"?: string
}
}
I have updated my .tsconfig
file to read the ./types
folder. The name of my file is index.d.ts
I can successfully compile the code if I do not use my custom header, but when I try to reference the token header in the code I get the following compilation error:
Error
error TS2538: Type 'string[]' cannot be used as an index type.
req.headers['XYZ-Token']
If I use any of the values of the original interface everything works fine.
Example:
req.headers['user-agent']
Additional information: I am using NestJS, which uses Fastify/Express under the hood. I can confirm that the Request interface being used is from Express. Fastify is backwards compatible with all Express modules. Mainly using Fastify because it's faster.
Upvotes: 13
Views: 17749
Reputation: 21
I faced a problem like this recently, and the solution that worked for me was creating a type that extends from IncomingHttpHeaders
import { IncomingHttpHeaders } from "http2";
interface MyCustomsHearders {
foo: "bar";
}
type IncomingCustomHeaders = IncomingHttpHeaders & MyCustomsHearders;
const { foo } = req.headers as IncomingCustomHeaders;
I know it's not quite the most "formal" way to solve the problem, but it worked fine for me.
Upvotes: 0
Reputation: 2951
Looks like the wrong module name is in the declaration.
Even though the IncomingHttpHeaders
interface is being attached to the Request
object from express-serve-static-core
, the original source of the IncomingHttpHeaders
interface is actually part of the http
package.
The following allowed the custom header to be accessible in the code and ts compiled correctly.
import { IncomingHttpHeaders } from 'http';
declare module 'http' {
interface IncomingHttpHeaders {
"XYZ-Token"?: string
}
}
Upvotes: 21
Reputation: 70191
For whatever reason, it thinks the string you are passing in is an array, but besides that point, if you need to set a custom header (and it is not a dynamic value) you can use the @Header()
decorator. If it is dynamic then you can use an interceptor to grab the response pre-flight and set the header there with something like
@Injectable()
export class CustomHeaderInterceptor implements NestInterceptor {
intercept(context: ExecutionContext, next: CallHandler): Observable<any> {
return next
.handle()
.pipe(
tap(() => context.switchToHttp().getResponse().header('XYZ-Token', customValue),
);
}
}
Upvotes: 0