Skip to content

Commit 3d2076a

Browse files
committed
feat: transaction interceptor
1 parent bbc9282 commit 3d2076a

File tree

2 files changed

+60
-0
lines changed

2 files changed

+60
-0
lines changed

Diff for: src/common/interceptor/transaction.interceptor.ts

+52
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
import {
2+
CallHandler,
3+
ExecutionContext,
4+
Injectable,
5+
NestInterceptor,
6+
} from '@nestjs/common';
7+
import {
8+
catchError,
9+
finalize,
10+
Observable,
11+
concatMap,
12+
} from 'rxjs';
13+
import { QueryRunner, DataSource } from 'typeorm';
14+
// import { Request } from 'express';
15+
16+
@Injectable()
17+
export class TransactionInterceptor implements NestInterceptor {
18+
constructor(private readonly dataSource: DataSource) {}
19+
20+
async intercept(
21+
context: ExecutionContext,
22+
next: CallHandler<any>,
23+
) : Promise<Observable<any>> {
24+
const request = context.switchToHttp().getRequest();
25+
const queryRunner: QueryRunner = await this.initRunner();
26+
request.queryRunnerManager = queryRunner.manager;
27+
28+
return next.handle().pipe(
29+
concatMap(async (data) => {
30+
await queryRunner.commitTransaction();
31+
console.log('data', data);
32+
return data;
33+
}),
34+
catchError(async (error) => {
35+
console.log('error', error);
36+
await queryRunner.rollbackTransaction();
37+
throw error;
38+
}),
39+
finalize(async () => {
40+
console.log('finalize');
41+
await queryRunner.release();
42+
}),
43+
);
44+
}
45+
46+
private async initRunner(): Promise<QueryRunner> {
47+
const queryRunner: QueryRunner = this.dataSource.createQueryRunner();
48+
await queryRunner.connect();
49+
await queryRunner.startTransaction();
50+
return queryRunner;
51+
}
52+
}

Diff for: src/decorator/transaction.decorator.ts

+8
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
import { ExecutionContext, createParamDecorator } from "@nestjs/common";
2+
3+
export const TransactionManager = createParamDecorator(
4+
(data: unknown, ctx: ExecutionContext) => {
5+
const request = ctx.switchToHttp().getRequest();
6+
return request.queryRunnerManager;
7+
}
8+
)

0 commit comments

Comments
 (0)