diff --git a/server/src/http/controllers/v2/applications.controller.v2.test.ts b/server/src/http/controllers/v2/applications.controller.v2.test.ts index 6f911a54f..97a67aa1d 100644 --- a/server/src/http/controllers/v2/applications.controller.v2.test.ts +++ b/server/src/http/controllers/v2/applications.controller.v2.test.ts @@ -1,5 +1,5 @@ import { ObjectId } from "mongodb" -import { IApplicationApiPayload, JOB_STATUS } from "shared" +import { IApplicationApiPublic, JOB_STATUS } from "shared" import { NIVEAUX_POUR_LBA, RECRUITER_STATUS } from "shared/constants" import { LBA_ITEM_TYPE } from "shared/constants/lbaitem" import { applicationTestFile, wrongApplicationTestFile } from "shared/fixtures/application.fixture" @@ -118,7 +118,7 @@ describe("POST /v2/application", () => { }) it("Return 202 and create an application using a recruter lba", async () => { - const body: IApplicationApiPayload = { + const body: IApplicationApiPublic = { applicant_attachment_name: "cv.pdf", applicant_attachment_content: applicationTestFile, applicant_email: "jeam.dupont@mail.com", @@ -174,7 +174,7 @@ describe("POST /v2/application", () => { it("Return 202 and create an application using a recruiter", async () => { const job = recruiter.jobs[0] - const body: IApplicationApiPayload = { + const body: IApplicationApiPublic = { applicant_attachment_name: "cv.pdf", applicant_attachment_content: applicationTestFile, applicant_email: "jeam.dupont@mail.com", @@ -230,7 +230,7 @@ describe("POST /v2/application", () => { }) it("return 400 as file type is not supported", async () => { const job = recruiter.jobs[0] - const body: IApplicationApiPayload = { + const body: IApplicationApiPublic = { applicant_attachment_name: "cv.pdf", applicant_attachment_content: wrongApplicationTestFile, applicant_email: "jeam.dupont@mail.com", diff --git a/server/src/services/application.service.ts b/server/src/services/application.service.ts index 31494c7da..36a736390 100644 --- a/server/src/services/application.service.ts +++ b/server/src/services/application.service.ts @@ -3,7 +3,18 @@ import { isEmailBurner } from "burner-email-providers" import dayjs from "dayjs" import { fileTypeFromBuffer } from "file-type" import { ObjectId } from "mongodb" -import { ApplicationScanStatus, IApplication, IApplicationApiPayloadOutput, IJob, ILbaCompany, INewApplicationV1, IRecruiter, JOB_STATUS, assertUnreachable } from "shared" +import { + ApplicationScanStatus, + IApplication, + IApplicationApiPrivateOutput, + IApplicationApiPublicOutput, + IJob, + ILbaCompany, + INewApplicationV1, + IRecruiter, + JOB_STATUS, + assertUnreachable, +} from "shared" import { ApplicantIntention } from "shared/constants/application" import { BusinessErrorCodes } from "shared/constants/errorCodes" import { LBA_ITEM_TYPE, LBA_ITEM_TYPE_OLD, getDirectJobPath, newItemTypeToOldItemType } from "shared/constants/lbaitem" @@ -229,7 +240,7 @@ export const sendApplicationV2 = async ({ caller, source, }: { - newApplication: IApplicationApiPayloadOutput + newApplication: IApplicationApiPublicOutput | IApplicationApiPrivateOutput caller?: string source?: ITrackingCookies }): Promise<{ _id: ObjectId }> => { @@ -514,7 +525,7 @@ const newApplicationToApplicationDocument = async (newApplication: INewApplicati /** * @description Initialize application object from query parameters */ -const newApplicationToApplicationDocumentV2 = async (newApplication: IApplicationApiPayloadOutput, LbaJob: IJobOrCompany, caller?: string) => { +const newApplicationToApplicationDocumentV2 = async (newApplication: IApplicationApiPublicOutput | IApplicationApiPrivateOutput, LbaJob: IJobOrCompany, caller?: string) => { const now = new Date() const application: IApplication = { ...offreOrCompanyToCompanyFields(LbaJob), diff --git a/shared/models/applications.model.ts b/shared/models/applications.model.ts index 6a5aa576c..f38e46acb 100644 --- a/shared/models/applications.model.ts +++ b/shared/models/applications.model.ts @@ -172,7 +172,9 @@ const ZNewApplicationTransitionToV2 = ZApplication.extend({ // KBA 20241011 to remove once V2 is LIVE and V1 support has ended export type INewApplicationV1 = z.output -const ZApplicationV2Base = ZApplication.pick({ +type JobCollectionName = "recruteurslba" | "jobs_partners" | "recruiters" + +export const ZApplicationApiPrivate = ZApplication.pick({ applicant_first_name: true, applicant_last_name: true, applicant_email: true, @@ -183,10 +185,6 @@ const ZApplicationV2Base = ZApplication.pick({ }).extend({ applicant_message: ZApplication.shape.applicant_message_to_company.optional(), applicant_attachment_content: z.string().max(4_215_276).describe("Le contenu du fichier du CV du candidat. La taille maximale autorisée est de 3 Mo."), -}) - -type JobCollectionName = "recruteurslba" | "jobs_partners" | "recruiters" -export const ZApplicationApiPayload = ZApplicationV2Base.extend({ recipient_id: z .string() .transform((recipientId) => { @@ -201,9 +199,18 @@ export const ZApplicationApiPayload = ZApplicationV2Base.extend({ }) .describe("Identifiant unique de la ressource vers laquelle la candidature est faite, préfixé par le nom de la collection"), }) -export type IApplicationApiPayloadOutput = z.output -export type IApplicationApiPayload = z.input -export type IApplicationApiPayloadJSON = Jsonify> + +export const ZApplicationApiPublic = ZApplicationApiPrivate.omit({ + caller: true, + job_searched_by_user: true, +}) + +export type IApplicationApiPublicOutput = z.output +export type IApplicationApiPrivateOutput = z.output +export type IApplicationApiPublic = z.input +export type IApplicationApiPrivate = z.input +export type IApplicationApiPrivateJSON = Jsonify> +export type IApplicationApiPublicJSON = Jsonify> export default { zod: ZApplication, diff --git a/shared/models/lbaItem.model.ts b/shared/models/lbaItem.model.ts index 5d2b77312..bad80350c 100644 --- a/shared/models/lbaItem.model.ts +++ b/shared/models/lbaItem.model.ts @@ -234,7 +234,7 @@ const ZLbaItemJob = z .object({ description: z.string().nullish(), // pe -> description | matcha -> description | partner -> offer_description employeurDescription: z.string().nullish(), // matcha -> job.job_employer_description | partner -> workplace_description - creationDate: z.date().nullable(), // pe -> dateCreation | matcha -> createdAt | + creationDate: z.date().nullable(), // pe -> dateCreation | matcha -> createdAt | parnter -> offer_creation id: z.string().nullish(), // pe -> id | matcha -> id mongo offre | partner -> partner_id contractType: z.string().nullish(), // pe -> typeContrat | matcha -> offres.type contractDescription: z.string().nullish(), // pe -> typeContratLibelle diff --git a/shared/routes/application.routes.v2.ts b/shared/routes/application.routes.v2.ts index 8cdd3c9a7..ab4a7f64b 100644 --- a/shared/routes/application.routes.v2.ts +++ b/shared/routes/application.routes.v2.ts @@ -1,5 +1,5 @@ import { z } from "../helpers/zodWithOpenApi" -import { ZApplicationApiPayload } from "../models" +import { ZApplicationApiPrivate, ZApplicationApiPublic } from "../models" import { IRoutesDef } from "./common.routes" @@ -8,7 +8,7 @@ export const zApplicationRoutesV2 = { "/application": { path: "/application", method: "post", - body: ZApplicationApiPayload, + body: ZApplicationApiPublic, response: { "202": z.object({ id: z.string(), @@ -19,7 +19,7 @@ export const zApplicationRoutesV2 = { "/_private/application": { path: "/_private/application", method: "post", - body: ZApplicationApiPayload, + body: ZApplicationApiPrivate, response: { "200": z.object({}), }, diff --git a/ui/components/ItemDetail/CandidatureLba/services/getSchema.ts b/ui/components/ItemDetail/CandidatureLba/services/getSchema.ts index 1a97a00db..67833842d 100644 --- a/ui/components/ItemDetail/CandidatureLba/services/getSchema.ts +++ b/ui/components/ItemDetail/CandidatureLba/services/getSchema.ts @@ -1,10 +1,10 @@ -import { IApplicationApiPayloadJSON, ZApplicationApiPayload } from "shared" +import { IApplicationApiPrivateJSON, ZApplicationApiPrivate } from "shared" import { validatePhone } from "shared/validators/phoneValidator" import { z } from "zod" import { sessionStorageGet } from "@/utils/localStorage" -export type IApplicationSchemaInitValues = Omit +export type IApplicationSchemaInitValues = Omit export function getInitialSchemaValues(): IApplicationSchemaInitValues { const inSessionValue = JSON.parse(sessionStorageGet("application-form-values")) @@ -19,7 +19,7 @@ export function getInitialSchemaValues(): IApplicationSchemaInitValues { } } -export const ApplicationFormikSchema = ZApplicationApiPayload.pick({ +export const ApplicationFormikSchema = ZApplicationApiPrivate.pick({ applicant_first_name: true, applicant_last_name: true, applicant_email: true, diff --git a/ui/components/ItemDetail/CandidatureLba/services/submitCandidature.ts b/ui/components/ItemDetail/CandidatureLba/services/submitCandidature.ts index 78d54f14e..a0a556de7 100644 --- a/ui/components/ItemDetail/CandidatureLba/services/submitCandidature.ts +++ b/ui/components/ItemDetail/CandidatureLba/services/submitCandidature.ts @@ -1,5 +1,5 @@ import { useContext } from "react" -import { IApplicationApiPayload, ILbaItemLbaCompany, ILbaItemLbaJob } from "shared" +import { IApplicationApiPrivate, ILbaItemLbaCompany, ILbaItemLbaJob } from "shared" import { DisplayContext } from "@/context/DisplayContextProvider" import { getItemId } from "@/utils/getItemId" @@ -40,7 +40,7 @@ export default async function submitCandidature({ }) { setSendingState("currently_sending") - const payload: IApplicationApiPayload = { + const payload: IApplicationApiPrivate = { applicant_first_name: formValues.applicant_first_name, applicant_last_name: formValues.applicant_last_name, applicant_email: formValues.applicant_email,