diff --git a/frontend/src/FileManager/Actions/UploadFile/UploadFile.action.jsx b/frontend/src/FileManager/Actions/UploadFile/UploadFile.action.jsx index 465b2560..c96832a6 100644 --- a/frontend/src/FileManager/Actions/UploadFile/UploadFile.action.jsx +++ b/frontend/src/FileManager/Actions/UploadFile/UploadFile.action.jsx @@ -1,8 +1,10 @@ import { useRef, useState } from "react"; +import PropTypes from "prop-types"; import Button from "../../../components/Button/Button"; import { AiOutlineCloudUpload } from "react-icons/ai"; import UploadItem from "./UploadItem"; import Loader from "../../../components/Loader/Loader"; +import OverwriteConfirmDialog from "../../../components/OverwriteConfirmDialog/OverwriteConfirmDialog"; import { useFileNavigation } from "../../../contexts/FileNavigationContext"; import { getFileExtension } from "../../../utils/getFileExtension"; import { getDataSize } from "../../../utils/getDataSize"; @@ -20,6 +22,9 @@ const UploadFileAction = ({ const [files, setFiles] = useState([]); const [isDragging, setIsDragging] = useState(false); const [isUploading, setIsUploading] = useState({}); + const [showOverwriteDialog, setShowOverwriteDialog] = useState(false); + const [pendingFile, setPendingFile] = useState(null); + const [pendingFilesCallback, setPendingFilesCallback] = useState(null); const { currentFolder, currentPathFiles } = useFileNavigation(); const { onError } = useFiles(); const fileInputRef = useRef(null); @@ -41,31 +46,93 @@ const UploadFileAction = ({ const fileExists = currentPathFiles.some( (item) => item.name.toLowerCase() === file.name.toLowerCase() && !item.isDirectory ); - if (fileExists) return t("fileAlreadyExist"); + if (fileExists) { + const allowOverwrite = fileUploadConfig?.allowOverwrite || false; + if (!allowOverwrite) return t("fileAlreadyExist"); + // If allowOverwrite is true, return special marker to trigger dialog + return "CONFIRM_OVERWRITE"; + } const sizeError = maxFileSize && file.size > maxFileSize; if (sizeError) return `${t("maxUploadSize")} ${getDataSize(maxFileSize, 0)}.`; }; - const setSelectedFiles = (selectedFiles) => { - selectedFiles = selectedFiles.filter( - (item) => - !files.some((fileData) => fileData.file.name.toLowerCase() === item.name.toLowerCase()) - ); + const handleOverwriteConfirm = (selectedFiles) => { + const newFiles = selectedFiles.map((file) => { + const appendData = onFileUploading(file, currentFolder); + return { + file: file, + appendData: appendData, + }; + }); + setFiles((prev) => [...prev, ...newFiles]); + setShowOverwriteDialog(false); + setPendingFile(null); + }; - if (selectedFiles.length > 0) { + const handleOverwriteCancel = () => { + const selectedFiles = pendingFilesCallback; + if (selectedFiles) { const newFiles = selectedFiles.map((file) => { const appendData = onFileUploading(file, currentFolder); - const error = checkFileError(file); - error && onError({ type: "upload", message: error }, file); + onError({ type: "upload", message: t("uploadCanceled") }, file); return { file: file, appendData: appendData, - ...(error && { error: error }), + error: t("uploadCanceled"), }; }); setFiles((prev) => [...prev, ...newFiles]); } + setShowOverwriteDialog(false); + setPendingFile(null); + setPendingFilesCallback(null); + }; + + const setSelectedFiles = (selectedFiles) => { + selectedFiles = selectedFiles.filter( + (item) => + !files.some((fileData) => fileData.file.name.toLowerCase() === item.name.toLowerCase()) + ); + + if (selectedFiles.length > 0) { + const filesNeedingConfirmation = []; + const filesWithoutErrors = []; + + selectedFiles.forEach((file) => { + const error = checkFileError(file); + if (error === "CONFIRM_OVERWRITE") { + filesNeedingConfirmation.push(file); + } else if (!error) { + filesWithoutErrors.push(file); + } else { + // File has other errors, add with error state + const appendData = onFileUploading(file, currentFolder); + onError({ type: "upload", message: error }, file); + filesWithoutErrors.push({ file, appendData, error }); + } + }); + + // Add files without errors immediately + if (filesWithoutErrors.length > 0) { + const newFiles = filesWithoutErrors.map((fileData) => { + const appendData = onFileUploading(fileData.file || fileData, currentFolder); + return { + file: fileData.file || fileData, + appendData: appendData, + ...(fileData.error && { error: fileData.error }), + }; + }); + setFiles((prev) => [...prev, ...newFiles]); + } + + // Show confirmation dialog if there are files needing confirmation + if (filesNeedingConfirmation.length > 0) { + setPendingFile(filesNeedingConfirmation[0]); + setPendingFilesCallback(filesNeedingConfirmation); + setShowOverwriteDialog(true); + } + } }; // Todo: Also validate allowed file extensions on drop @@ -102,6 +169,14 @@ const UploadFileAction = ({ return (
{t("confirmOverwrite")}
+ {fileName &&{fileName}
} +