【问题标题】:NestJS Typeorm: Run insert operation with multiple repositoriesNestJS Typeorm:使用多个存储库运行插入操作
【发布时间】:2023-02-03 08:13:42
【问题描述】:

我有几个运行 CRUD 操作的 API,例如:

POST /table
POST /chair

并且每个在各自的服务文件中都有自己的存储库实例。以下是表的服务文件的示例代码 -

table.service.ts

// import statements

export class TableService {
  private readonly tableRepository: Repository<TableEntity>;
    constructor(
      @Inject('CONNECTION') private connection: DataSource,
    ) {
      this.tableRepository = connection.getRepository(TableEntity);
    }

  async create(createTableDto: CreateTable) {
    const result = await this.tableRepository.insert({...createTableDto});
    return this.tableRepository.findOneOrFail({where: {id: result.identifiers[0].id}});
  }
}

Chair 的服务文件具有类似的实现。

我有另一个 api,我们称它为 /test,它将通过调用服务文件中的 create 方法对 TableEntityChairEntity 执行插入操作 -

test.service.ts

export class TestService {
  constructor(
    private readonly tableService: TableService,
    private readonly chairService: ChairService,
    @Inject('CONNECTION') private connection: DataSource,
  ) {}

  async create() {
   const tableData = ...;
   const chairData = ...;
   tableService.create(tableData);
   chairService.create(chairData); 
  }

我将如何在交易中运行上述操作?我不能使用DataSource.transaction,因为所有数据库操作都必须使用提供的实体管理器执行,而我不是这种情况。

我可以利用 connection 对象吗?或者我们还有其他的方法吗?

【问题讨论】:

    标签: javascript node.js typescript nestjs typeorm


    【解决方案1】:

    如果您使用的是最新版本的 nestjs 9 和 typeOrm 0.3.11,这就是我完成此操作的方法:

    import { HttpException, Injectable } from '@nestjs/common';
    import { InjectRepository, InjectDataSource } from '@nestjs/typeorm';
    import { Like, Repository, DataSource, EntityManager  } from 'typeorm';
    import { Users } from './entities/users.entity';
    import { UsersRoles } from './entities/users_roles.entity';
    
    @Injectable()
    export class AppService {
        constructor(
            @InjectRepository(Users)
            private usersRepository: Repository<Users>,
            @InjectRepository(UsersRoles)
            private usersRolesRepository: Repository<UsersRoles>,
            @InjectDataSource()
            private dataSource: DataSource,
    ) {}
    
    async createUser(data: any, submit_user: any): Promise<any> {
        try {
            const result = await this.dataSource.manager.transaction(async (entityManager: EntityManager) => {
                const user = new Users();
                user.name = data.name;
                user.email = data.email;
                user.created_at = new Date();
                user.updated_at = new Date();
                await entityManager.save(user);
    
                const userRole = new UsersRoles();
                userRole.users_id = user.id;
                userRole.roles_id = data.role_id;
                userRole.supervisor_id = data.supervisor_id || null;
                userRole.submitted_by = submit_user.id;
                userRole.created_at = new Date();
                userRole.updated_at = new Date();
                await entityManager.save(userRole);
            });
            console.log(result);
            return result;
        } catch (error) {
            throw new HttpException(error, 500);
        }
       }
    }
    

    为了从本质上解释它,您从 TypeORM 注入数据源并将其与事务管理器一起使用,您创建一个回调函数,其中包含您将在内部使用的 entityManager 参数。

    在我的案例中实例化 2 个实体 User 和 User 角色并添加要保存的数据,然后使用该 entityManager 参数执行保存。

    由于您使用的是事务管理器,它应该在失败时为您处理回滚,但需要进行测试以 100% 验证这一点。

    【讨论】:

      猜你喜欢
      • 2020-04-19
      • 1970-01-01
      • 2019-07-05
      • 2021-07-15
      • 2021-11-21
      • 2020-09-01
      • 1970-01-01
      • 2020-04-19
      • 2022-08-05
      相关资源
      最近更新 更多