Nodejs 请教:nest.js 如何优雅做接口鉴权和转发

发布于 1周前 作者 gougou168 来自 nodejs/Nestjs

Nodejs 请教:nest.js 如何优雅做接口鉴权和转发
背景:后台同时跑了两个服务,php 和 nest ,正在做 php 向 nest 重构的过程,前端通过接口路径区分调用哪个服务的接口,php 接口 v1 后缀,nest 接口 v2 后缀。nginx 配置:部分已经由 nest 重构过的接口流量转发到 nest 服务,未重构的接口代理到 php 服务。
目的:最近想要把接口的鉴权逻辑统一搬到 nest 上,ps:这个鉴权是业务层面的鉴权,不是用户网关鉴权。所以目前的流程是 接口请求统一由 nginx 转发到 nest 服务,nest 服务对接口做鉴权,鉴权不通过的话,nest 直接拦截;鉴权通过的话,转发到 php 服务。

目前尝试了两种方案:
1 、nginx auth_request 模块,php 接口请求全部转发到 nest 提供的一个鉴权接口上,这个鉴权接口和其他部署在 nest 上的业务接口一样走全局鉴权守卫。 问题:post 类型的接口由 auth_request 做了转发会丢失请求体,但是做权限判断的时候需要拿请求体的参数来做权限校验,找了一圈解决方法,就是 lua 脚本读取请求体,然后添加到 header 中进行转发,感觉这种做法又复杂又怪。
2 、php 接口转发到 nest ,nest 使用代理中间件 proxy 转发。问题:nest 只重构了部分接口,大部分 php 接口在 nest 里没有定义,转发到 nest 的话这些接口需要定义一遍。目前也没有找到 node 有代理中间件转发到 php-fpm

请教大佬有没有啥好的解决方法,或者相关的文章可以看看的


2 回复

直接在 PHP 里把验权请求 nest,通过了再走下面的业务?


在NestJS中实现接口鉴权和转发,可以通过使用中间件(Middleware)、守卫(Guard)和拦截器(Interceptor)来实现优雅的设计。下面是一个基本的示例,展示如何使用这些特性:

1. 安装依赖

首先,确保你已经安装了必要的依赖:

npm install @nestjs/passport passport passport-jwt @nestjs/jwt

2. 配置JWT

auth.module.ts中配置JWT模块:

import { Module } from '@nestjs/common';
import { JwtModule } from '@nestjs/jwt';
import { PassportModule } from '@nestjs/passport';
import { JwtStrategy } from './jwt.strategy';

@Module({
  imports: [
    PassportModule,
    JwtModule.register({
      secret: 'your-secret-key',
      signOptions: { expiresIn: '60m' },
    }),
  ],
  providers: [JwtStrategy],
  exports: [PassportModule],
})
export class AuthModule {}

3. 创建守卫

创建一个JWT守卫来验证请求:

import { Injectable, CanActivate, ExecutionContext } from '@nestjs/common';
import { AuthGuard } from '@nestjs/passport';

@Injectable()
export class JwtAuthGuard extends AuthGuard('jwt') {}

4. 应用守卫和转发请求

在控制器中使用守卫,并通过服务转发请求:

import { Controller, Get, UseGuards } from '@nestjs/common';
import { JwtAuthGuard } from './jwt-auth.guard';

@Controller('protected')
@UseGuards(JwtAuthGuard)
export class ProtectedController {
  @Get()
  findAll() {
    // 你可以在这里添加转发逻辑
    return { message: 'This route is protected' };
  }
}

这种方式使得鉴权和转发逻辑清晰且模块化,易于维护和扩展。

回到顶部