-
Notifications
You must be signed in to change notification settings - Fork 4
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
resync old convention business logic
- Loading branch information
Showing
10 changed files
with
736 additions
and
2 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
39 changes: 39 additions & 0 deletions
39
back/src/adapters/secondary/InMemoryConventionToSyncRepository.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,39 @@ | ||
import { ConventionId } from "shared"; | ||
import { | ||
ConventionToSync, | ||
ConventionToSyncRepository, | ||
} from "../../domain/convention/ports/ConventionToSyncRepository"; | ||
|
||
export class InMemoryConventionToSyncRepository | ||
implements ConventionToSyncRepository | ||
{ | ||
public async getById( | ||
id: ConventionId, | ||
): Promise<ConventionToSync | undefined> { | ||
return this.conventionsToSync.find((convention) => convention.id === id); | ||
} | ||
|
||
public async getNotProcessedAndErrored( | ||
limit: number, | ||
): Promise<ConventionToSync[]> { | ||
return this.conventionsToSync | ||
.filter(({ status }) => status === "ERROR" || status === "TO_PROCESS") | ||
.slice(0, limit); | ||
} | ||
|
||
public async save(conventionToSync: ConventionToSync): Promise<void> { | ||
const index = this.conventionsToSync.findIndex( | ||
(convention) => convention.id === conventionToSync.id, | ||
); | ||
index === -1 | ||
? this.conventionsToSync.push(conventionToSync) | ||
: (this.conventionsToSync[index] = conventionToSync); | ||
} | ||
|
||
// for testing purpose | ||
public setForTesting(conventions: ConventionToSync[]) { | ||
this.conventionsToSync = conventions; | ||
} | ||
|
||
public conventionsToSync: ConventionToSync[] = []; | ||
} |
21 changes: 21 additions & 0 deletions
21
back/src/adapters/secondary/pg/PgConventionToSyncRepository.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,21 @@ | ||
import { ConventionId } from "shared"; | ||
import { | ||
ConventionToSync, | ||
ConventionToSyncRepository, | ||
} from "../../../domain/convention/ports/ConventionToSyncRepository"; | ||
|
||
export class PgConventionToSyncRepository | ||
implements ConventionToSyncRepository | ||
{ | ||
getNotProcessedAndErrored(): Promise<ConventionToSync[]> { | ||
return Promise.resolve([]); | ||
} | ||
|
||
save(_filledConvention: ConventionToSync): Promise<void> { | ||
return Promise.resolve(undefined); | ||
} | ||
|
||
getById(_id: ConventionId): Promise<ConventionToSync | undefined> { | ||
return Promise.resolve(undefined); | ||
} | ||
} |
32 changes: 32 additions & 0 deletions
32
back/src/domain/convention/ports/ConventionToSyncRepository.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,32 @@ | ||
import { ConventionId } from "shared"; | ||
|
||
export type ConventionToSync = | ||
| { | ||
id: ConventionId; | ||
status: "TO_PROCESS"; | ||
} | ||
| { | ||
id: ConventionId; | ||
status: "SUCCESS"; | ||
processDate: Date; | ||
} | ||
| { | ||
id: ConventionId; | ||
status: "ERROR"; | ||
processDate: Date; | ||
reason: string; | ||
} | ||
| { | ||
id: ConventionId; | ||
status: "SKIP"; | ||
processDate: Date; | ||
reason: string; | ||
}; | ||
|
||
export interface ConventionToSyncRepository { | ||
getById(id: ConventionId): Promise<ConventionToSync | undefined>; | ||
|
||
getNotProcessedAndErrored(limit: number): Promise<ConventionToSync[]>; | ||
|
||
save(filledConvention: ConventionToSync): Promise<void>; | ||
} |
140 changes: 140 additions & 0 deletions
140
back/src/domain/convention/useCases/ResyncOldConventionsToPe.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,140 @@ | ||
import { z } from "zod"; | ||
import { ConventionId } from "shared"; | ||
import { NotFoundError } from "../../../adapters/primary/helpers/httpErrors"; | ||
import { TimeGateway } from "../../core/ports/TimeGateway"; | ||
import { UnitOfWork, UnitOfWorkPerformer } from "../../core/ports/UnitOfWork"; | ||
import { TransactionalUseCase } from "../../core/UseCase"; | ||
import { ConventionToSync } from "../ports/ConventionToSyncRepository"; | ||
import { PoleEmploiGateway } from "../ports/PoleEmploiGateway"; | ||
import { BroadcastToPoleEmploiOnConventionUpdates } from "./broadcast/BroadcastToPoleEmploiOnConventionUpdates"; | ||
|
||
type ResyncOldConventionToPeReport = { | ||
success: number; | ||
skips: Record<ConventionId, string>; | ||
errors: Record<ConventionId, Error>; | ||
}; | ||
|
||
export class ResyncOldConventionToPe extends TransactionalUseCase< | ||
void, | ||
ResyncOldConventionToPeReport | ||
> { | ||
constructor( | ||
private uowPerform: UnitOfWorkPerformer, | ||
private poleEmploiGateway: PoleEmploiGateway, | ||
private timeGateway: TimeGateway, | ||
private limit: number, | ||
) { | ||
super(uowPerform); | ||
} | ||
|
||
protected override inputSchema = z.void(); | ||
|
||
public async _execute( | ||
_: void, | ||
uow: UnitOfWork, | ||
): Promise<ResyncOldConventionToPeReport> { | ||
const conventionsToSync = | ||
await uow.conventionToSyncRepository.getNotProcessedAndErrored( | ||
this.limit, | ||
); | ||
await Promise.all( | ||
conventionsToSync.map((conventionToSync) => | ||
this.handleConventionToSync(uow, conventionToSync), | ||
), | ||
); | ||
|
||
return this.report; | ||
} | ||
|
||
private async handleConventionToSync( | ||
uow: UnitOfWork, | ||
conventionToSync: ConventionToSync, | ||
) { | ||
try { | ||
await this.resync(uow, conventionToSync); | ||
const updatedConventionToSync = | ||
await uow.conventionToSyncRepository.getById(conventionToSync.id); | ||
if (updatedConventionToSync === undefined) { | ||
this.report.errors[conventionToSync.id] = new Error( | ||
"Convention not found or no status", | ||
); | ||
return; | ||
} | ||
if (updatedConventionToSync.status === "TO_PROCESS") { | ||
this.report.errors[conventionToSync.id] = new Error( | ||
"Convention still have status TO_PROCESS", | ||
); | ||
} | ||
if (updatedConventionToSync.status === "SUCCESS") | ||
this.report.success += 1; | ||
if (updatedConventionToSync.status === "SKIP") { | ||
this.report.skips[conventionToSync.id] = updatedConventionToSync.reason; | ||
} | ||
if (updatedConventionToSync.status === "ERROR") { | ||
this.report.errors[conventionToSync.id] = new Error( | ||
updatedConventionToSync.reason, | ||
); | ||
} | ||
// const strategy: { | ||
// [K in ConventionToSync["status"]]: ( | ||
// conventionCase: Extract<ConventionToSync, { status: K }>, | ||
// ) => void; | ||
// } = { | ||
// SUCCESS: () => { | ||
// this.report.success += 1; | ||
// }, | ||
// TO_PROCESS: () => { | ||
// this.report.errors[conventionToSync.id] = new Error( | ||
// "Convention still have status TO_PROCESS", | ||
// ); | ||
// }, | ||
// SKIP: (conventionCase) => { | ||
// this.report.skips[conventionToSync.id] = conventionCase.reason; | ||
// }, | ||
// ERROR: (conventionCase) => { | ||
// this.report.errors[conventionToSync.id] = new Error( | ||
// conventionCase.reason, | ||
// ); | ||
// }, | ||
// }; | ||
// strategy[updatedConventionToSync.status](updatedConventionToSync); | ||
} catch (error) { | ||
const anError = | ||
error instanceof Error | ||
? error | ||
: new Error("Not an Error: " + JSON.stringify(error)); | ||
await uow.conventionToSyncRepository.save({ | ||
id: conventionToSync.id, | ||
status: "ERROR", | ||
processDate: this.timeGateway.now(), | ||
reason: anError.message, | ||
}); | ||
this.report.errors[conventionToSync.id] = anError; | ||
} | ||
} | ||
|
||
private async resync( | ||
uow: UnitOfWork, | ||
conventionToSync: ConventionToSync, | ||
): Promise<void> { | ||
const convention = await uow.conventionRepository.getById( | ||
conventionToSync.id, | ||
); | ||
if (!convention) | ||
throw new NotFoundError( | ||
`Convention with id ${conventionToSync.id} missing in conventionRepository.`, | ||
); | ||
await new BroadcastToPoleEmploiOnConventionUpdates( | ||
this.uowPerform, | ||
this.poleEmploiGateway, | ||
this.timeGateway, | ||
true, | ||
).execute(convention); | ||
} | ||
|
||
private report: ResyncOldConventionToPeReport = { | ||
errors: {}, | ||
skips: {}, | ||
success: 0, | ||
}; | ||
} |
Oops, something went wrong.