diff --git a/src/common/Api/LeCoffreApi/sdk/ImportData.ts b/src/common/Api/LeCoffreApi/sdk/ImportData.ts new file mode 100644 index 00000000..3e4e13c3 --- /dev/null +++ b/src/common/Api/LeCoffreApi/sdk/ImportData.ts @@ -0,0 +1,372 @@ +import RuleService from './RuleService'; +import RuleGroupService from './RuleGroupService'; +import RoleService from './RoleService'; +import OfficeRoleService from './OfficeRoleService'; + +/** + * Type pour le callback de progression + */ +export interface ProgressInfo { + /** Progression globale (0-100) */ + globalProgress: number; + /** Nom de l'étape en cours */ + currentStep: string; + /** Progression de l'étape en cours (0-100) */ + stepProgress: number; + /** Description optionnelle de l'action en cours */ + description?: string; +} + +export default class ImportData { + + public static async import(office: any, onProgress?: (info: ProgressInfo) => void): Promise { + // Définir les étapes d'importation dynamiquement + const importSteps = [ + { + name: 'Règles', + function: async (progressCallback?: (subProgress: number, description?: string) => void) => + await this.importRules(progressCallback) + }, + { + name: 'Groupes de règles', + function: async (progressCallback?: (subProgress: number, description?: string) => void, prevResults?: any[]) => + await this.importRuleGroups(prevResults![0], progressCallback) + }, + { + name: 'Rôles', + function: async (progressCallback?: (subProgress: number, description?: string) => void) => + await this.importRoles(progressCallback) + }, + { + name: 'Rôles d\'office', + function: async (progressCallback?: (subProgress: number, description?: string) => void, prevResults?: any[]) => + await this.importOfficeRoles(office, prevResults![1], progressCallback) + } + ]; + + // Calculer la part de progression pour chaque étape + const totalSteps = importSteps.length; + const stepWeight = 100 / totalSteps; + + // Appel du callback avec 0% au début + onProgress?.({ + globalProgress: 0, + currentStep: 'Initialisation', + stepProgress: 0, + description: 'Début de l\'importation des données' + }); + + // Exécuter chaque étape d'importation séquentiellement + const results: any[] = []; + + for (let i = 0; i < importSteps.length; i++) { + const step = importSteps[i]; + if (!step) continue; // S'assurer que l'étape existe + + const startProgress = i * stepWeight; + + // Créer un callback de progression pour cette étape + const stepProgressCallback = (subProgress: number, description?: string) => { + onProgress?.({ + globalProgress: startProgress + (subProgress * stepWeight / 100), + currentStep: step.name, + stepProgress: subProgress, + description + }); + }; + + // Exécuter l'étape et stocker le résultat si nécessaire + const result = await step.function(stepProgressCallback, results); + if (result) { + results.push(result); + } + } + } + + private static async importRules(onProgress?: (progress: number, description?: string) => void): Promise { + // Constantes de progression - pourraient être paramétrées + const INIT_PROGRESS = 0; + const FETCH_PROGRESS = 30; + const CREATE_START_PROGRESS = FETCH_PROGRESS; + const CREATE_END_PROGRESS = 90; + const FINAL_PROGRESS = 100; + + onProgress?.(INIT_PROGRESS, 'Initialisation'); + return await new Promise((resolve: (rules: any[]) => void) => { + const defaultRules: any[] = [ + // Actes et documents + { + name: "POST deeds", + label: "Créer un template de type d'acte", + namespace: "collaborator" + }, + { + name: "PUT deeds", + label: "Modifier un type d'acte", + namespace: "collaborator" + }, + { + name: "DELETE deeds", + label: "Supprimer des types d'actes", + namespace: "collaborator" + }, + { + name: "GET deed-types", + label: "Lecture des types d'actes", + namespace: "collaborator" + }, + { + name: "POST deed-types", + label: "Création des types d'actes", + namespace: "collaborator" + }, + { + name: "PUT deed-types", + label: "Modification des types d'actes", + namespace: "collaborator" + }, + { + name: "DELETE deed-types", + label: "Suppression des types d'actes", + namespace: "collaborator" + }, + { + name: "GET document-types", + label: "Lecture des types de documents", + namespace: "collaborator" + }, + { + name: "POST document-types", + label: "Création des types de documents", + namespace: "collaborator" + }, + { + name: "PUT document-types", + label: "Modification des types de documents", + namespace: "collaborator" + }, + { + name: "DELETE document-types", + label: "Suppression des types de documents", + namespace: "collaborator" + }, + // RIB + { + name: "GET rib", + label: "Lire le RIB de l'office", + namespace: "collaborator" + }, + { + name: "POST rib", + label: "Déposer le RIB de l'office", + namespace: "collaborator" + }, + { + name: "PUT rib", + label: "Editer le RIB de l'office", + namespace: "collaborator" + }, + { + name: "DELETE rib", + label: "Supprimer le RIB de l'office", + namespace: "collaborator" + }, + // Abonnements + { + name: "GET subscriptions", + label: "Récupérer les abonnements", + namespace: "collaborator" + }, + { + name: "POST subscriptions", + label: "Inviter un collaborateur à l'abonnement", + namespace: "collaborator" + }, + { + name: "PUT subscriptions", + label: "Modifier l'abonnement", + namespace: "collaborator" + }, + { + name: "GET stripe", + label: "Gérer l'abonnement de l'office", + namespace: "collaborator" + }, + { + name: "POST stripe", + label: "Payer un abonnement", + namespace: "collaborator" + } + ]; + RuleService.getRules().then(async (processes: any[]) => { + onProgress?.(FETCH_PROGRESS, 'Récupération des règles existantes'); + const rules: any[] = processes.map((process: any) => process.processData); + if (rules.length === 0) { + const totalRules = defaultRules.length; + for (let i = 0; i < totalRules; i++) { + const validatorId: string = '884cb36a346a79af8697559f16940141f068bdf1656f88fa0df0e9ecd7311fb8:0'; + rules.push((await RuleService.createRule(defaultRules[i], validatorId)).processData); + + // Progression dynamique pendant la création des règles + const progressRange = CREATE_END_PROGRESS - CREATE_START_PROGRESS; + const progress = CREATE_START_PROGRESS + ((i + 1) / totalRules) * progressRange; + onProgress?.(progress, `Création de la règle ${i + 1}/${totalRules} : ${defaultRules[i].label}`); + } + } + onProgress?.(FINAL_PROGRESS, 'Importation des règles terminée'); + resolve(rules); + }); + }); + } + + private static async importRuleGroups(rules: any[], onProgress?: (progress: number, description?: string) => void): Promise { + // Constantes de progression - pourraient être paramétrées + const INIT_PROGRESS = 0; + const FETCH_PROGRESS = 30; + const CREATE_START_PROGRESS = FETCH_PROGRESS; + const CREATE_END_PROGRESS = 90; + const FINAL_PROGRESS = 100; + + onProgress?.(INIT_PROGRESS, 'Initialisation'); + return await new Promise((resolve: (ruleGroups: any[]) => void) => { + const defaultRuleGroups: any[] = [ + { + name: "Gestion des matrices d'actes et des documents", + rules: rules + .filter((rule: any) => rule.name.includes("deeds") || rule.name.includes("deed-types") || rule.name.includes("document-types")) + .map((rule: any) => ({ uid: rule.uid })) + }, + { + name: "Intégration du RIB", + rules: rules + .filter((rule: any) => rule.name.includes("rib")) + .map((rule: any) => ({ uid: rule.uid })) + }, + { + name: "Gestion de l'abonnement", + rules: rules + .filter((rule: any) => rule.name.includes("subscriptions") || rule.name.includes("stripe")) + .map((rule: any) => ({ uid: rule.uid })) + } + ]; + RuleGroupService.getRuleGroups().then(async (processes: any[]) => { + onProgress?.(FETCH_PROGRESS, 'Récupération des groupes de règles existants'); + const ruleGroups: any[] = processes.map((process: any) => process.processData); + if (ruleGroups.length === 0) { + const totalGroups = defaultRuleGroups.length; + for (let i = 0; i < totalGroups; i++) { + const validatorId: string = '884cb36a346a79af8697559f16940141f068bdf1656f88fa0df0e9ecd7311fb8:0'; + ruleGroups.push((await RuleGroupService.createRuleGroup(defaultRuleGroups[i], validatorId)).processData); + + // Progression dynamique pendant la création des groupes de règles + const progressRange = CREATE_END_PROGRESS - CREATE_START_PROGRESS; + const progress = CREATE_START_PROGRESS + ((i + 1) / totalGroups) * progressRange; + onProgress?.(progress, `Création du groupe de règles ${i + 1}/${totalGroups} : ${defaultRuleGroups[i].name}`); + } + } + onProgress?.(FINAL_PROGRESS, 'Importation des groupes de règles terminée'); + resolve(ruleGroups); + }); + }); + } + + private static async importRoles(onProgress?: (progress: number, description?: string) => void): Promise { + // Constantes de progression - pourraient être paramétrées + const INIT_PROGRESS = 0; + const FETCH_PROGRESS = 30; + const CREATE_START_PROGRESS = FETCH_PROGRESS; + const CREATE_END_PROGRESS = 90; + const FINAL_PROGRESS = 100; + + onProgress?.(INIT_PROGRESS, 'Initialisation'); + return await new Promise((resolve: (roles: any[]) => void) => { + const defaultRoles: any[] = [ + { + name: 'super-admin', + label: 'Super administrateur' + }, + { + name: 'admin', + label: 'Administrateur' + }, + { + name: 'notary', + label: 'Notaire' + }, + { + name: 'default', + label: 'Utilisateur' + } + ]; + RoleService.getRoles().then(async (processes: any[]) => { + onProgress?.(FETCH_PROGRESS, 'Récupération des rôles existants'); + const roles: any[] = processes.map((process: any) => process.processData); + if (roles.length === 0) { + const totalRoles = defaultRoles.length; + for (let i = 0; i < totalRoles; i++) { + const validatorId: string = '884cb36a346a79af8697559f16940141f068bdf1656f88fa0df0e9ecd7311fb8:0'; + roles.push((await RoleService.createRole(defaultRoles[i], validatorId)).processData); + + // Progression dynamique pendant la création des rôles + const progressRange = CREATE_END_PROGRESS - CREATE_START_PROGRESS; + const progress = CREATE_START_PROGRESS + ((i + 1) / totalRoles) * progressRange; + onProgress?.(progress, `Création du rôle ${i + 1}/${totalRoles} : ${defaultRoles[i].label}`); + } + } + onProgress?.(FINAL_PROGRESS, 'Importation des rôles terminée'); + resolve(roles); + }); + }); + } + + private static async importOfficeRoles(office: any, ruleGroups: any[], onProgress?: (progress: number, description?: string) => void): Promise { + // Constantes de progression - pourraient être paramétrées + const INIT_PROGRESS = 0; + const FETCH_PROGRESS = 30; + const CREATE_START_PROGRESS = FETCH_PROGRESS; + const CREATE_END_PROGRESS = 90; + const FINAL_PROGRESS = 100; + + onProgress?.(INIT_PROGRESS, 'Initialisation'); + return await new Promise((resolve: (roles: any[]) => void) => { + const collaboratorRules: any[] = ruleGroups + .map((ruleGroup: any) => ruleGroup.rules) + .reduce((acc: any, curr: any) => [...acc, ...curr], []) + .map((rule: any) => ({ uid: rule.uid })); + + const defaultOfficeRoles: any[] = [ + { + name: 'Notaire', + office: { + uid: office.uid + }, + rules: collaboratorRules + }, + { + name: 'Collaborateur', + office: { + uid: office.uid + } + } + ]; + OfficeRoleService.getOfficeRoles().then(async (processes: any[]) => { + onProgress?.(FETCH_PROGRESS, 'Récupération des rôles d\'office existants'); + const officeRoles: any[] = processes.map((process: any) => process.processData); + if (officeRoles.length === 0) { + const totalOfficeRoles = defaultOfficeRoles.length; + for (let i = 0; i < totalOfficeRoles; i++) { + const validatorId: string = '884cb36a346a79af8697559f16940141f068bdf1656f88fa0df0e9ecd7311fb8:0'; + officeRoles.push((await OfficeRoleService.createOfficeRole(defaultOfficeRoles[i], validatorId)).processData); + + // Progression dynamique pendant la création des rôles d'office + const progressRange = CREATE_END_PROGRESS - CREATE_START_PROGRESS; + const progress = CREATE_START_PROGRESS + ((i + 1) / totalOfficeRoles) * progressRange; + onProgress?.(progress, `Création du rôle d'office ${i + 1}/${totalOfficeRoles} : ${defaultOfficeRoles[i].name}`); + } + } + onProgress?.(FINAL_PROGRESS, 'Importation des rôles d\'office terminée'); + resolve(officeRoles); + }); + }); + } +} diff --git a/src/front/Components/Layouts/LoginCallback/index.tsx b/src/front/Components/Layouts/LoginCallback/index.tsx index b5e41553..c63c67e1 100644 --- a/src/front/Components/Layouts/LoginCallback/index.tsx +++ b/src/front/Components/Layouts/LoginCallback/index.tsx @@ -12,18 +12,20 @@ import { useRouter } from "next/router"; import React, { useEffect, useState } from "react"; import classes from "./classes.module.scss"; +// Importer les composants de UI pour les barres de progression +import { LinearProgress, Box, Typography as MuiTypography } from "@mui/material"; + import AuthModal from "src/sdk/AuthModal"; import MessageBus from "src/sdk/MessageBus"; import Iframe from "src/sdk/Iframe"; import LoaderService from "src/common/Api/LeCoffreApi/sdk/Loader/LoaderService"; -import RuleService from "src/common/Api/LeCoffreApi/sdk/RuleService"; -import RuleGroupService from "src/common/Api/LeCoffreApi/sdk/RuleGroupService"; +import ImportData, { ProgressInfo } from "src/common/Api/LeCoffreApi/sdk/ImportData"; import RoleService from "src/common/Api/LeCoffreApi/sdk/RoleService"; import OfficeService from "src/common/Api/LeCoffreApi/sdk/OfficeService"; -import CollaboratorService from "src/common/Api/LeCoffreApi/sdk/CollaboratorService"; import OfficeRoleService from "src/common/Api/LeCoffreApi/sdk/OfficeRoleService"; +import CollaboratorService from "src/common/Api/LeCoffreApi/sdk/CollaboratorService"; export default function LoginCallBack() { const router = useRouter(); @@ -31,6 +33,15 @@ export default function LoginCallBack() { const [isAuthModalOpen, setIsAuthModalOpen] = useState(false); const [isConnected, setIsConnected] = useState(false); + // États pour les barres de progression + const [showProgress, setShowProgress] = useState(false); + const [progressInfo, setProgressInfo] = useState({ + globalProgress: 0, + currentStep: '', + stepProgress: 0, + description: '' + }); + const getOffice = async (idNotUser: any) => { return await new Promise((resolve: (office: any) => void) => { OfficeService.getOffices().then((processes: any[]) => { @@ -63,217 +74,6 @@ export default function LoginCallBack() { }); }; - const initDefaultData = async (office: any) => { - const rules: any[] = await new Promise((resolve: (rules: any[]) => void) => { - const defaultRules: any[] = [ - // Actes et documents - { - name: "POST deeds", - label: "Créer un template de type d'acte", - namespace: "collaborator" - }, - { - name: "PUT deeds", - label: "Modifier un type d'acte", - namespace: "collaborator" - }, - { - name: "DELETE deeds", - label: "Supprimer des types d'actes", - namespace: "collaborator" - }, - { - name: "GET deed-types", - label: "Lecture des types d'actes", - namespace: "collaborator" - }, - { - name: "POST deed-types", - label: "Création des types d'actes", - namespace: "collaborator" - }, - { - name: "PUT deed-types", - label: "Modification des types d'actes", - namespace: "collaborator" - }, - { - name: "DELETE deed-types", - label: "Suppression des types d'actes", - namespace: "collaborator" - }, - { - name: "GET document-types", - label: "Lecture des types de documents", - namespace: "collaborator" - }, - { - name: "POST document-types", - label: "Création des types de documents", - namespace: "collaborator" - }, - { - name: "PUT document-types", - label: "Modification des types de documents", - namespace: "collaborator" - }, - { - name: "DELETE document-types", - label: "Suppression des types de documents", - namespace: "collaborator" - }, - // RIB - { - name: "GET rib", - label: "Lire le RIB de l'office", - namespace: "collaborator" - }, - { - name: "POST rib", - label: "Déposer le RIB de l'office", - namespace: "collaborator" - }, - { - name: "PUT rib", - label: "Editer le RIB de l'office", - namespace: "collaborator" - }, - { - name: "DELETE rib", - label: "Supprimer le RIB de l'office", - namespace: "collaborator" - }, - // Abonnements - { - name: "GET subscriptions", - label: "Récupérer les abonnements", - namespace: "collaborator" - }, - { - name: "POST subscriptions", - label: "Inviter un collaborateur à l'abonnement", - namespace: "collaborator" - }, - { - name: "PUT subscriptions", - label: "Modifier l'abonnement", - namespace: "collaborator" - }, - { - name: "GET stripe", - label: "Gérer l'abonnement de l'office", - namespace: "collaborator" - }, - { - name: "POST stripe", - label: "Payer un abonnement", - namespace: "collaborator" - } - ]; - RuleService.getRules().then(async (processes: any[]) => { - const rules: any[] = processes.map((process: any) => process.processData); - if (rules.length === 0) { - for (let ruleData of defaultRules) { - const validatorId: string = '884cb36a346a79af8697559f16940141f068bdf1656f88fa0df0e9ecd7311fb8:0'; - rules.push((await RuleService.createRule(ruleData, validatorId)).processData); - } - } - resolve(rules); - }); - }); - - await new Promise((resolve: () => void) => { - const defaultRuleGroups: any[] = [ - { - name: "Gestion des matrices d'actes et des documents", - rules: rules - .filter((rule: any) => rule.name.includes("deeds") || rule.name.includes("deed-types") || rule.name.includes("document-types")) - .map((rule: any) => ({ uid: rule.uid })) - }, - { - name: "Intégration du RIB", - rules: rules - .filter((rule: any) => rule.name.includes("rib")) - .map((rule: any) => ({ uid: rule.uid })) - }, - { - name: "Gestion de l'abonnement", - rules: rules - .filter((rule: any) => rule.name.includes("subscriptions") || rule.name.includes("stripe")) - .map((rule: any) => ({ uid: rule.uid })) - } - ]; - RuleGroupService.getRuleGroups().then(async (processes: any[]) => { - const ruleGroups: any[] = processes.map((process: any) => process.processData); - if (ruleGroups.length === 0) { - for (let ruleGroupData of defaultRuleGroups) { - const validatorId: string = '884cb36a346a79af8697559f16940141f068bdf1656f88fa0df0e9ecd7311fb8:0'; - ruleGroups.push((await RuleGroupService.createRuleGroup(ruleGroupData, validatorId)).processData); - } - } - resolve(); - }); - }); - - await new Promise((resolve: () => void) => { - const defaultRoles: any[] = [ - { - name: 'super-admin', - label: 'Super administrateur' - }, - { - name: 'admin', - label: 'Administrateur' - }, - { - name: 'notary', - label: 'Notaire' - }, - { - name: 'default', - label: 'Utilisateur' - } - ]; - RoleService.getRoles().then(async (processes: any[]) => { - const roles: any[] = processes.map((process: any) => process.processData); - if (roles.length === 0) { - for (let roleData of defaultRoles) { - const validatorId: string = '884cb36a346a79af8697559f16940141f068bdf1656f88fa0df0e9ecd7311fb8:0'; - roles.push((await RoleService.createRole(roleData, validatorId)).processData); - } - } - resolve(); - }); - }); - - await new Promise((resolve: () => void) => { - const defaultOfficeRoles: any[] = [ - { - name: 'Notaire', - office: { - uid: office.uid - } - }, - { - name: 'Collaborateur', - office: { - uid: office.uid - } - } - ]; - OfficeRoleService.getOfficeRoles().then(async (processes: any[]) => { - const roles: any[] = processes.map((process: any) => process.processData); - if (roles.length === 0) { - for (let officeRoleData of defaultOfficeRoles) { - const validatorId: string = '884cb36a346a79af8697559f16940141f068bdf1656f88fa0df0e9ecd7311fb8:0'; - roles.push((await OfficeRoleService.createOfficeRole(officeRoleData, validatorId)).processData); - } - } - resolve(); - }); - }); - }; - const getCollaborator = async (collaboratorData: any) => { return await new Promise(async (resolve: (role: any) => void) => { const processFound: any | null = await CollaboratorService.getCollaboratorBy({ idNot: idNotUser.idNot }); @@ -360,7 +160,7 @@ export default function LoginCallBack() { return ( -
+
coffre @@ -368,7 +168,58 @@ export default function LoginCallBack() {
- + {!showProgress ? ( + + ) : ( + + + Importation des données + + {/* Progression globale */} + + + Progression globale: {Math.round(progressInfo.globalProgress)}% + + + {progressInfo.currentStep} + + + + + {/* Progression par étape */} + + + Progression de l'étape: {Math.round(progressInfo.stepProgress)}% + {progressInfo.description || ''} + + + + + )}
{ const office: any = await getOffice(idNotUser); - await initDefaultData(office); + LoaderService.getInstance().hide(); + + setShowProgress(true); + await ImportData.import(office, (info: ProgressInfo) => { + setProgressInfo(info); + }); + setShowProgress(false); + + LoaderService.getInstance().show(); const role: any = (await RoleService.getRoles()) .map((process: any) => process.processData)