Add branches management module with database schema and validation

- Introduced `BranchesModule` to manage organizational branches, including read and write controllers.
- Created database migrations for the `branches` table, including constraints and unique indexes.
- Implemented validation for branch fields such as name, code, and address with corresponding utility functions.
- Developed service and repository layers for handling branch data operations.
- Added unit tests for the branches service, repository, and controllers to ensure functionality and correctness.
- Updated application module to include the new `BranchesModule` for better organization.
This commit is contained in:
shancheas
2026-08-24 13:42:19 +07:00
parent a8faea20ff
commit d28506e878
22 changed files with 3686 additions and 13 deletions
@@ -189,12 +189,16 @@ export class DivisionsRepository {
}
async delete(id: string): Promise<void> {
const deleted = await this.db
.delete(divisions)
.where(eq(divisions.id, id))
.returning({ id: divisions.id });
if (deleted.length === 0) {
throw new NotFoundException('Division not found');
try {
const deleted = await this.db
.delete(divisions)
.where(eq(divisions.id, id))
.returning({ id: divisions.id });
if (deleted.length === 0) {
throw new NotFoundException('Division not found');
}
} catch (error) {
this.rethrowForeignKeyViolation(error);
}
}
@@ -202,11 +206,15 @@ export class DivisionsRepository {
if (ids.length === 0) {
return 0;
}
const deleted = await this.db
.delete(divisions)
.where(inArray(divisions.id, ids))
.returning({ id: divisions.id });
return deleted.length;
try {
const deleted = await this.db
.delete(divisions)
.where(inArray(divisions.id, ids))
.returning({ id: divisions.id });
return deleted.length;
} catch (error) {
this.rethrowForeignKeyViolation(error);
}
}
private buildListWhere(filters: ListDivisionsFilters): SQL | undefined {
@@ -255,4 +263,12 @@ export class DivisionsRepository {
}
throw error;
}
private rethrowForeignKeyViolation(error: unknown): never {
const err = error as { code?: string };
if (err.code === '23503') {
throw new ConflictException('Division is referenced by other records');
}
throw error;
}
}