首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Prisma交易交叉模

Prisma交易交叉模
EN

Stack Overflow用户
提问于 2022-11-21 09:01:05
回答 2查看 72关注 0票数 0

问题

我试图用DDD架构实现干净的prisma事务架构。我的问题是,我希望能够跨不同模块执行transactions,而不需要将prisma事务客户端传递给每个存储库,即:

代码语言:javascript
复制
// repository layer
@injectable()
export class UserRepository{
  constructor(@inject(PrismaClient) private prisma: PrismaClient)

  save(user: IUser): Promise<User>{
     return this.prisma.user.create({data: user});
  }
}

@injectable()
export class OrderRepository{
  constructor(@inject(PrismaClient) private prisma: PrismaClient)
  
  save(order: IOrder): Promise<Order>{
    return this.prisma.order.create({data: order});
  }
}
代码语言:javascript
复制
// service layer
export class UserService{
  constructor(@inject(UserRepository) private userRepo: UserRepository)

  create(request: CreateUserRequest){
    return this.userRepo.save(request);
  }
}

export class OrderService{
  constructor(@inject(OrderRepository) private orderRepo: OrderRepository)
  
  create(request: CreateOrderRequest){
    return this.orderRepo.save(request);
  }
}
代码语言:javascript
复制
// controller layer
export UserController{
   constructor(
    @inject(UserService) private userService: UserService,
    @inject(OrderService) private orderService: OrderService
   ){}

  placeOrder(
    userRequest: CreateUserRequest,
    orderRequest: CreateOrderRequest
  ){
    // perform transaction, if any fails go with rollback
    // !THIS ACTUALLY DOESN'T WORK
    prisma.$transaction([
       await this.userService.create(userRequest),
       await this.orderService.create(orderRequest)
    ])
  }
}

我想找出一个干净的方法来实现这一点,以前有没有人遇到过类似的问题?

谢谢大家!

EN

回答 2

Stack Overflow用户

发布于 2022-12-01 16:59:54

您的UserRepository.saveOrderRepository.save应该返回PrismaPromises而不是Promise(https://www.prisma.io/docs/concepts/components/prisma-client/transactions#the-transaction-api)

此外,当您await UserRepository.save返回的承诺时,您传递的是一个User,而不是$transaction所期望的PrismaPromise<User>

要修复它,请按照上面的注释从存储库方法中修复输入,然后您应该能够通过倒转等待的顺序来完成事务:

代码语言:javascript
复制
await prisma.$transaction([
   this.userService.create(userRequest),
   this.orderService.create(orderRequest)
])
票数 0
EN

Stack Overflow用户

发布于 2022-12-02 23:18:03

为此,您可以使用一个类型库,其中包括一个事务装饰器,它可以用于在单个事务中包装多个查询。或者,您可以在每个存储库中使用本机prisma事务客户端。这将涉及在需要使用事务客户端时将其传递给每个存储库。例如:

代码语言:javascript
复制
// repository layer
@injectable()
export class UserRepository{
  constructor(@inject(PrismaClient) private prisma: PrismaClient)
  save(user: IUser, transactionClient: Prisma.TransactionClient): Promise<User>{
     return this.prisma.user.create({data: user}, {transaction: transactionClient});
  }
}

@injectable()
export class OrderRepository{
  constructor(@inject(PrismaClient) private prisma: PrismaClient)
  
  save(order: IOrder, transactionClient: Prisma.TransactionClient): Promise<Order>{
    return this.prisma.order.create({data: order}, {transaction: transactionClient});
  }
}
// service layer
export class UserService{
  constructor(@inject(UserRepository) private userRepo: UserRepository)

  create(request: CreateUserRequest, transactionClient: Prisma.TransactionClient){
    return this.userRepo.save(request, transactionClient);
  }
}

export class OrderService{
  constructor(@inject(OrderRepository) private orderRepo: OrderRepository)
  
  create(request: CreateOrderRequest, transactionClient: Prisma.TransactionClient){
    return this.orderRepo.save(request, transactionClient);
  }
}
// controller layer
export UserController{
   constructor(
    @inject(UserService) private userService: UserService,
    @inject(OrderService) private orderService: OrderService
   ){}

  placeOrder(
    userRequest: CreateUserRequest,
    orderRequest: CreateOrderRequest
  ){
    // create the transaction client
    const transactionClient = this.prisma.transaction();
    // perform transaction, if any fails go with rollback
    this.prisma.$transaction([
       await this.userService.create(userRequest, transactionClient),
       await this.orderService.create(orderRequest, transactionClient)
    ])
  }
}
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/74516388

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档