import type { ITransactionManager } from "@erp/core/api"; import type { UniqueID } from "@repo/rdx-ddd"; import { Result } from "@repo/rdx-utils"; import type { ICreateSupplierInputMapper } from "../mappers"; import type { ISupplierCreator } from "../services"; import type { ISupplierFullSnapshotBuilder } from "../snapshot-builders"; import type { CreateSupplierCommand } from "./create-supplier.command"; type CreateSupplierUseCaseInput = { companyId: UniqueID; command: CreateSupplierCommand; }; type CreateSupplierUseCaseDeps = { dtoMapper: ICreateSupplierInputMapper; creator: ISupplierCreator; fullSnapshotBuilder: ISupplierFullSnapshotBuilder; transactionManager: ITransactionManager; }; export class CreateSupplierUseCase { private readonly dtoMapper: ICreateSupplierInputMapper; private readonly creator: ISupplierCreator; private readonly fullSnapshotBuilder: ISupplierFullSnapshotBuilder; private readonly transactionManager: ITransactionManager; constructor(deps: CreateSupplierUseCaseDeps) { this.dtoMapper = deps.dtoMapper; this.creator = deps.creator; this.fullSnapshotBuilder = deps.fullSnapshotBuilder; this.transactionManager = deps.transactionManager; } public execute(params: CreateSupplierUseCaseInput) { const { command, companyId } = params; const mappedPropsResult = this.dtoMapper.map(command, { companyId }); if (mappedPropsResult.isFailure) { return mappedPropsResult; } const { props, id } = mappedPropsResult.data; return this.transactionManager.complete(async (transaction: unknown) => { try { const createResult = await this.creator.create({ companyId, id, props, transaction }); if (createResult.isFailure) { return createResult; } const newSupplier = createResult.data; const snapshot = this.fullSnapshotBuilder.toOutput(newSupplier); return Result.ok(snapshot); } catch (error: unknown) { return Result.fail(error as Error); } }); } }