使用 Prisma 2 和 NestJS 进行日志记录 - 依赖注入问题?
Posted
技术标签:
【中文标题】使用 Prisma 2 和 NestJS 进行日志记录 - 依赖注入问题?【英文标题】:Logging with Prisma 2 and NestJS - Dependency Injection problem? 【发布时间】:2021-08-03 03:28:17 【问题描述】:目前在我的第一个 NestJS 项目中。我正在使用 Prisma 2,并希望以调试模式将查询记录到控制台,以学习和检查并避免 n+1 等!
我创建了prisma.service.ts
:
import Injectable, OnModuleInit, OnModuleDestroy from '@nestjs/common'
import PrismaClient from '@prisma/client'
@Injectable()
export class PrismaService extends PrismaClient implements OnModuleInit, OnModuleDestroy
constructor()
super();
async onModuleInit()
await this.$connect()
async onModuleDestroy()
await this.$disconnect()
工作正常,我可以在 API 中使用它并访问数据库。但是,根据Logging 上的 Prisma 2 Docs,我需要通过
import PrismaClient from '@prisma/client'
const prisma = new PrismaClient(
log: [
level: 'warn', emit: 'event' ,
level: 'info', emit: 'event' ,
level: 'error', emit: 'event' ,
],
然后像这样使用它:
@Injectable()
export class TestService
constructor(private prismaService: PrismaService)
this.prismaService.$on('query', e =>
console.log("Query: " + e.query)
console.log("Duration: " + e.duration + "ms")
)
很遗憾,编译时出现以下错误:
TSError: ⨯ Unable to compile TypeScript:
src/test.service.ts:9:31 - error TS2345: Argument of type '"query"' is not assignable to parameter of type '"beforeExit"'.
9 this.prismaService.$on('query', e =>
~~~~~~~
src/test.service.ts:10:39 - error TS2339: Property 'query' does not exist on type '() => Promise<void>'.
10 console.log("Query: " + e.query)
~~~~~
src/test.service.ts:11:42 - error TS2339: Property 'duration' does not exist on type '() => Promise<void>'.
11 console.log("Duration: " + e.duration + "ms")
我尝试将log
数组传递到服务中的super()
,但没有任何运气。
我只是错过了一些小东西吗?
【问题讨论】:
【参考方案1】:嘿兄弟,我一直在使用 prima 2 + nestjs,我将配置 prima 放在父级的 super 中,就像这样。它对我产生了奇迹。
希望对你有帮助;)
这是我的 prismaService.ts
prisma.service.ts
import INestApplication, Injectable, OnModuleInit from '@nestjs/common';
import PrismaClient from '@prisma/client';
@Injectable()
export class PrismaService extends PrismaClient implements OnModuleInit
constructor()
super(
log: [
emit: 'event', level: 'query' ,
emit: 'stdout', level: 'info' ,
emit: 'stdout', level: 'warn' ,
emit: 'stdout', level: 'error' ,
],
errorFormat: 'colorless',
);
async onModuleInit()
await this.$connect();
async enableShutdownHooks(app: INestApplication)
this.$on('beforeExit', async (event) =>
console.log(event.name);
await app.close();
);
@Injectable()
export class TestService
constructor(private prismaService: PrismaService)
prismaService.$on<any>('query', (event: Prisma.QueryEvent) =>
console.log('Query: ' + event.query);
console.log('Duration: ' + event.duration + 'ms');
);
Ps:我不得不删除 dist 文件夹并再次运行。
【讨论】:
【参考方案2】:看起来像是 Prisma 客户端类型的问题。我建议你在 Prisma Github repo 上打开一个问题。在此之前,您需要通过转换为 any
或 unknown
来忽略提供的类型
【讨论】:
【参考方案3】:我使用了这个基于 Prisma GitHub 问题的解决方案。
@Injectable()
export class TestService
constructor(
private prismaService: PrismaClient<Prisma.PrismaClientOptions, 'query'>,
)
this.prismaService.$on('query', (e) =>
console.log('Query: ' + e.query);
console.log('Duration: ' + e.duration + 'ms');
);
【讨论】:
【参考方案4】:您可以在PrismaClient
泛型中指定您想要的事件。
@Injectable()
export class PrismaService extends PrismaClient<Prisma.PrismaClientOptions, 'query' | 'error'> implements OnModuleInit
private readonly logger = new Logger(PrismaService.name);
constructor()
super(
log: [
emit: 'event',
level: 'query',
,
emit: 'event',
level: 'error',
,
emit: 'stdout',
level: 'info',
,
emit: 'stdout',
level: 'warn',
,
],
);
async onModuleInit()
this.$on('error', (event) =>
this.logger.verbose(event.target);
);
await this.$connect();
async enableShutdownHooks(app: INestApplication)
this.$on('beforeExit', async () =>
await app.close();
);
【讨论】:
以上是关于使用 Prisma 2 和 NestJS 进行日志记录 - 依赖注入问题?的主要内容,如果未能解决你的问题,请参考以下文章
NestJS 中与 GraphQL 的 Prisma 自关系
NestJS-Prisma,如何编写与 prisma 一对多类型匹配的 DTO
在没有实际访问数据库的情况下测试使用 Prisma 的 NestJS 服务
Docker 中的 NestJS 无法在另一个 Docker 容器中的 Postgres 上执行 Prisma Migrate