From 57db7392e56919bd9334b1a1dc6bae5670f58d53 Mon Sep 17 00:00:00 2001 From: Clement Brousseau Date: Thu, 12 Dec 2024 13:51:20 +0100 Subject: [PATCH 1/5] =?UTF-8?q?feat:=20pouvoir=20sortir=20de=20la=20modale?= =?UTF-8?q?=20d'int=C3=A9gration=20lorsqu'une=20des=20validations=20=C3=A9?= =?UTF-8?q?choue=20#582?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../DatasheetUploadIntegrationDialog.tsx | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+) diff --git a/assets/entrepot/pages/datasheet/DatasheetNew/DatasheetUploadIntegration/DatasheetUploadIntegrationDialog.tsx b/assets/entrepot/pages/datasheet/DatasheetNew/DatasheetUploadIntegration/DatasheetUploadIntegrationDialog.tsx index 7c16fd68..7e220246 100644 --- a/assets/entrepot/pages/datasheet/DatasheetNew/DatasheetUploadIntegration/DatasheetUploadIntegrationDialog.tsx +++ b/assets/entrepot/pages/datasheet/DatasheetNew/DatasheetUploadIntegration/DatasheetUploadIntegrationDialog.tsx @@ -205,6 +205,24 @@ const DatasheetUploadIntegrationDialog: FC )} + {integrationStatus === "at_least_one_failure" && uploadQuery.data?.tags.datasheet_name !== undefined && ( +
+ +
+ )} + {integrationStatus === "at_least_one_failure" && uploadQuery.data?.tags?.vectordb_id !== undefined && (
Date: Tue, 17 Dec 2024 14:02:36 +0100 Subject: [PATCH 2/5] =?UTF-8?q?feat:=20pouvoir=20acc=C3=A9der=20aux=20rais?= =?UTF-8?q?ons=20de=20l'=C3=A9chec=20d'une=20validation=20#583?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- assets/@types/app.ts | 7 ++ assets/entrepot/api/upload.ts | 9 ++ .../DatasetListTab/UnfinishedUploadList.tsx | 7 +- .../StoredDataDetails/DeliveryDetails.tsx | 95 +++++++++++++++++++ .../PreviewTab/DeliveryPreviewTab.tsx | 42 ++++++++ .../StoredDataDetails/ReportTab/ReportTab.tsx | 41 ++++---- assets/modules/entrepot/RQKeys.ts | 1 + assets/router/RouterRenderer.tsx | 3 + assets/router/router.ts | 7 ++ src/Controller/Entrepot/UploadController.php | 29 ++++++ 10 files changed, 219 insertions(+), 22 deletions(-) create mode 100644 assets/entrepot/pages/stored_data/StoredDataDetails/DeliveryDetails.tsx create mode 100644 assets/entrepot/pages/stored_data/StoredDataDetails/PreviewTab/DeliveryPreviewTab.tsx diff --git a/assets/@types/app.ts b/assets/@types/app.ts index 38f8b1b9..340405fe 100644 --- a/assets/@types/app.ts +++ b/assets/@types/app.ts @@ -259,6 +259,13 @@ export type StoredDataReport = { processing_executions: StoredDataReportProcessingExecution[]; }; +export type DeliveryReport = { + input_upload: Upload & { + file_tree: UploadTree; + checks: CheckDetailed[]; + }; +}; + export type StoredDataReportProcessingExecution = ProcessingExecution & { output: ProcessingExecutionOutputStoredDataDto; logs?: CheckOrProcessingExecutionLogs; diff --git a/assets/entrepot/api/upload.ts b/assets/entrepot/api/upload.ts index 43cf55ab..625c1bc4 100644 --- a/assets/entrepot/api/upload.ts +++ b/assets/entrepot/api/upload.ts @@ -1,5 +1,6 @@ import SymfonyRouting from "../../modules/Routing"; import { jsonFetch } from "../../modules/jsonFetch"; +import { DeliveryReport } from "../../@types/app"; import { Upload, UploadTree, UploadTypeEnum } from "../../@types/app"; const getList = (datastoreId: string, type?: UploadTypeEnum, otherOptions: RequestInit = {}) => { @@ -61,6 +62,13 @@ const remove = (datastoreId: string, uploadId: string) => { return jsonFetch(url, { method: "DELETE" }); }; +const getDeliveryReport = (datastoreId: string, uploadId: string, otherOptions: RequestInit = {}) => { + const url = SymfonyRouting.generate("cartesgouvfr_api_upload_get_delivery_report", { datastoreId, uploadId }); + return jsonFetch(url, { + ...otherOptions, + }); +}; + const upload = { getList, add, @@ -69,6 +77,7 @@ const upload = { pingIntegrationProgress, getFileTree, remove, + getDeliveryReport, }; export default upload; diff --git a/assets/entrepot/pages/datasheet/DatasheetView/DatasetListTab/UnfinishedUploadList.tsx b/assets/entrepot/pages/datasheet/DatasheetView/DatasetListTab/UnfinishedUploadList.tsx index 5ed363fe..ea2a8b7a 100644 --- a/assets/entrepot/pages/datasheet/DatasheetView/DatasetListTab/UnfinishedUploadList.tsx +++ b/assets/entrepot/pages/datasheet/DatasheetView/DatasetListTab/UnfinishedUploadList.tsx @@ -28,8 +28,11 @@ const UnfinishedUploadList: FC = ({ datastoreId, uplo
- +
diff --git a/assets/entrepot/pages/stored_data/StoredDataDetails/DeliveryDetails.tsx b/assets/entrepot/pages/stored_data/StoredDataDetails/DeliveryDetails.tsx new file mode 100644 index 00000000..2b5dbdcd --- /dev/null +++ b/assets/entrepot/pages/stored_data/StoredDataDetails/DeliveryDetails.tsx @@ -0,0 +1,95 @@ +import { fr } from "@codegouvfr/react-dsfr"; +import Alert from "@codegouvfr/react-dsfr/Alert"; +import Button from "@codegouvfr/react-dsfr/Button"; +import Tabs from "@codegouvfr/react-dsfr/Tabs"; +import { useQuery } from "@tanstack/react-query"; +import { FC, useMemo } from "react"; + +import { DeliveryReport } from "../../../../@types/app"; +import DatastoreLayout from "../../../../components/Layout/DatastoreLayout"; +import LoadingIcon from "../../../../components/Utils/LoadingIcon"; +import RQKeys from "../../../../modules/entrepot/RQKeys"; +import { CartesApiException } from "../../../../modules/jsonFetch"; +import { routes } from "../../../../router/router"; +import api from "../../../api"; +import DeliveryPreviewTab from "./PreviewTab/DeliveryPreviewTab"; +import ReportTab from "./ReportTab/ReportTab"; + +type DeliveryDetailsProps = { + datastoreId: string; + uploadDataId: string; +}; + +const DeliveryDetails: FC = ({ datastoreId, uploadDataId }) => { + const datastoreQuery = useQuery({ + queryKey: RQKeys.datastore(datastoreId), + queryFn: ({ signal }) => api.datastore.get(datastoreId, { signal }), + staleTime: 3600000, + }); + + const reportQuery = useQuery({ + queryKey: RQKeys.datastore_delivery_report(datastoreId, uploadDataId), + queryFn: ({ signal }) => api.upload.getDeliveryReport(datastoreId, uploadDataId, { signal }), + staleTime: 3600000, + }); + + const datasheetName = useMemo(() => reportQuery?.data?.input_upload?.tags?.datasheet_name, [reportQuery?.data?.input_upload?.tags?.datasheet_name]); + + return ( + +
+ {datasheetName ? ( +
+ +
+ {reportQuery.isError && } +
+ {reportQuery?.data?.input_upload?.name && ( +
+

{reportQuery?.data?.input_upload?.name}

+
+ )} + + {reportQuery.data && ( +
+
+ , + }, + { + label: "Rapport de génération", + content: , + }, + ]} + /> +
+
+ )} +
+ ); +}; + +export default DeliveryDetails; diff --git a/assets/entrepot/pages/stored_data/StoredDataDetails/PreviewTab/DeliveryPreviewTab.tsx b/assets/entrepot/pages/stored_data/StoredDataDetails/PreviewTab/DeliveryPreviewTab.tsx new file mode 100644 index 00000000..473e43e1 --- /dev/null +++ b/assets/entrepot/pages/stored_data/StoredDataDetails/PreviewTab/DeliveryPreviewTab.tsx @@ -0,0 +1,42 @@ +import { fr } from "@codegouvfr/react-dsfr"; +import Accordion from "@codegouvfr/react-dsfr/Accordion"; +import { FC } from "react"; + +import { DeliveryReport } from "../../../../../@types/app"; +import { niceBytes } from "../../../../../utils"; +import ReportStatusBadge from "../ReportTab/ReportStatusBadge"; + +type DeliveryPreviewTabProps = { + reportData: DeliveryReport; +}; + +const DeliveryPreviewTab: FC = ({ reportData }) => { + const uploadData = reportData.input_upload; + + return ( + +
    +
  • + Nom : {uploadData.name} +
  • +
  • + Identifiant technique : {uploadData._id} +
  • +
  • + Projection : {uploadData.srs} +
  • +
  • + Statut : {} +
  • +
  • + Taille : {uploadData.size && niceBytes(uploadData.size.toString())} +
  • +
  • + Type : {uploadData.type} +
  • +
+
+ ); +}; + +export default DeliveryPreviewTab; diff --git a/assets/entrepot/pages/stored_data/StoredDataDetails/ReportTab/ReportTab.tsx b/assets/entrepot/pages/stored_data/StoredDataDetails/ReportTab/ReportTab.tsx index 11f2f809..67c06129 100644 --- a/assets/entrepot/pages/stored_data/StoredDataDetails/ReportTab/ReportTab.tsx +++ b/assets/entrepot/pages/stored_data/StoredDataDetails/ReportTab/ReportTab.tsx @@ -3,7 +3,7 @@ import Accordion from "@codegouvfr/react-dsfr/Accordion"; import { UseQueryResult } from "@tanstack/react-query"; import { FC } from "react"; -import { StoredDataReport as ReportTab } from "../../../../../@types/app"; +import { DeliveryReport, StoredDataReport as ReportTab } from "../../../../../@types/app"; import { CheckingExecutionDetailResponseDtoStatusEnum, ProcessingExecutionDetailResponseDtoStatusEnum } from "../../../../../@types/entrepot"; import { CartesApiException } from "../../../../../modules/jsonFetch"; import { niceBytes } from "../../../../../utils"; @@ -14,7 +14,7 @@ import UploadFileTree from "./UploadFileTree"; type ReportTabProps = { datastoreName?: string; - reportQuery: UseQueryResult; + reportQuery: UseQueryResult; }; const ReportTab: FC = ({ datastoreName, reportQuery }) => { @@ -65,24 +65,25 @@ const ReportTab: FC = ({ datastoreName, reportQuery }) => { ))} - {reportQuery?.data.processing_executions.map((procExec) => ( - -

{`${step++}. Traitement : ${procExec.processing.name}`}

- - - } - defaultExpanded={[ - ProcessingExecutionDetailResponseDtoStatusEnum.FAILURE, - ProcessingExecutionDetailResponseDtoStatusEnum.ABORTED, - ].includes(procExec.status)} - > - -
- ))} + {"processing_executions" in reportQuery.data && + reportQuery?.data.processing_executions.map((procExec) => ( + +

{`${step++}. Traitement : ${procExec.processing.name}`}

+ + + } + defaultExpanded={[ + ProcessingExecutionDetailResponseDtoStatusEnum.FAILURE, + ProcessingExecutionDetailResponseDtoStatusEnum.ABORTED, + ].includes(procExec.status)} + > + +
+ ))} ) ); diff --git a/assets/modules/entrepot/RQKeys.ts b/assets/modules/entrepot/RQKeys.ts index 8159a76d..d5ab9221 100644 --- a/assets/modules/entrepot/RQKeys.ts +++ b/assets/modules/entrepot/RQKeys.ts @@ -20,6 +20,7 @@ const RQKeys = { datastore_stored_data: (datastoreId: string, storedDataId: string): string[] => ["datastore", datastoreId, "stored_data", storedDataId], datastore_stored_data_uses: (datastoreId: string, storedDataId: string): string[] => ["datastore", datastoreId, "stored_data", storedDataId, "uses"], datastore_stored_data_report: (datastoreId: string, storedDataId: string): string[] => ["datastore", datastoreId, "stored_data", storedDataId, "report"], + datastore_delivery_report: (datastoreId: string, uploadDataId: string): string[] => ["datastore", datastoreId, "upload_data", uploadDataId, "report"], datastore_datasheet_list: (datastoreId: string): string[] => ["datastore", datastoreId, "datasheet"], datastore_datasheet: (datastoreId: string, dataName: string): string[] => ["datastore", datastoreId, "datasheet", dataName], diff --git a/assets/router/RouterRenderer.tsx b/assets/router/RouterRenderer.tsx index 5fd209aa..c7f70fbd 100644 --- a/assets/router/RouterRenderer.tsx +++ b/assets/router/RouterRenderer.tsx @@ -43,6 +43,7 @@ const DatasheetUploadIntegrationPage = lazy(() => import("../entrepot/pages/data const DatasheetView = lazy(() => import("../entrepot/pages/datasheet/DatasheetView/DatasheetView")); const StoredDataDetails = lazy(() => import("../entrepot/pages/stored_data/StoredDataDetails/StoredDataDetails")); +const DeliveryReport = lazy(() => import("../entrepot/pages/stored_data/StoredDataDetails/DeliveryDetails")); const DatastoreCreationForm = lazy(() => import("../entrepot/pages/datastore/DatastoreCreationForm")); const Confirm = lazy(() => import("../entrepot/pages/datastore/Confirmation")); @@ -157,6 +158,8 @@ const RouterRenderer: FC = () => { return ; case "datastore_stored_data_details": return ; + case "datastore_delivery_details": + return ; case "datastore_wfs_service_new": return ; case "datastore_wfs_service_edit": diff --git a/assets/router/router.ts b/assets/router/router.ts index 57280d63..03851e33 100644 --- a/assets/router/router.ts +++ b/assets/router/router.ts @@ -141,6 +141,13 @@ const routeDefs = { }, (p) => `${appRoot}/entrepot/${p.datastoreId}/donnees/${p.storedDataId}/details` ), + datastore_delivery_details: defineRoute( + { + datastoreId: param.path.string, + uploadDataId: param.path.string, + }, + (p) => `${appRoot}/entrepot/${p.datastoreId}/donnees/${p.uploadDataId}/rapport` + ), // Creer et publier un service WFS datastore_wfs_service_new: defineRoute( diff --git a/src/Controller/Entrepot/UploadController.php b/src/Controller/Entrepot/UploadController.php index e04e0eaa..2a08120e 100644 --- a/src/Controller/Entrepot/UploadController.php +++ b/src/Controller/Entrepot/UploadController.php @@ -308,4 +308,33 @@ public function delete(string $datastoreId, string $uploadId): JsonResponse throw new CartesApiException($ex->getMessage(), JsonResponse::HTTP_INTERNAL_SERVER_ERROR); } } + + #[Route('/{uploadId}/delivery-report', name: 'get_delivery_report', methods: ['GET'])] + public function getDeliveryReport(string $datastoreId, string $uploadId): JsonResponse + { + try { + // Récupération des détails de l'upload ayant échoué + $inputUpload = $this->uploadApiService->get($datastoreId, $uploadId); + $inputUpload['file_tree'] = $this->uploadApiService->getFileTree($datastoreId, $inputUpload['_id']); + $inputUpload['checks'] = []; + $uploadChecks = $this->uploadApiService->getCheckExecutions($datastoreId, $inputUpload['_id']); + + foreach ($uploadChecks as &$checkType) { + foreach ($checkType as &$checkExecution) { + $checkExecution = array_merge($checkExecution, $this->uploadApiService->getCheckExecution($datastoreId, $checkExecution['_id'])); + try { + $checkExecution['logs'] = $this->uploadApiService->getCheckExecutionLogs($datastoreId, $checkExecution['_id']); + } catch (ApiException $ex) { + } + $inputUpload['checks'][] = $checkExecution; + } + } + + return $this->json([ + 'input_upload' => $inputUpload, + ]); + } catch (ApiException $ex) { + throw new CartesApiException($ex->getMessage(), $ex->getStatusCode(), $ex->getDetails()); + } + } } From e299e02264df4976eaac6ab472634a2d46728b24 Mon Sep 17 00:00:00 2001 From: Clement Brousseau Date: Tue, 17 Dec 2024 15:39:54 +0100 Subject: [PATCH 3/5] =?UTF-8?q?feat:=20compl=C3=A9ter=20le=20fil=20d'arian?= =?UTF-8?q?e=20de=20la=20route=20de=20reprise=20d'int=C3=A9gration=20#584?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../DatasetListTab/UnfinishedUploadList.tsx | 7 ++++++- .../StoredDataDetails/DeliveryDetails.tsx | 8 ++++---- assets/i18n/Breadcrumb.tsx | 3 +++ assets/modules/entrepot/breadcrumbs.ts | 15 +++++++++++++++ assets/router/router.ts | 1 + 5 files changed, 29 insertions(+), 5 deletions(-) diff --git a/assets/entrepot/pages/datasheet/DatasheetView/DatasetListTab/UnfinishedUploadList.tsx b/assets/entrepot/pages/datasheet/DatasheetView/DatasetListTab/UnfinishedUploadList.tsx index ea2a8b7a..3f305545 100644 --- a/assets/entrepot/pages/datasheet/DatasheetView/DatasetListTab/UnfinishedUploadList.tsx +++ b/assets/entrepot/pages/datasheet/DatasheetView/DatasetListTab/UnfinishedUploadList.tsx @@ -28,7 +28,12 @@ const UnfinishedUploadList: FC = ({ datastoreId, uplo
-
- -
- {reportQuery.isError && } -
{reportQuery?.data?.input_upload?.name && (

{reportQuery?.data?.input_upload?.name}

)} +
+ {reportQuery.isError && } +
+ {reportQuery.data && (
diff --git a/assets/i18n/Breadcrumb.tsx b/assets/i18n/Breadcrumb.tsx index e9f133a4..0c41b2a0 100644 --- a/assets/i18n/Breadcrumb.tsx +++ b/assets/i18n/Breadcrumb.tsx @@ -32,6 +32,7 @@ export const { i18n } = declareComponentKeys< | "upload" | "datastore_datasheet_upload_integration" | "datastore_stored_data_details" + | "datastore_delivery_details" | "datastore_wfs_service_new" | "datastore_wfs_service_edit" | "datastore_wms_vector_service_new" @@ -74,6 +75,7 @@ export const BreadcrumbFrTranslations: Translations<"fr">["Breadcrumb"] = { upload: "Téléversement", datastore_datasheet_upload_integration: "Intégration de données", datastore_stored_data_details: "Détails d'une donnée stockée", + datastore_delivery_details: "Détails d'une livraison", datastore_wfs_service_new: "Création d'un service WFS", datastore_wfs_service_edit: "Modification d'un service WFS", datastore_wms_vector_service_new: "Création d'un service WMS", @@ -116,6 +118,7 @@ export const BreadcrumbEnTranslations: Translations<"en">["Breadcrumb"] = { upload: "Upload", datastore_datasheet_upload_integration: "Data integration", datastore_stored_data_details: "Details of stored data", + datastore_delivery_details: "Details of delivery", datastore_wfs_service_new: "Create a WFS service", datastore_wfs_service_edit: "Modify WFS service", datastore_wms_vector_service_new: "Create a WMS service", diff --git a/assets/modules/entrepot/breadcrumbs.ts b/assets/modules/entrepot/breadcrumbs.ts index acd87397..4ea6e79d 100644 --- a/assets/modules/entrepot/breadcrumbs.ts +++ b/assets/modules/entrepot/breadcrumbs.ts @@ -161,6 +161,21 @@ const getBreadcrumb = (route: Route, datastore?: Datastore): Brea }); } return { ...defaultProps, currentPageLabel: t("datastore_stored_data_details") }; + case "datastore_delivery_details": + defaultProps.segments = [ + ...defaultProps.segments, + ...[ + { label: t("dashboard_pro"), linkProps: routes.dashboard_pro().link }, + { label: datastore?.name, linkProps: routes.datasheet_list({ datastoreId: route.params.datastoreId }).link }, + ], + ]; + if ("datasheetName" in route.params && route.params.datasheetName) { + defaultProps.segments.push({ + label: route.params.datasheetName, + linkProps: routes.datastore_datasheet_view({ datastoreId: route.params.datastoreId, datasheetName: route.params.datasheetName }).link, + }); + } + return { ...defaultProps, currentPageLabel: t("datastore_delivery_details") }; case "datastore_wfs_service_new": case "datastore_wfs_service_edit": diff --git a/assets/router/router.ts b/assets/router/router.ts index 03851e33..e897c482 100644 --- a/assets/router/router.ts +++ b/assets/router/router.ts @@ -145,6 +145,7 @@ const routeDefs = { { datastoreId: param.path.string, uploadDataId: param.path.string, + datasheetName: param.query.optional.string, }, (p) => `${appRoot}/entrepot/${p.datastoreId}/donnees/${p.uploadDataId}/rapport` ), From e23c6c47f480664377156d3381f25ee9bf43f80d Mon Sep 17 00:00:00 2001 From: Clement Brousseau Date: Tue, 17 Dec 2024 16:15:04 +0100 Subject: [PATCH 4/5] =?UTF-8?q?feat:=20ajout=20d'une=20balise=20'=C3=A9cho?= =?UTF-8?q?u=C3=A9e'=20dans=20le=20cas=20d'une=20livraison=20non=20termin?= =?UTF-8?q?=C3=A9e=20#585?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../DatasheetView/DatasetListTab/UnfinishedUploadList.tsx | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/assets/entrepot/pages/datasheet/DatasheetView/DatasetListTab/UnfinishedUploadList.tsx b/assets/entrepot/pages/datasheet/DatasheetView/DatasetListTab/UnfinishedUploadList.tsx index 3f305545..e1ad47d0 100644 --- a/assets/entrepot/pages/datasheet/DatasheetView/DatasetListTab/UnfinishedUploadList.tsx +++ b/assets/entrepot/pages/datasheet/DatasheetView/DatasetListTab/UnfinishedUploadList.tsx @@ -5,6 +5,7 @@ import { symToStr } from "tsafe/symToStr"; import { routes } from "../../../../../router/router"; import { Upload } from "../../../../../@types/app"; +import ReportStatusBadge from "../../../stored_data/StoredDataDetails/ReportTab/ReportStatusBadge"; type UnfinishedUploadListProps = { datastoreId: string; @@ -23,7 +24,10 @@ const UnfinishedUploadList: FC = ({ datastoreId, uplo {uploadList?.map((upload) => (
-
{upload.name}
+
+ {upload.name} + +
From 2caaef83d691a469a48206732ce2aed3784c2a73 Mon Sep 17 00:00:00 2001 From: Clement Brousseau Date: Fri, 20 Dec 2024 17:13:04 +0100 Subject: [PATCH 5/5] =?UTF-8?q?feat:=20pouvoir=20supprimer=20une=20livrais?= =?UTF-8?q?on=20en=20=C3=A9chec=20#588?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../DatasetListTab/DatasetListTab.tsx | 7 +- .../DatasetListTab/UnfinishedUploadList.tsx | 137 +++++++++++++++--- .../datasheet/DatasheetView/DatasheetView.tsx | 25 ++++ assets/router/router.ts | 2 +- 4 files changed, 146 insertions(+), 25 deletions(-) diff --git a/assets/entrepot/pages/datasheet/DatasheetView/DatasetListTab/DatasetListTab.tsx b/assets/entrepot/pages/datasheet/DatasheetView/DatasetListTab/DatasetListTab.tsx index 1e87ed88..bbc1d128 100644 --- a/assets/entrepot/pages/datasheet/DatasheetView/DatasetListTab/DatasetListTab.tsx +++ b/assets/entrepot/pages/datasheet/DatasheetView/DatasetListTab/DatasetListTab.tsx @@ -39,7 +39,12 @@ const DatasetListTab: FC = ({ datastoreId, datasheet }) => { {unfinishedUploads && unfinishedUploads.length > 0 && (
- +
)} diff --git a/assets/entrepot/pages/datasheet/DatasheetView/DatasetListTab/UnfinishedUploadList.tsx b/assets/entrepot/pages/datasheet/DatasheetView/DatasetListTab/UnfinishedUploadList.tsx index e1ad47d0..8a0387b5 100644 --- a/assets/entrepot/pages/datasheet/DatasheetView/DatasetListTab/UnfinishedUploadList.tsx +++ b/assets/entrepot/pages/datasheet/DatasheetView/DatasetListTab/UnfinishedUploadList.tsx @@ -2,16 +2,47 @@ import { fr } from "@codegouvfr/react-dsfr"; import Button from "@codegouvfr/react-dsfr/Button"; import { FC, memo } from "react"; import { symToStr } from "tsafe/symToStr"; +import { useMutation, useQueryClient } from "@tanstack/react-query"; +import RQKeys from "../../../../../modules/entrepot/RQKeys"; +import api from "../../../../api"; +import { type DatasheetDetailed } from "../../../../../@types/app"; import { routes } from "../../../../../router/router"; import { Upload } from "../../../../../@types/app"; import ReportStatusBadge from "../../../stored_data/StoredDataDetails/ReportTab/ReportStatusBadge"; +import { deleteDeliveryConfirmModal } from "../DatasheetView"; +import Wait from "../../../../../components/Utils/Wait"; +import LoadingIcon from "../../../../../components/Utils/LoadingIcon"; +import { useTranslation } from "../../../../../i18n/i18n"; type UnfinishedUploadListProps = { datastoreId: string; uploadList?: Upload[]; + nbPublications: number; + datasheet: DatasheetDetailed; }; -const UnfinishedUploadList: FC = ({ datastoreId, uploadList }) => { + +const UnfinishedUploadList: FC = ({ datastoreId, uploadList, nbPublications, datasheet }) => { + const { t } = useTranslation("DatastoreManageStorage"); + + const queryClient = useQueryClient(); + + const isLastUpload = (uploadList: Upload[]): boolean => { + return uploadList.length === 1 && nbPublications === 0; + }; + + const deleteUnfinishedUpload = useMutation({ + mutationFn: (uploadId: string) => api.upload.remove(datastoreId, uploadId), + onSuccess(uploadId) { + queryClient.setQueryData(RQKeys.datastore_datasheet(datastoreId, datasheet.name), (datasheet: { upload_list: Upload[] }) => { + return { + ...datasheet, + upload_list: datasheet.upload_list.filter((upload) => upload._id !== uploadId), + }; + }); + }, + }); + return ( <>
@@ -21,32 +52,92 @@ const UnfinishedUploadList: FC = ({ datastoreId, uplo
- {uploadList?.map((upload) => ( -
-
-
- {upload.name} - + {uploadList?.map((upload) => { + const integrationProgress = JSON.parse(upload.tags.integration_progress || "{}"); + const steps = Object.entries(integrationProgress); + const failureCase = steps.some(([, status]) => status === "failed"); + + return ( +
+
+
+ {upload.name} + {failureCase ? ( + + ) : ( + + )} +
-
-
-
- - +
+
+ {failureCase ? ( + <> + + + + ) : ( + <> + + + + )} +
+
+
+ ); + })} + {deleteUnfinishedUpload.isPending && ( + +
+
+ +
{t("storage.upload.deletion.in_progress")}
-
- ))} + + )} ); }; diff --git a/assets/entrepot/pages/datasheet/DatasheetView/DatasheetView.tsx b/assets/entrepot/pages/datasheet/DatasheetView/DatasheetView.tsx index 9272596b..c9c49522 100644 --- a/assets/entrepot/pages/datasheet/DatasheetView/DatasheetView.tsx +++ b/assets/entrepot/pages/datasheet/DatasheetView/DatasheetView.tsx @@ -31,6 +31,11 @@ const deleteDataConfirmModal = createModal({ isOpenedByDefault: false, }); +export const deleteDeliveryConfirmModal = createModal({ + id: "delete-delivery-confirm-modal", + isOpenedByDefault: false, +}); + export enum DatasheetViewActiveTabEnum { Metadata = "metadata", Dataset = "dataset", @@ -260,6 +265,26 @@ const DatasheetView: FC = ({ datastoreId, datasheetName }) = , document.body )} + {createPortal( + datasheetDeleteMutation.mutate(), + priority: "primary", + }, + ]} + > + En supprimant cette livraison, la fiche de données {datasheetName} sera supprimée. + , + document.body + )} ); diff --git a/assets/router/router.ts b/assets/router/router.ts index e897c482..1983ec44 100644 --- a/assets/router/router.ts +++ b/assets/router/router.ts @@ -147,7 +147,7 @@ const routeDefs = { uploadDataId: param.path.string, datasheetName: param.query.optional.string, }, - (p) => `${appRoot}/entrepot/${p.datastoreId}/donnees/${p.uploadDataId}/rapport` + (p) => `${appRoot}/entrepot/${p.datastoreId}/livraisons/${p.uploadDataId}/rapport` ), // Creer et publier un service WFS