Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[TRA 14646] - Ajout de courtier/négociant sur BSVHU #3645

Open
wants to merge 8 commits into
base: dev
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions Changelog.md
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ et le projet suit un schéma de versionning inspiré de [Calendar Versioning](ht
#### :rocket: Nouvelles fonctionnalités

- Ajout d'Eco-organisme sur BSVHU [PR 3619](https://github.com/MTES-MCT/trackdechets/pull/3619)
- Ajout des profils Négociant et Courtier sur BSVHU [PR 3645](https://github.com/MTES-MCT/trackdechets/pull/3645)

#### :bug: Corrections de bugs

Expand Down
2 changes: 1 addition & 1 deletion back/src/bsda/registry.ts
Original file line number Diff line number Diff line change
Expand Up @@ -417,7 +417,7 @@ export function toIncomingWaste(bsda: RegistryBsda): Required<IncomingWaste> {
traderRecepisseNumber: null,
brokerCompanyName: bsda.brokerCompanyName,
brokerCompanySiret: bsda.brokerCompanySiret,
brokerRecepisseNumber: null,
brokerRecepisseNumber: bsda.brokerRecepisseNumber,
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ajout de valeur manquante, je m'en suis rendu compte en regardnt ce qui était fait côté BSDA

emitterCompanyMail: bsda.emitterCompanyMail,
...getOperationData(bsda),
nextDestinationProcessingOperation:
Expand Down
72 changes: 72 additions & 0 deletions back/src/bsda/validation/recipify.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,72 @@
import { getTransporterCompanyOrgId } from "@td/constants";
import { getSealedFields } from "./rules";
import { ParsedZodBsda } from "./schema";
import { BsdaValidationContext, ZodBsdaTransformer } from "./types";
import { CompanyRole } from "../../common/validation/zod/schema";
import { buildRecipify, RecipifyInputAccessor } from "../../companies/recipify";

const recipifyBsdaAccessors = (
bsd: ParsedZodBsda,
// Tranformations should not be run on sealed fields
sealedFields: string[]
): RecipifyInputAccessor<ParsedZodBsda>[] => [
...(bsd.transporters ?? []).map(
(_, idx) =>
({
role: CompanyRole.Transporter,
skip: !!bsd.transporters![idx].transporterTransportSignatureDate,
orgIdGetter: () => {
const orgId = getTransporterCompanyOrgId({
transporterCompanySiret:
bsd.transporters![idx].transporterCompanySiret ?? null,
transporterCompanyVatNumber:
bsd.transporters![idx].transporterCompanyVatNumber ?? null
});
return orgId ?? null;
Comment on lines +18 to +25
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

petite différence avec les accesseurs sirenify, on a une fonction pour récup l'orgId au lieu de juste un champ "siret" pour gérer les récupérations d'orgId qui sont soit vat soit siret comme ici

},
setter: async (bsda: ParsedZodBsda, receipt) => {
const transporter = bsda.transporters![idx];
if (transporter.transporterRecepisseIsExempted) {
transporter.transporterRecepisseNumber = null;
transporter.transporterRecepisseValidityLimit = null;
transporter.transporterRecepisseDepartment = null;
} else {
transporter.transporterRecepisseNumber =
receipt?.receiptNumber ?? null;
transporter.transporterRecepisseValidityLimit =
receipt?.validityLimit ?? null;
transporter.transporterRecepisseDepartment =
receipt?.department ?? null;
}
}
} as RecipifyInputAccessor<ParsedZodBsda>)
),
{
role: CompanyRole.Broker,
skip: sealedFields.includes("brokerRecepisseNumber"),
orgIdGetter: () => {
return bsd.brokerCompanySiret ?? null;
},
setter: async (bsda: ParsedZodBsda, receipt) => {
if (!bsda.brokerRecepisseNumber && receipt?.receiptNumber) {
bsda.brokerRecepisseNumber = receipt.receiptNumber;
}
if (!bsda.brokerRecepisseValidityLimit && receipt?.validityLimit) {
bsda.brokerRecepisseValidityLimit = receipt.validityLimit;
}
if (!bsda.brokerRecepisseDepartment && receipt?.department) {
bsda.brokerRecepisseDepartment = receipt.department;
}
}
}
];

export const recipifyBsda: (
context: BsdaValidationContext
) => ZodBsdaTransformer = context => {
return async bsda => {
const sealedFields = await getSealedFields(bsda, context);
const accessors = recipifyBsdaAccessors(bsda, sealedFields);
return buildRecipify(accessors, bsda);
};
};
3 changes: 1 addition & 2 deletions back/src/bsda/validation/rules.ts
Original file line number Diff line number Diff line change
Expand Up @@ -725,8 +725,7 @@ export const bsdaEditionRules: BsdaEditionRules = {
sealed: { from: "OPERATION" }
},
brokerRecepisseValidityLimit: {
readableFieldName:
"la date de validité de la certification de l'entreprise de travaux",
readableFieldName: "la date de validité du récépissé du courtier",
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

wording qui n'était pas le bon, remarqué en regardant ce qui était fait côté BSDA

sealed: { from: "OPERATION" }
},
wasteCode: {
Expand Down
4 changes: 2 additions & 2 deletions back/src/bsda/validation/schema.ts
Original file line number Diff line number Diff line change
Expand Up @@ -35,13 +35,13 @@ import {
updateTransporterRecepisse
} from "./transformers";
import { sirenifyBsda, sirenifyBsdaTransporter } from "./sirenify";
import { updateTransportersRecepisse } from "../../common/validation/zod/transformers";
import {
CompanyRole,
foreignVatNumberSchema,
rawTransporterSchema,
siretSchema
} from "../../common/validation/zod/schema";
import { recipifyBsda } from "./recipify";

const ZodBsdaPackagingEnum = z.enum([
"BIG_BAG",
Expand Down Expand Up @@ -292,7 +292,7 @@ export const contextualSchemaAsync = (context: BsdaValidationContext) => {
// `enableCompletionTransformers=false`;
transformedSyncSchema
.transform(sirenifyBsda(context))
.transform(updateTransportersRecepisse)
.transform(recipifyBsda(context))
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

utilisation du nouveau recipify

.transform(fillWasteConsistenceWhenForwarding)
: transformedSyncSchema;

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -92,6 +92,9 @@ describe("Query.bsds.vhus base workflow", () => {
destination = await userWithCompanyFactory(UserRole.ADMIN, {
companyTypes: {
set: ["WASTE_VEHICLES"]
},
wasteVehiclesTypes: {
set: ["BROYEUR", "DEMOLISSEUR"]
Comment on lines +95 to +97
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

En raison de l'ajout de la validation du sous profil qui n'était pas faite alors que ça devrait être le cas, j'ai dû ajouter la définition de sous profil dans plein de tests

}
});
});
Expand Down
54 changes: 54 additions & 0 deletions back/src/bsffs/validation/bsff/recipify.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
import { getTransporterCompanyOrgId } from "@td/constants";
import { ParsedZodBsff } from "./schema";
import { BsffValidationContext, ZodBsffTransformer } from "./types";
import { CompanyRole } from "../../../common/validation/zod/schema";
import {
buildRecipify,
RecipifyInputAccessor
} from "../../../companies/recipify";

const recipifyBsffAccessors = (
bsd: ParsedZodBsff
): RecipifyInputAccessor<ParsedZodBsff>[] => [
...(bsd.transporters ?? []).map(
(_, idx) =>
({
role: CompanyRole.Transporter,
skip: !!bsd.transporters![idx].transporterTransportSignatureDate,
orgIdGetter: () => {
const orgId = getTransporterCompanyOrgId({
transporterCompanySiret:
bsd.transporters![idx].transporterCompanySiret ?? null,
transporterCompanyVatNumber:
bsd.transporters![idx].transporterCompanyVatNumber ?? null
});
return orgId ?? null;
},
setter: async (bsff: ParsedZodBsff, receipt) => {
const transporter = bsff.transporters![idx];
if (transporter.transporterRecepisseIsExempted) {
transporter.transporterRecepisseNumber = null;
transporter.transporterRecepisseValidityLimit = null;
transporter.transporterRecepisseDepartment = null;
} else {
transporter.transporterRecepisseNumber =
receipt?.receiptNumber ?? null;
transporter.transporterRecepisseValidityLimit =
receipt?.validityLimit ?? null;
transporter.transporterRecepisseDepartment =
receipt?.department ?? null;
}
}
} as RecipifyInputAccessor<ParsedZodBsff>)
)
];

export const recipifyBsff: (
context: BsffValidationContext
) => ZodBsffTransformer = () => {
return async bsff => {
// const sealedFields = await getSealedFields(bsda, context);
const accessors = recipifyBsffAccessors(bsff);
return buildRecipify(accessors, bsff);
};
};
4 changes: 2 additions & 2 deletions back/src/bsffs/validation/bsff/schema.ts
Original file line number Diff line number Diff line change
Expand Up @@ -19,12 +19,12 @@ import {
checkAndSetPreviousPackagings,
updateTransporterRecepisse
} from "./transformers";
import { updateTransportersRecepisse } from "../../../common/validation/zod/transformers";
import {
CompanyRole,
rawTransporterSchema,
siretSchema
} from "../../../common/validation/zod/schema";
import { recipifyBsff } from "./recipify";

export const ZodWasteCodeEnum = z
.enum(BSFF_WASTE_CODES, {
Expand Down Expand Up @@ -195,7 +195,7 @@ export const contextualBsffSchemaAsync = (context: BsffValidationContext) => {
return refinedBsffSchema
.superRefine(checkCompanies)
.transform(sirenifyBsff(context))
.transform(updateTransportersRecepisse)
.transform(recipifyBsff(context))
.superRefine(
// run le check sur les champs requis après les transformations
// au cas où des transformations auto-complète certains champs
Expand Down
16 changes: 15 additions & 1 deletion back/src/bsvhu/__tests__/bsvhuEdition.test.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import {
BsvhuBrokerInput,
BsvhuDestinationInput,
BsvhuDestinationType,
BsvhuEcoOrganismeInput,
Expand All @@ -9,6 +10,7 @@ import {
BsvhuOperationInput,
BsvhuRecepisseInput,
BsvhuReceptionInput,
BsvhuTraderInput,
BsvhuTransporterInput,
BsvhuTransportInput,
BsvhuWeightInput,
Expand Down Expand Up @@ -102,6 +104,16 @@ describe("edition", () => {
name: "yyy"
};

const broker: Required<BsvhuBrokerInput> = {
company,
recepisse
};

const trader: Required<BsvhuTraderInput> = {
company,
recepisse
};

const input: Required<BsvhuInput> = {
emitter,
wasteCode: "",
Expand All @@ -112,7 +124,9 @@ describe("edition", () => {
transporter,
destination,
intermediaries: [company],
ecoOrganisme
ecoOrganisme,
broker,
trader
};
const flatInput = graphQlInputToZodBsvhu(input);
for (const key of Object.keys(flatInput)) {
Expand Down
13 changes: 12 additions & 1 deletion back/src/bsvhu/__tests__/elastic.integration.ts
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,8 @@ describe("toBsdElastic > companies Names & OrgIds", () => {
let intermediary1: Company;
let intermediary2: Company;
let ecoOrganisme: Company;
let broker: Company;
let trader: Company;

beforeAll(async () => {
// Given
Expand All @@ -45,7 +47,8 @@ describe("toBsdElastic > companies Names & OrgIds", () => {
intermediary1 = await companyFactory({ name: "Intermediaire 1" });
intermediary2 = await companyFactory({ name: "Intermediaire 2" });
ecoOrganisme = await companyFactory({ name: "Eco organisme" });

broker = await companyFactory({ name: "Broker" });
trader = await companyFactory({ name: "Trader" });
bsvhu = await bsvhuFactory({
opt: {
emitterCompanyName: emitter.name,
Expand All @@ -57,6 +60,10 @@ describe("toBsdElastic > companies Names & OrgIds", () => {
destinationCompanySiret: destination.siret,
ecoOrganismeName: ecoOrganisme.name,
ecoOrganismeSiret: ecoOrganisme.siret,
brokerCompanySiret: broker.siret,
brokerCompanyName: broker.name,
traderCompanySiret: trader.siret,
traderCompanyName: trader.name,
intermediaries: {
createMany: {
data: [
Expand All @@ -80,6 +87,8 @@ describe("toBsdElastic > companies Names & OrgIds", () => {
expect(elasticBsvhu.companyNames).toContain(intermediary1.name);
expect(elasticBsvhu.companyNames).toContain(intermediary2.name);
expect(elasticBsvhu.companyNames).toContain(ecoOrganisme.name);
expect(elasticBsvhu.companyNames).toContain(broker.name);
expect(elasticBsvhu.companyNames).toContain(trader.name);
});

test("companyOrgIds > should contain the orgIds of ALL BSVHU companies", async () => {
Expand All @@ -90,5 +99,7 @@ describe("toBsdElastic > companies Names & OrgIds", () => {
expect(elasticBsvhu.companyOrgIds).toContain(intermediary1.siret);
expect(elasticBsvhu.companyOrgIds).toContain(intermediary2.siret);
expect(elasticBsvhu.companyOrgIds).toContain(ecoOrganisme.siret);
expect(elasticBsvhu.companyOrgIds).toContain(broker.siret);
expect(elasticBsvhu.companyOrgIds).toContain(trader.siret);
});
});
32 changes: 30 additions & 2 deletions back/src/bsvhu/__tests__/factories.vhu.ts
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,14 @@ export const bsvhuFactory = async ({
companyTypes: ["TRANSPORTER"]
});
const destinationCompany = await companyFactory({
companyTypes: ["WASTE_VEHICLES"]
companyTypes: ["WASTE_VEHICLES"],
wasteVehiclesTypes: ["BROYEUR", "DEMOLISSEUR"]
});
const brokerCompany = await companyFactory({
companyTypes: ["BROKER"]
});
const traderCompany = await companyFactory({
companyTypes: ["TRADER"]
});
const ecoOrganisme = await ecoOrganismeFactory({
handle: { handleBsvhu: true },
Expand All @@ -34,6 +41,8 @@ export const bsvhuFactory = async ({
transporterCompanySiret: transporterCompany.siret,
destinationCompanySiret: destinationCompany.siret,
ecoOrganismeSiret: ecoOrganisme.siret,
brokerCompanySiret: brokerCompany.siret,
traderCompanySiret: traderCompany.siret,
...opt
},
include: {
Expand Down Expand Up @@ -97,7 +106,26 @@ const getVhuFormdata = (): Prisma.BsvhuCreateInput => ({
destinationOperationCode: null,

ecoOrganismeSiret: siretify(4),
ecoOrganismeName: "Eco-Organisme"
ecoOrganismeName: "Eco-Organisme",

brokerCompanyName: "Courtier efficace",
brokerCompanySiret: siretify(5),
brokerCompanyAddress: "15 Rue des Lilas, 33000 Lille",
brokerCompanyContact: "Anton Spencer",
brokerCompanyPhone: "06 67 78 89 91",
brokerCompanyMail: "[email protected]",
brokerRecepisseNumber: "receipt number",
brokerRecepisseDepartment: "33",
brokerRecepisseValidityLimit: "2026-11-27T00:00:00.000Z",
traderCompanyName: "Le Négoce QVB",
traderCompanySiret: siretify(6),
traderCompanyAddress: "32 Avenue des Azalées, 33700 Mérignac",
traderCompanyContact: "Benjamin Turner",
traderCompanyPhone: "06 68 35 64 34",
traderCompanyMail: "[email protected]",
traderRecepisseNumber: "receipt of the firm",
traderRecepisseDepartment: "33",
traderRecepisseValidityLimit: "2026-11-28T00:00:00.000Z"
});

export const toIntermediaryCompany = (company: Company, contact = "toto") => ({
Expand Down
Loading
Loading