diff --git a/endpoints/upload.php b/endpoints/upload.php new file mode 100644 index 0000000..cf2d47a --- /dev/null +++ b/endpoints/upload.php @@ -0,0 +1,14 @@ + listFiles(), + "getAllFiles" => listFiles(false), + "UploadFiles" => parseIncomingFiles(), + default => ["Status" => "Fail", "message" => "Invalid action"], + }; +} \ No newline at end of file diff --git a/lib/upload.php b/lib/upload.php new file mode 100644 index 0000000..0e361a0 --- /dev/null +++ b/lib/upload.php @@ -0,0 +1,180 @@ + $valueArr) { + if (is_array($valueArr)) { // file input "multiple" + foreach ($valueArr as $i => $value) { + $filesByInput[$i][$key] = $value; + } + } else { // -> string, normal file input + $filesByInput[] = $infoArr; + break; + } + } + $files2 = array_merge($files2, $filesByInput); + } + $files3 = []; + foreach ($files2 as $file) { // let's filter empty & errors + if (!$file['error']) $files3[] = $file; + } + return $files3; +} + +function saveUploadedFileInDatabase($filePath, $fileType):bool +{ + global $mysqli; + $stmt = $mysqli->prepare("INSERT INTO Files (Path, Type, UploadedBy, UploadedAt) VALUES (?, ?, ?, NOW())"); + $stmt->bind_param("ssi", $filePath, $fileType, $_SESSION["ID"]); + $stmt->execute(); + $stat = $stmt->affected_rows > 0; + $stmt->close(); + return $stat; +} + +function doImageUpload($inFile, $outFile): bool +{ + // Create Imagick object + $imagick = new Imagick($inFile); + + // Set the desired format for reencoding (WebP) + $imagick->setImageFormat('webp'); + + // Remove non-essential metadata + $imagick->stripImage(); + + // Write the reencoded image to the output file + $imagick->writeImage($outFile); + + // Destroy the Imagick object to free up resources + $imagick->destroy(); + + // Check if the reencoding was successful + if (file_exists($outFile)) { + return saveUploadedFileInDatabase($outFile, 'image/webp'); + } else { + return false; + } +} + +function listFiles($onlyMine = true):array +{ + $output = ["Status" => "Fail"]; + require_once "lib/account.php"; + if(($onlyMine && isLoggedIn()) || (!$onlyMine && isModerator())) { + global $mysqli; + $query = "SELECT ID, Path, Type, UploadedAt, UploadedBy FROM Files"; + + if($onlyMine){ + $query .= " WHERE UploadedBy = ?"; + } + + $stmt = $mysqli->prepare($query); + if($onlyMine) { + $stmt->bind_param("i", $_SESSION["ID"]); + } + + $id = 0; + $path = ""; + $type = ""; + $uploadedAt = ""; + $uploadedBy = 0; + + $stmt->bind_result($id, $path, $type, $uploadedAt, $uploadedBy); + + $stmt->execute(); + + // Fetch the results into the bound variables + while ($stmt->fetch()) { + $files[] = [ + 'ID' => $id, + 'Path' => $path, + 'Type' => $type, + 'UploadedAt' => $uploadedAt, + 'UploadedBy' => $uploadedBy, + ]; + } + + // Check if any results were fetched + if (!empty($files)) { + $output["Status"] = "Success"; + $output["Files"] = $files; + } + + $stmt->close(); + } + + return $output; + +} + +function parseIncomingFiles(): array +{ + $incomingFiles = getIncomingFiles(); + $success = true; + + foreach ($incomingFiles as $incomingFile) { + if ($incomingFile["error"] == 0 && is_file($incomingFile["tmp_name"])) { + $type = explode("/", $incomingFile["type"]); + switch ($type) { + case "image": + $imgFname = pathinfo($incomingFile["name"], PATHINFO_FILENAME); + $uploadPath = getUploadPath("image", $imgFname); + if(!empty($uploadPath)) { + if (!doImageUpload($incomingFile["tmp_name"], $uploadPath)) { + $success = false; + } + } + else{ + $success = false; + } + break; + } + } + } + $output = ["Status" => "Fail"]; + if($success){ + $output["Status"] = "Success"; + } + return $output; +} + +function getUploadPath($type = "unknown", $filename = "hehe"): string +{ + $type = makePathSafe($type); + $id = makePathSafe($_SESSION["ID"]); + $date = makePathSafe(date("Y/m/d")); + $filename = makePathSafe($filename); + $extension = match ($type) { + 'image' => 'webp', + default => 'dummy', + }; + if($extension != "dummy") { + return "uploads/$type/$id/$date/$filename.$extension"; + } + else { + return ""; + } +} \ No newline at end of file