UnauthorizedException 作为内部服务器错误交付

UnauthorizedException is deliver as Internal Server Error

我正在尝试创建一个共享 Guard 作为外部库,以便跨服务导入和使用。 what is described in some guides 我没有做任何特别的事情,但代码将驻留在共享库中的特殊性。一切正常,但 return 异常是 401 错误。

我的守卫看起来像这样:

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

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

没有别的。如果我在服务文件夹中使用它,它会起作用,但当我在他们自己的库中移动时,响应会发生变化。

我在服务中使用的方式没有什么特别的:

import { MainGuard } from 'shared-guard-library';
import { Controller, Get, UseGuards } from '@nestjs/common';
import { SomeService } from './some.service';

@Controller()
export class SomeController {
  constructor(private someService: SomeService) {}

  @Get('/foo')
  @UseGuards(MainGuard)
  async getSomething(): Promise<any> {
    return this.someService.getSomething();
  }
}

客户端收到错误500:

http :3010/foo
HTTP/1.1 500 Internal Server Error
Connection: keep-alive
Content-Length: 52
Content-Type: application/json; charset=utf-8
Date: Thu, 09 Dec 2021 04:11:42 GMT
ETag: W/"34-rlKccw1E+/fV8niQk4oFitDfPro"
Keep-Alive: timeout=5
Vary: Origin
X-Powered-By: Express

{
    "message": "Internal server error",
    "statusCode": 500
}

并且在日志中显示:

[Nest] 93664  - 12/08/2021, 10:11:42 PM   ERROR [ExceptionsHandler] Unauthorized
UnauthorizedException: Unauthorized
    at MainGuard.handleRequest (/sharedGuardLibrary/node_modules/@nestjs/passport/dist/auth.guard.js:68:30)
    at /sharedGuardLibrary/node_modules/@nestjs/passport/dist/auth.guard.js:49:128
    at /sharedGuardLibrary/node_modules/@nestjs/passport/dist/auth.guard.js:86:24
    at allFailed (/sharedGuardLibrary/node_modules/passport/lib/middleware/authenticate.js:101:18)
    at attempt (/sharedGuardLibrary/node_modules/passport/lib/middleware/authenticate.js:174:28)
    at Object.strategy.fail (/sharedGuardLibrary/node_modules/passport/lib/middleware/authenticate.js:296:9)
    at Object.JwtStrategy.authenticate (/sharedGuardLibrary/node_modules/passport-jwt/lib/strategy.js:96:21)
    at attempt (/sharedGuardLibrary/node_modules/passport/lib/middleware/authenticate.js:360:16)
    at authenticate (/sharedGuardLibrary/node_modules/passport/lib/middleware/authenticate.js:361:7)
    at /sharedGuardLibrary/node_modules/@nestjs/passport/dist/auth.guard.js:91:3

日志告诉我抛出了正确的异常,但在某些时候被忽略了,我不知道原因。再次说明:同一项目中的相同代码有效。

我看了一下原来的class和I don't see any particular way to treat the exception

如有任何线索或指导,我们将不胜感激。

所以,这恰好是 Typescript 的一个“特性”,也是 JavaScript 对象相等性的一般工作方式。所以在 Nest 的 BaseExceptionFilter 中有一个检查 exception instanceof HttpException,通常,UnauthorizedException 将是这个的一个实例,但是因为这是一个库,所以需要考虑一些事情。

  1. 您正在使用的所有 NestJS 依赖项peerDependencies。这确保了在安装库时,@nestjs/* 包只有一个结果包。

  2. 在本地开发期间,您需要注意确保您没有解析同一包的多个实例(即使它是完全相同的版本,JavaScript { hello: 'world' } === { hello: 'world' } // false)。为了解决这个问题,像 npm/yarn/pnpm link 这样的东西应该 而不是 被使用,而是你应该将 distpackage.json 复制到主应用程序的node_modules/<package_name> 目录。

    一个。另一种选择是使用像 Nest's monorepo approach or Nx 这样的 monorepo 工具,它具有单一包版本方法,并使用库的路径而不是内部链接。

如果您按照此操作,当您的生产应用程序安装 npm 库时,一切都会正常运行。这当然很烦人,但这是 JavaScript 工作方式的副作用