diff --git a/.DS_Store b/.DS_Store new file mode 100644 index 0000000..84591f9 Binary files /dev/null and b/.DS_Store differ diff --git a/auth.js b/auth.js index cea970c..cd03eca 100644 --- a/auth.js +++ b/auth.js @@ -1,6 +1,7 @@ document.addEventListener("DOMContentLoaded", function () { - document.getElementById("fileListContainer").style.display = "none"; // Hide file list on load - document.getElementById("uploadForm").style.display = "none"; // Hide upload form on load + // Hide file list and upload form on load + document.getElementById("fileListContainer").style.display = "none"; + document.getElementById("uploadFileForm").style.display = "none"; checkAuthentication(); @@ -25,7 +26,7 @@ document.addEventListener("DOMContentLoaded", function () { if (data.success) { console.log("Login successful."); document.getElementById("loginForm").style.display = "none"; - document.getElementById("uploadForm").style.display = "block"; + document.getElementById("uploadFileForm").style.display = "block"; document.getElementById("fileListContainer").style.display = "block"; checkAuthentication(); // Recheck authentication to show the file list } else { @@ -44,19 +45,18 @@ function checkAuthentication() { if (data.authenticated) { console.log("User authenticated, showing file list."); document.getElementById("loginForm").style.display = "none"; - document.getElementById("uploadForm").style.display = "block"; + document.getElementById("uploadFileForm").style.display = "block"; document.getElementById("fileListContainer").style.display = "block"; loadFileList(); } else { // Only log a warning if the file list is supposed to be shown (i.e. after a login) - if (document.getElementById("uploadForm").style.display === "block") { + if (document.getElementById("uploadFileForm").style.display === "block") { console.warn("User not authenticated."); } document.getElementById("loginForm").style.display = "block"; - document.getElementById("uploadForm").style.display = "none"; + document.getElementById("uploadFileForm").style.display = "none"; document.getElementById("fileListContainer").style.display = "none"; } }) .catch(error => console.error("Error checking authentication:", error)); } - diff --git a/copyFiles.php b/copyFiles.php new file mode 100644 index 0000000..e7884d6 --- /dev/null +++ b/copyFiles.php @@ -0,0 +1,70 @@ + "Unauthorized"]); + exit; +} + +$data = json_decode(file_get_contents("php://input"), true); +if (!$data || !isset($data['source']) || !isset($data['destination']) || !isset($data['files'])) { + echo json_encode(["error" => "Invalid request"]); + exit; +} + +$sourceFolder = trim($data['source']); +$destinationFolder = trim($data['destination']); +$files = $data['files']; + +// Build the source and destination directories. +$sourceDir = ($sourceFolder === 'root') ? UPLOAD_DIR : rtrim(UPLOAD_DIR, '/\\') . DIRECTORY_SEPARATOR . $sourceFolder . DIRECTORY_SEPARATOR; +$destDir = ($destinationFolder === 'root') ? UPLOAD_DIR : rtrim(UPLOAD_DIR, '/\\') . DIRECTORY_SEPARATOR . $destinationFolder . DIRECTORY_SEPARATOR; + +// Load metadata. +$metadataFile = "file_metadata.json"; +$metadata = file_exists($metadataFile) ? json_decode(file_get_contents($metadataFile), true) : []; + +// Ensure destination directory exists. +if (!is_dir($destDir)) { + if (!mkdir($destDir, 0775, true)) { + echo json_encode(["error" => "Could not create destination folder"]); + exit; + } +} + +$errors = []; +foreach ($files as $fileName) { + $basename = basename($fileName); + $srcPath = $sourceDir . $basename; + $destPath = $destDir . $basename; + // Build metadata keys. + $srcKey = ($sourceFolder === 'root') ? $basename : $sourceFolder . "/" . $basename; + $destKey = ($destinationFolder === 'root') ? $basename : $destinationFolder . "/" . $basename; + + if (!file_exists($srcPath)) { + $errors[] = "$basename does not exist in source."; + continue; + } + if (!copy($srcPath, $destPath)) { + $errors[] = "Failed to copy $basename"; + continue; + } + // Update metadata: if source key exists, duplicate it to destination key. + if (isset($metadata[$srcKey])) { + $metadata[$destKey] = $metadata[$srcKey]; + } +} + +if (!file_put_contents($metadataFile, json_encode($metadata, JSON_PRETTY_PRINT))) { + $errors[] = "Failed to update metadata."; +} + +if (empty($errors)) { + echo json_encode(["success" => "Files copied successfully"]); +} else { + echo json_encode(["error" => implode("; ", $errors)]); +} +?> diff --git a/createFolder.php b/createFolder.php new file mode 100644 index 0000000..72efc97 --- /dev/null +++ b/createFolder.php @@ -0,0 +1,41 @@ + false, 'error' => 'Invalid request method.']); + exit; +} + +// Get the JSON input and decode it +$input = json_decode(file_get_contents('php://input'), true); +if (!isset($input['folder'])) { + echo json_encode(['success' => false, 'error' => 'Folder name not provided.']); + exit; +} + +$folderName = trim($input['folder']); + +// Basic sanitation: allow only letters, numbers, underscores, dashes, and spaces +if (!preg_match('/^[A-Za-z0-9_\- ]+$/', $folderName)) { + echo json_encode(['success' => false, 'error' => 'Invalid folder name.']); + exit; +} + +// Build the folder path (assuming UPLOAD_DIR is defined in config.php) +$folderPath = rtrim(UPLOAD_DIR, '/\\') . DIRECTORY_SEPARATOR . $folderName; + +// Check if the folder already exists +if (file_exists($folderPath)) { + echo json_encode(['success' => false, 'error' => 'Folder already exists.']); + exit; +} + +// Attempt to create the folder +if (mkdir($folderPath, 0755, true)) { + echo json_encode(['success' => true]); +} else { + echo json_encode(['success' => false, 'error' => 'Failed to create folder.']); +} +?> diff --git a/deleteFiles.php b/deleteFiles.php index 5fb8296..5a4b17d 100644 --- a/deleteFiles.php +++ b/deleteFiles.php @@ -19,7 +19,14 @@ if (!isset($data['files']) || !is_array($data['files'])) { exit; } -$uploadDir = UPLOAD_DIR; +// Determine folder – default to 'root' +$folder = isset($data['folder']) ? trim($data['folder']) : 'root'; +if ($folder !== 'root') { + $uploadDir = rtrim(UPLOAD_DIR, '/\\') . DIRECTORY_SEPARATOR . $folder . DIRECTORY_SEPARATOR; +} else { + $uploadDir = rtrim(UPLOAD_DIR, '/\\') . DIRECTORY_SEPARATOR; +} + $deletedFiles = []; $errors = []; @@ -33,14 +40,14 @@ foreach ($data['files'] as $fileName) { $errors[] = "Failed to delete $fileName"; } } else { - $errors[] = "$fileName not found"; + // If file not found, consider it already deleted. + $deletedFiles[] = $fileName; } } -// Return response if (empty($errors)) { echo json_encode(["success" => "Files deleted: " . implode(", ", $deletedFiles)]); } else { - echo json_encode(["error" => implode("; ", $errors)]); + echo json_encode(["error" => implode("; ", $errors) . ". Files deleted: " . implode(", ", $deletedFiles)]); } ?> diff --git a/deleteFolder.php b/deleteFolder.php new file mode 100644 index 0000000..bf1a2e7 --- /dev/null +++ b/deleteFolder.php @@ -0,0 +1,46 @@ + false, 'error' => 'Invalid request method.']); + exit; +} + +// Get the JSON input and decode it +$input = json_decode(file_get_contents('php://input'), true); +if (!isset($input['folder'])) { + echo json_encode(['success' => false, 'error' => 'Folder name not provided.']); + exit; +} + +$folderName = trim($input['folder']); + +// Basic sanitation: allow only letters, numbers, underscores, dashes, and spaces +if (!preg_match('/^[A-Za-z0-9_\- ]+$/', $folderName)) { + echo json_encode(['success' => false, 'error' => 'Invalid folder name.']); + exit; +} + +$folderPath = rtrim(UPLOAD_DIR, '/\\') . DIRECTORY_SEPARATOR . $folderName; + +// Check if the folder exists and is a directory +if (!file_exists($folderPath) || !is_dir($folderPath)) { + echo json_encode(['success' => false, 'error' => 'Folder does not exist.']); + exit; +} + +// Prevent deletion if the folder is not empty +if (count(scandir($folderPath)) > 2) { + echo json_encode(['success' => false, 'error' => 'Folder is not empty.']); + exit; +} + +// Attempt to delete the folder +if (rmdir($folderPath)) { + echo json_encode(['success' => true]); +} else { + echo json_encode(['success' => false, 'error' => 'Failed to delete folder.']); +} +?> diff --git a/getFileList.php b/getFileList.php index 2cc636a..484161a 100644 --- a/getFileList.php +++ b/getFileList.php @@ -3,21 +3,23 @@ require_once 'config.php'; session_start(); header('Content-Type: application/json'); -$response = ["files" => []]; - if (!isset($_SESSION['authenticated']) || $_SESSION['authenticated'] !== true) { echo json_encode(["error" => "Unauthorized"]); exit; } -$directory = UPLOAD_DIR; -$metadataFile = "file_metadata.json"; +$folder = isset($_GET['folder']) ? trim($_GET['folder']) : 'root'; +if ($folder !== 'root') { + $directory = rtrim(UPLOAD_DIR, '/\\') . DIRECTORY_SEPARATOR . $folder; +} else { + $directory = UPLOAD_DIR; +} -// Load stored metadata +$metadataFile = "file_metadata.json"; $metadata = file_exists($metadataFile) ? json_decode(file_get_contents($metadataFile), true) : []; if (!is_dir($directory)) { - echo json_encode(["error" => "Uploads directory not found."]); + echo json_encode(["error" => "Directory not found."]); exit; } @@ -26,20 +28,16 @@ $fileList = []; foreach ($files as $file) { $filePath = $directory . DIRECTORY_SEPARATOR . $file; - if (!file_exists($filePath)) { - continue; - } + // Only include files (skip directories) + if (!is_file($filePath)) continue; + + // Build the metadata key. + $metaKey = ($folder !== 'root') ? $folder . "/" . $file : $file; - // Get "Date Modified" using filemtime() $fileDateModified = filemtime($filePath) ? date(DATE_TIME_FORMAT, filemtime($filePath)) : "Unknown"; + $fileUploadedDate = isset($metadata[$metaKey]["uploaded"]) ? $metadata[$metaKey]["uploaded"] : "Unknown"; + $fileUploader = isset($metadata[$metaKey]["uploader"]) ? $metadata[$metaKey]["uploader"] : "Unknown"; - // Get "Uploaded Date" from metadata (set during upload) - $fileUploadedDate = isset($metadata[$file]["uploaded"]) ? $metadata[$file]["uploaded"] : "Unknown"; - - // Get the uploader from metadata - $fileUploader = isset($metadata[$file]["uploader"]) ? $metadata[$file]["uploader"] : "Unknown"; - - // Calculate File Size $fileSizeBytes = filesize($filePath); if ($fileSizeBytes >= 1073741824) { $fileSizeFormatted = sprintf("%.1f GB", $fileSizeBytes / 1073741824); diff --git a/getFolderList.php b/getFolderList.php new file mode 100644 index 0000000..6912761 --- /dev/null +++ b/getFolderList.php @@ -0,0 +1,18 @@ + diff --git a/index.html b/index.html index 64cc9d7..e3bc57f 100644 --- a/index.html +++ b/index.html @@ -1,5 +1,6 @@ + @@ -12,34 +13,31 @@ - - - +
@@ -156,7 +159,7 @@
- +
@@ -174,29 +177,57 @@
- - -
-
-
-
- - + + + -
- - -
-

Uploaded Files

- -
-
- + - +
- + + diff --git a/moveFiles.php b/moveFiles.php new file mode 100644 index 0000000..b70bf1b --- /dev/null +++ b/moveFiles.php @@ -0,0 +1,71 @@ + "Unauthorized"]); + exit; +} + +$data = json_decode(file_get_contents("php://input"), true); +if (!$data || !isset($data['source']) || !isset($data['destination']) || !isset($data['files'])) { + echo json_encode(["error" => "Invalid request"]); + exit; +} + +$sourceFolder = trim($data['source']); +$destinationFolder = trim($data['destination']); +$files = $data['files']; + +// Build the source and destination directories. +$sourceDir = ($sourceFolder === 'root') ? UPLOAD_DIR : rtrim(UPLOAD_DIR, '/\\') . DIRECTORY_SEPARATOR . $sourceFolder . DIRECTORY_SEPARATOR; +$destDir = ($destinationFolder === 'root') ? UPLOAD_DIR : rtrim(UPLOAD_DIR, '/\\') . DIRECTORY_SEPARATOR . $destinationFolder . DIRECTORY_SEPARATOR; + +// Load metadata. +$metadataFile = "file_metadata.json"; +$metadata = file_exists($metadataFile) ? json_decode(file_get_contents($metadataFile), true) : []; + +// Ensure destination directory exists. +if (!is_dir($destDir)) { + if (!mkdir($destDir, 0775, true)) { + echo json_encode(["error" => "Could not create destination folder"]); + exit; + } +} + +$errors = []; +foreach ($files as $fileName) { + $basename = basename($fileName); + $srcPath = $sourceDir . $basename; + $destPath = $destDir . $basename; + // Build metadata keys. + $srcKey = ($sourceFolder === 'root') ? $basename : $sourceFolder . "/" . $basename; + $destKey = ($destinationFolder === 'root') ? $basename : $destinationFolder . "/" . $basename; + + if (!file_exists($srcPath)) { + $errors[] = "$basename does not exist in source."; + continue; + } + if (!rename($srcPath, $destPath)) { + $errors[] = "Failed to move $basename"; + continue; + } + // Update metadata: if source key exists, copy it to destination key then remove source key. + if (isset($metadata[$srcKey])) { + $metadata[$destKey] = $metadata[$srcKey]; + unset($metadata[$srcKey]); + } +} + +if (!file_put_contents($metadataFile, json_encode($metadata, JSON_PRETTY_PRINT))) { + $errors[] = "Failed to update metadata."; +} + +if (empty($errors)) { + echo json_encode(["success" => "Files moved successfully"]); +} else { + echo json_encode(["error" => implode("; ", $errors)]); +} +?> diff --git a/renameFolder.php b/renameFolder.php new file mode 100644 index 0000000..13ff730 --- /dev/null +++ b/renameFolder.php @@ -0,0 +1,48 @@ + false, 'error' => 'Invalid request method.']); + exit; +} + +// Get the JSON input and decode it +$input = json_decode(file_get_contents('php://input'), true); +if (!isset($input['oldFolder']) || !isset($input['newFolder'])) { + echo json_encode(['success' => false, 'error' => 'Required folder names not provided.']); + exit; +} + +$oldFolder = trim($input['oldFolder']); +$newFolder = trim($input['newFolder']); + +// Basic sanitation: allow only letters, numbers, underscores, dashes, and spaces +if (!preg_match('/^[A-Za-z0-9_\- ]+$/', $oldFolder) || !preg_match('/^[A-Za-z0-9_\- ]+$/', $newFolder)) { + echo json_encode(['success' => false, 'error' => 'Invalid folder name(s).']); + exit; +} + +$oldPath = rtrim(UPLOAD_DIR, '/\\') . DIRECTORY_SEPARATOR . $oldFolder; +$newPath = rtrim(UPLOAD_DIR, '/\\') . DIRECTORY_SEPARATOR . $newFolder; + +// Check if the folder to rename exists +if (!file_exists($oldPath) || !is_dir($oldPath)) { + echo json_encode(['success' => false, 'error' => 'Folder to rename does not exist.']); + exit; +} + +// Check if the new folder name already exists +if (file_exists($newPath)) { + echo json_encode(['success' => false, 'error' => 'New folder name already exists.']); + exit; +} + +// Attempt to rename the folder +if (rename($oldPath, $newPath)) { + echo json_encode(['success' => true]); +} else { + echo json_encode(['success' => false, 'error' => 'Failed to rename folder.']); +} +?> diff --git a/saveFile.php b/saveFile.php index 5a7156c..eedbacd 100644 --- a/saveFile.php +++ b/saveFile.php @@ -5,7 +5,7 @@ header('Content-Type: application/json'); $data = json_decode(file_get_contents("php://input"), true); -// Debugging: Check what data is received +// Debugging: Check what data is received. if (!$data) { echo json_encode(["error" => "No data received"]); exit; @@ -17,15 +17,18 @@ if (!isset($data["fileName"]) || !isset($data["content"])) { } $fileName = basename($data["fileName"]); -$filePath = UPLOAD_DIR . $fileName; -// Ensure only .txt and .json files are allowed -if (!preg_match("/\\.txt$|\\.json$/", $fileName)) { - echo json_encode(["error" => "Invalid file type"]); - exit; +// Determine the folder. Default to "root" if not provided. +$folder = isset($data["folder"]) ? trim($data["folder"]) : "root"; +if ($folder !== "root") { + $targetDir = rtrim(UPLOAD_DIR, '/\\') . DIRECTORY_SEPARATOR . $folder . DIRECTORY_SEPARATOR; +} else { + $targetDir = UPLOAD_DIR; } -// Try to save the file +$filePath = $targetDir . $fileName; + +// Try to save the file. if (file_put_contents($filePath, $data["content"]) !== false) { echo json_encode(["success" => "File saved successfully"]); } else { diff --git a/upload.js b/upload.js index ecefd31..3c5514c 100644 --- a/upload.js +++ b/upload.js @@ -3,7 +3,7 @@ document.addEventListener("DOMContentLoaded", function() { const progressContainer = document.getElementById("uploadProgressContainer"); const uploadForm = document.getElementById("uploadFileForm"); - // When files are selected, display a list with preview, full file name, and a progress bar. + // When files are selected, display a list with preview, file name, and a progress bar. fileInput.addEventListener("change", function() { progressContainer.innerHTML = ""; // Clear previous entries const files = fileInput.files; @@ -14,7 +14,7 @@ document.addEventListener("DOMContentLoaded", function() { Array.from(files).forEach((file, index) => { const listItem = document.createElement("li"); - listItem.style.paddingTop = "20px"; // pushes contents down + listItem.style.paddingTop = "20px"; listItem.style.marginBottom = "10px"; listItem.style.display = "flex"; listItem.style.alignItems = "center"; @@ -92,8 +92,10 @@ document.addEventListener("DOMContentLoaded", function() { Array.from(files).forEach((file, index) => { const formData = new FormData(); - // Using the original field name "file[]" as expected by upload.php + // Append the file formData.append("file[]", file); + // Append the current folder value from the hidden input + formData.append("folder", document.getElementById("uploadFolder").value); const xhr = new XMLHttpRequest(); let currentPercent = 0; @@ -121,7 +123,6 @@ document.addEventListener("DOMContentLoaded", function() { // Use the load event for final update. xhr.addEventListener("load", function() { - // Only update to Done if currentPercent is 100 if (currentPercent >= 100) { listItems[index].progressBar.innerText = "Done"; } diff --git a/upload.php b/upload.php index 0ffe450..2fdd602 100644 --- a/upload.php +++ b/upload.php @@ -8,26 +8,34 @@ if (!isset($_SESSION['authenticated']) || $_SESSION['authenticated'] !== true) { exit; } -$uploadDir = UPLOAD_DIR; -$metadataFile = "file_metadata.json"; +$folder = isset($_POST['folder']) ? trim($_POST['folder']) : 'root'; -if (!file_exists($uploadDir)) { - mkdir($uploadDir, 0775, true); +// Determine the target upload directory. +$uploadDir = UPLOAD_DIR; +if ($folder !== 'root') { + $uploadDir = rtrim(UPLOAD_DIR, '/\\') . DIRECTORY_SEPARATOR . $folder . DIRECTORY_SEPARATOR; + if (!is_dir($uploadDir)) { + mkdir($uploadDir, 0775, true); + } +} else { + if (!is_dir($uploadDir)) { + mkdir($uploadDir, 0775, true); + } } -// Load existing metadata +$metadataFile = "file_metadata.json"; $metadata = file_exists($metadataFile) ? json_decode(file_get_contents($metadataFile), true) : []; $metadataChanged = false; foreach ($_FILES["file"]["name"] as $index => $fileName) { - $filePath = $uploadDir . basename($fileName); - - if (move_uploaded_file($_FILES["file"]["tmp_name"][$index], $filePath)) { - // Store "Uploaded Date" and "Uploader" only if not already stored - if (!isset($metadata[$fileName])) { - $uploadedDate = date(DATE_TIME_FORMAT); // Store only the first upload time + $targetPath = $uploadDir . basename($fileName); + if (move_uploaded_file($_FILES["file"]["tmp_name"][$index], $targetPath)) { + // Use a metadata key that includes the folder if not in root. + $metaKey = ($folder !== 'root') ? $folder . "/" . $fileName : $fileName; + if (!isset($metadata[$metaKey])) { + $uploadedDate = date(DATE_TIME_FORMAT); $uploader = $_SESSION['username'] ?? "Unknown"; - $metadata[$fileName] = [ + $metadata[$metaKey] = [ "uploaded" => $uploadedDate, "uploader" => $uploader ]; @@ -39,7 +47,6 @@ foreach ($_FILES["file"]["name"] as $index => $fileName) { } } -// Save metadata only if modified if ($metadataChanged) { file_put_contents($metadataFile, json_encode($metadata, JSON_PRETTY_PRINT)); }