Skip to content

Commit

Permalink
feat: millesime unique pour insersup
Browse files Browse the repository at this point in the history
  • Loading branch information
K4ST0R committed Nov 26, 2024
1 parent e603c51 commit 94f9dbb
Show file tree
Hide file tree
Showing 14 changed files with 1,648 additions and 131 deletions.
39 changes: 39 additions & 0 deletions server/src/common/repositories/formationStats.js
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import { StatsRepository } from "./base.js";
import { dbCollection } from "#src/common/db/mongodb.js";
import { name } from "#src/common/db/collections/formationsStats.js";
import { getMillesimeFormationsYearFrom } from "#src/common/stats.js";

export class FormationStatsRepository extends StatsRepository {
constructor() {
Expand Down Expand Up @@ -33,6 +34,44 @@ export class FormationStatsRepository extends StatsRepository {

return result ? result.map((data) => data.millesime) : [];
}

// Retourne les formations du supérieur possédant un millésime aggregé et un millésime unique
async findMillesimeInDouble(millesime, filiere = "superieur") {
const millesimeYear = getMillesimeFormationsYearFrom(millesime);

return await dbCollection(this.getCollection())
.aggregate([
{ $match: { filiere, millesime: millesimeYear } },
{
$lookup: {
from: this.getCollection(),
localField: "uai",
foreignField: "uai",
as: "others",
let: { code_certification_base: "$code_certification" },
pipeline: [
{
$match: {
$expr: {
$and: [
{ $eq: ["$filiere", filiere] },
{ $eq: ["$$code_certification_base", "$code_certification"] },
{ $eq: ["$millesime", millesime] },
],
},
},
},
],
},
},
{
$match: {
"others.0": { $exists: true },
},
},
])
.toArray();
}
}

export default new FormationStatsRepository();
21 changes: 21 additions & 0 deletions server/src/common/stats.js
Original file line number Diff line number Diff line change
Expand Up @@ -84,6 +84,23 @@ export function getLastMillesimesFormationsSup() {
return config.millesimes.formationsSup[config.millesimes.formationsSup.length - 1];
}

export function getLastMillesimesFormationsFor(filiere) {
return filiere === "superieur" ? getLastMillesimesFormationsSup() : getLastMillesimesFormations();
}

export function getLastMillesimesFormationsYearFor(filiere) {
const millesime = filiere === "superieur" ? getLastMillesimesFormationsSup() : getLastMillesimesFormations();
return millesime.split("_")[1];
}

export function getMillesimeFormationsFrom(millesime) {
return `${parseInt(millesime) - 1}_${millesime}`;
}

export function getMillesimeFormationsYearFrom(millesime) {
return millesime.split("_")[1];
}

export function getMillesimesRegionales() {
return config.millesimes.regionales;
}
Expand All @@ -92,6 +109,10 @@ export function getLastMillesimesRegionales() {
return config.millesimes.regionales[config.millesimes.regionales.length - 1];
}

export function isMillesimesYearSingle(millesime) {
return millesime.split("_").length === 1 ? true : false;
}

function divide({ dividend, divisor }) {
return {
compute: (data) => percentage(data[dividend], data[divisor]),
Expand Down
59 changes: 45 additions & 14 deletions server/src/http/routes/formationsRoutes.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ import express from "express";
import { tryCatch } from "#src/http/middlewares/tryCatchMiddleware.js";
import { authMiddleware } from "#src/http/middlewares/authMiddleware.js";
import Joi from "joi";
import { flatten } from "lodash-es";
import * as validators from "#src/http/utils/validators.js";
import { validate } from "#src/http/utils/validators.js";
import { addCsvHeaders, addJsonHeaders, sendStats, sendImageOnError } from "#src/http/utils/responseUtils.js";
Expand All @@ -15,7 +16,11 @@ import { getStatsAsColumns } from "#src/common/utils/csvUtils.js";
import {
getLastMillesimesFormations,
getLastMillesimesFormationsSup,
getLastMillesimesFormationsYearFor,
getMillesimeFormationsFrom,
getMillesimeFormationsYearFrom,
transformDisplayStat,
isMillesimesYearSingle,
} from "#src/common/stats.js";
import BCNRepository from "#src/common/repositories/bcn.js";
import BCNSiseRepository from "#src/common/repositories/bcnSise.js";
Expand All @@ -36,7 +41,12 @@ async function formationStats({ uai, codeCertificationWithType, millesime }) {
const result = await FormationStatsRepository.first({
uai,
code_certification: code_certification,
millesime: formatMillesime(millesime),
millesime: [
millesime,
isMillesimesYearSingle(millesime)
? getMillesimeFormationsFrom(millesime)
: getMillesimeFormationsYearFrom(millesime),
],
});

if (!result) {
Expand Down Expand Up @@ -99,12 +109,35 @@ export default () => {
...(millesimes.length === 0
? {
$or: [
{ filiere: "superieur", millesime: getLastMillesimesFormationsSup() },
{ filiere: { $ne: "superieur" }, millesime: getLastMillesimesFormations() },
{
filiere: "superieur",
millesime: {
$in: [
getMillesimeFormationsYearFrom(getLastMillesimesFormationsSup()),
getLastMillesimesFormationsSup(),
],
},
},
{
filiere: { $ne: "superieur" },
millesime: {
$in: [
getMillesimeFormationsYearFrom(getLastMillesimesFormations()),
getLastMillesimesFormations(),
],
},
},
],
}
: {
millesime: millesimes,
millesime: flatten(
millesimes.map((m) => {
return [
m,
isMillesimesYearSingle(m) ? getMillesimeFormationsFrom(m) : getMillesimeFormationsYearFrom(m),
];
})
),
}),
},
{
Expand Down Expand Up @@ -166,10 +199,9 @@ export default () => {
}
);
const codeCertificationWithType = formatCodeCertificationWithType(code_certification);
const millesime =
millesimeBase ||
(codeCertificationWithType.filiere === "superieur" && getLastMillesimesFormationsSup()) ||
getLastMillesimesFormations();
const millesime = formatMillesime(
millesimeBase || getLastMillesimesFormationsYearFor(codeCertificationWithType.filiere)
);

return sendImageOnError(
async () => {
Expand Down Expand Up @@ -206,15 +238,14 @@ export default () => {
);

const codeCertificationWithType = formatCodeCertificationWithType(code_certification);
const millesime =
millesimeBase ||
(codeCertificationWithType.filiere === "superieur" && getLastMillesimesFormationsSup()) ||
getLastMillesimesFormations();
const millesime = formatMillesime(
millesimeBase || getLastMillesimesFormationsYearFor(codeCertificationWithType.filiere)
);

try {
const stats = await formationStats({ uai, codeCertificationWithType, millesime });
const etablissement = await AcceEtablissementRepository.first({ numero_uai: uai });
const data = await formatDataWidget({ stats, millesime, etablissement });
const data = await formatDataWidget({ stats, etablissement });

const widget = await getUserWidget({
hash,
Expand All @@ -240,7 +271,7 @@ export default () => {
options,
data: {
error: err.name,
millesimes: formatMillesime(millesime).split("_"),
millesimes: millesime.split("_"),
code_certification,
uai,
},
Expand Down
4 changes: 2 additions & 2 deletions server/src/http/utils/widgetUtils.js
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import { buildDescriptionFiliere, buildDescription } from "#src/common/stats.js";
import { formatMillesime } from "#src/http/utils/formatters.js";

export async function formatDataWidget({ stats, millesime, region = null, etablissement = null }) {
export async function formatDataWidget({ stats, region = null, etablissement = null }) {
const description = buildDescription(stats);

const data = {
Expand All @@ -12,7 +12,7 @@ export async function formatDataWidget({ stats, millesime, region = null, etabli
{ name: "emploi", value: stats.taux_en_emploi_6_mois },
{ name: "autres", value: stats.taux_autres_6_mois },
],
millesimes: formatMillesime(millesime).split("_"),
millesimes: formatMillesime(stats.millesime).split("_"),
description,
// TODO: fix libelle BCN
formationLibelle: stats.libelle,
Expand Down
12 changes: 12 additions & 0 deletions server/src/jobs/stats/computeUAI.js
Original file line number Diff line number Diff line change
Expand Up @@ -56,6 +56,18 @@ async function computeUAIBase(millesime, result, handleError) {
async (stats) => {
const { uai, code_formation_diplome, millesime, filiere } = stats;

// On ne connait pas le type de l'uai pour le supérieur
if (filiere === "superieur") {
return {
uai: stats.uai,
uai_type: "inconnu",
uai_donnee: stats.uai,
uai_donnee_type: "inconnu",
code_certification: stats.code_certification,
millesime: millesime,
};
}

// Le lieu de formation, le formateur et le gestionnaire sont identiques pour la voie scolaire
if (filiere !== "apprentissage") {
return {
Expand Down
21 changes: 21 additions & 0 deletions server/src/jobs/stats/importFormationsSupStats.js
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ import { findRegionByNom, findAcademieByNom } from "#src/services/regions.js";
import { computeCustomStats, getMillesimesFormationsSup, INSERSUP_STATS_NAMES } from "#src/common/stats.js";
import { getCertificationSupInfo } from "#src/common/certification.js";
import { InserSup } from "#src/services/dataEnseignementSup/InserSup.js";
import FormationStatsRepository from "#src/common/repositories/formationStats.js";

const logger = getLoggerWithContext("import");

Expand All @@ -23,6 +24,21 @@ function formatStats(stats) {
};
}

async function checkMillesimeInDouble(jobStats, millesimes) {
for (const millesime of millesimes) {
const results = await FormationStatsRepository.findMillesimeInDouble(millesime);
for (const result of results) {
jobStats.failed++;
const formatted = {
...pick(result, ["uai", "code_certification", "filiere"]),
millesimes: [result.millesime, ...result.others.map((r) => r.millesime)],
};
logger.error(`Millésime en double pour : `, formatted);
jobStats.error = `Millésime en double pour : ${JSON.stringify(formatted)}`;
}
}
}

export async function importFormationsSupStats(options = {}) {
const jobStats = { created: 0, updated: 0, failed: 0 };

Expand Down Expand Up @@ -143,5 +159,10 @@ export async function importFormationsSupStats(options = {}) {
)
);

// Vérifie que l'on a pas un mélange millésime unique/aggregé pour une même année/formation
// Actuellement le cas n'existe pas, on met une alerte au cas ou
// Si le cas apparait : modifier les routes bulks pour envoyer l'information suivant les règles de priorités des millésimes
await checkMillesimeInDouble(jobStats, millesimes);

return jobStats;
}
52 changes: 9 additions & 43 deletions server/src/services/dataEnseignementSup/InserSup.js
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,7 @@ class InserSup {
const statsByMillesime = stats.reduce((acc, stat) => {
acc[stat.promo.join("_")] = acc[stat.promo.join("_")] ?? {
...stat,
millesime: stat.promo.join("_"),
nb_diplomes: stat.nb_sortants + stat.nb_poursuivants,
nb_en_emploi: {},
};
Expand All @@ -72,55 +73,20 @@ class InserSup {
}),
// Aggregate two millesimes
transformData((stats) => {
// When the stats is already on two millesimes
if (stats[millesime]) {
return stats[millesime];
}
// We don't want to aggregate when stats are only available by millesimes for now
return null;

// const statsMerged = Object.values(stats).reduce((acc, stat) => {
// if (!acc) {
// return {
// ...stat,
// nb_en_emploi: mapValues(stat.nb_en_emploi, (v) => [v]),
// };
// }

// return {
// ...acc,
// promo: [...acc.promo, ...stat.promo],
// nb_poursuivants: acc.nb_poursuivants + stat.nb_poursuivants,
// nb_sortants: acc.nb_sortants + stat.nb_sortants,
// nb_diplomes: acc.nb_diplomes + stat.nb_diplomes,
// nb_en_emploi: mergeWith(
// acc.nb_en_emploi,
// mapValues(stat.nb_en_emploi, (v) => [v]),
// (objValue, srcValue) => objValue.concat(srcValue)
// ),
// };
// }, null);

// if (statsMerged.promo.length !== 2) {
// return null;
// }

// // Remove value that not exist on both millesime
// statsMerged.nb_en_emploi = mapValues(statsMerged.nb_en_emploi, (v) => {
// if (v.length !== 2 || v.some((v) => v === null)) {
// return null;
// }
// return v.reduce((s, v) => s + v, 0);
// });

// return statsMerged;
return Object.values(stats).filter((stats) => {
return (
stats.millesime === millesime ||
stats.millesime === millesimePart[0] ||
stats.millesime === millesimePart[1]
);
});
}),
flattenArray(),
// Format data
transformData((stats) => {
return {
...stats,
...stats.nb_en_emploi,
millesime,
};
}),
writeData((stats) => {
Expand Down
Loading

0 comments on commit 94f9dbb

Please sign in to comment.