網站搜尋

typescript - 我如何在 NestJS 的回應中設定標頭欄位?


我正在嘗試:

    @Post('login')
    async login(@Body() body: AuthDto, @Res() res: Response) {
        const loginResponse = await this.authService.login(body);
        console.log('loginResponse', loginResponse)
        res.headers.set('x-access-token', loginResponse.access_token)
        return loginResponse
    }

但是沒有用。我收到一個錯誤:

TypeError: Cannot read property 'set' of undefined

答案#1

不是最優雅的方式:return res.set({ 'x-access-token': loginResponse.access_token }).json(loginResponse);

我會把這個邏輯分離到一個攔截器中,檢查回應是否對路徑 /login 有效,如果有效,則返回正確的標頭(使用 loginResponse 中的一些值)

import { Controller, Get, Response } from '@nestjs/common';
import { Response as Res } from 'express';
import { AppService } from './app.service';

@Controller()
export class AppController {
  constructor(private readonly appService: AppService) {}

  @Get()
  getHello(@Response() res: Res): Res {
    return res.set({ 'x-access-token': 1 }).json({ hello: 'world' });
  }

  @Get()
  getHelloAlt(@Response() res: Res): Res {
    return res.set({ 'x-access-token': 1 }).json({ hello: 'world' });
  }
}

這是我的工作版本,注意使用的是 Express Response 而不是 Nest.js。

編輯:從 Nest.js/common 導入的類型是一個裝飾器函數,相反,應使用無類型,或從 Express.js 導入 Response。

答案#2

要指定自訂回應標頭,你可以使用 @Header() 裝飾器或特定函式庫的回應物件(並直接呼叫 res.header())。

從 @nestjs/common 套件 匯入 Header。

@Post()
@Header('Cache-Control', 'none')
create() {
  return 'This action adds a new cat';
}

答案#3

我使用攔截器。由於我想在回應的標頭中新增一個欄位以標示我的服務,所以我也將它設為全域攔截器,但你也可以按路由使用它。

response-add-access-token-to-header.interceptor.ts

import { CallHandler, ExecutionContext, Injectable, NestInterceptor } from '@nestjs/common';
import { Observable } from 'rxjs';

import { Response as ExpressResponse } from 'express';

@Injectable()
export class ResponseAddAccessTokenToHeaderInterceptor implements NestInterceptor {
    intercept(context:ExecutionContext, next:CallHandler): Observable<any> {

        const ResponseObj:ExpressResponse = context.switchToHttp().getResponse();
        ResponseObj.setHeader('x-access-token', 'Your Data' );
        return next.handle();
    }
}

要全局添加它,請調整 main.ts:

async function bootstrap() {
    const app = await NestFactory.create(AppModule);
    app.useGlobalInterceptors(new ResponseAddAccessTokenToHeaderInterceptor());
    await app.listen(8080);
}
bootstrap();