Procházet zdrojové kódy

文件上传与下载

xuxinyi před 1 rokem
rodič
revize
e763bcbae1

binární
img.png


+ 102 - 0
src/main/java/com/example/demo/controllers/FileController.java

@@ -0,0 +1,102 @@
+package com.example.demo.controllers;
+
+import org.springframework.http.HttpStatus;
+import org.springframework.http.ResponseEntity;
+import org.springframework.web.bind.annotation.*;
+import org.springframework.web.multipart.MultipartFile;
+
+import java.io.File;
+import java.io.IOException;
+import java.nio.file.Files;
+import java.nio.file.Path;
+import java.nio.file.Paths;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.stream.Collectors;
+
+@RestController
+@RequestMapping("/api/files")
+public class FileController {
+
+    private final String uploadDir = "uploads/";
+
+    // 添加删除文件的接口
+    @DeleteMapping("/delete/{filename}")
+    public ResponseEntity<String> deleteFile(@PathVariable String filename) {
+        try {
+            Path path = Paths.get(uploadDir + filename);
+            Files.deleteIfExists(path);
+            return ResponseEntity.ok("文件删除成功: " + filename);
+        } catch (IOException e) {
+            return ResponseEntity.status(HttpStatus.INTERNAL_SERVER_ERROR).body("文件删除失败");
+        }
+    }
+
+    // 获取文件列表,支持分页和搜索
+    @GetMapping
+    public ResponseEntity<List<String>> listFiles(
+            @RequestParam(value = "page", defaultValue = "0") int page,
+            @RequestParam(value = "size", defaultValue = "10") int size,
+            @RequestParam(value = "search", required = false) String search) {
+
+        try {
+            File folder = new File(uploadDir);
+            File[] listOfFiles = folder.listFiles();
+            List<String> fileNames = new ArrayList<>();
+
+            if (listOfFiles != null) {
+                for (File file : listOfFiles) {
+                    if (file.isFile()) {
+                        fileNames.add(file.getName());
+                    }
+                }
+            }
+
+            // 根据搜索条件过滤文件
+            if (search != null && !search.isEmpty()) {
+                fileNames = fileNames.stream()
+                        .filter(name -> name.contains(search))
+                        .collect(Collectors.toList());
+            }
+
+            // 计算分页
+            int start = Math.min(page * size, fileNames.size());
+            int end = Math.min(start + size, fileNames.size());
+            List<String> paginatedFiles = fileNames.subList(start, end);
+
+            return ResponseEntity.ok(paginatedFiles);
+        } catch (Exception e) {
+            return ResponseEntity.status(HttpStatus.INTERNAL_SERVER_ERROR).body(null);
+        }
+    }
+
+    // 文件上传
+    @PostMapping("/upload")
+    public ResponseEntity<String> uploadFile(@RequestParam("file") MultipartFile file) {
+        try {
+            if (file.isEmpty()) {
+                return ResponseEntity.status(HttpStatus.BAD_REQUEST).body("请上传文件");
+            }
+            Path path = Paths.get(uploadDir + file.getOriginalFilename());
+            Files.createDirectories(path.getParent());
+            file.transferTo(path);
+            return ResponseEntity.ok("文件上传成功: " + file.getOriginalFilename());
+        } catch (IOException e) {
+            return ResponseEntity.status(HttpStatus.INTERNAL_SERVER_ERROR).body("文件上传失败");
+        }
+    }
+
+    // 文件下载
+    @GetMapping("/download/{filename}")
+    public ResponseEntity<byte[]> downloadFile(@PathVariable String filename) {
+        try {
+            Path path = Paths.get(uploadDir + filename);
+            byte[] data = Files.readAllBytes(path);
+            return ResponseEntity.ok()
+                    .header("Content-Disposition", "attachment; filename=\"" + filename + "\"")
+                    .body(data);
+        } catch (IOException e) {
+            return ResponseEntity.status(HttpStatus.NOT_FOUND).body(null);
+        }
+    }
+}

+ 7 - 1
src/main/resources/application.yml

@@ -1,4 +1,9 @@
 spring:
+  servlet:
+    multipart:
+      enabled: true
+      max-file-size: -1
+      max-request-size: -1
   application:
     name: Server
 
@@ -6,4 +11,5 @@ spring:
     url: jdbc:mysql://60.204.139.57:3306/college_poi
     username: root
     password: 1
-    driver-class-name: com.mysql.cj.jdbc.Driver
+    driver-class-name: com.mysql.cj.jdbc.Driver
+

+ 210 - 0
src/main/resources/static/index.html

@@ -0,0 +1,210 @@
+<!DOCTYPE html>
+<html lang="zh">
+<head>
+    <meta charset="UTF-8">
+    <meta name="viewport" content="width=device-width, initial-scale=1.0">
+    <title>文件管理系统</title>
+    <style>
+        body {
+            font-family: Arial, sans-serif;
+            background-color: #f4f4f4;
+            margin: 0;
+            padding: 20px;
+        }
+        h1 {
+            text-align: center;
+            color: #333;
+        }
+        h2 {
+            color: #555;
+            margin-top: 20px;
+        }
+        ul {
+            list-style-type: none;
+            padding: 0;
+        }
+        li {
+            background: #fff;
+            margin: 5px 0;
+            padding: 15px;
+            border-radius: 5px;
+            display: flex;
+            justify-content: space-between;
+            align-items: center;
+            box-shadow: 0 2px 5px rgba(0, 0, 0, 0.1);
+        }
+        button {
+            background-color: #28a745;
+            color: white;
+            border: none;
+            padding: 8px 12px;
+            border-radius: 5px;
+            cursor: pointer;
+            transition: background-color 0.3s;
+        }
+        button:hover {
+            background-color: #218838;
+        }
+        input[type="file"], input[type="text"] {
+            margin-top: 20px;
+            display: block;
+            width: 100%;
+            padding: 10px;
+            border: 1px solid #ccc;
+            border-radius: 5px;
+        }
+        .upload-container {
+            margin-top: 20px;
+        }
+        .pagination {
+            margin-top: 20px;
+            display: flex;
+            justify-content: center;
+        }
+        .page-button {
+            margin: 0 5px;
+            padding: 8px 12px;
+            border: 1px solid #ccc;
+            border-radius: 5px;
+            cursor: pointer;
+            background: #007bff;
+            color: white;
+            transition: background-color 0.3s;
+        }
+        .page-button:hover {
+            background-color: #0056b3;
+        }
+        .button-container {
+            display: flex;
+            gap: 10px;
+        }
+    </style>
+</head>
+<body>
+<h1>文件管理系统</h1>
+<h2>当前文件列表</h2>
+
+<input type="text" id="searchInput" placeholder="搜索文件..." />
+<button onclick="searchFiles()">搜索</button>
+
+<ul id="fileList"></ul>
+
+<div class="pagination" id="pagination"></div>
+
+<div class="upload-container">
+    <input type="file" id="fileInput" />
+    <button onclick="uploadFile()">上传文件</button>
+</div>
+
+<script>
+    let currentPage = 0;
+    const pageSize = 6;
+
+    function loadFileList() {
+        fetch(`/api/files?page=${currentPage}&size=${pageSize}`)
+            .then(response => response.json())
+            .then(files => {
+                const fileList = document.getElementById('fileList');
+                fileList.innerHTML = '';
+                files.forEach(file => {
+                    const li = document.createElement('li');
+                    li.innerHTML = `${file}
+                                    <div class="button-container">
+                                        <button onclick="downloadFile('${file}')">下载</button>
+                                        <button onclick="deleteFile('${file}')">删除</button>
+                                    </div>`;
+                    fileList.appendChild(li);
+                });
+                loadPagination();
+            })
+            .catch(error => console.error('Error:', error));
+    }
+
+    function uploadFile() {
+        const fileInput = document.getElementById('fileInput');
+        const file = fileInput.files[0];
+        const formData = new FormData();
+        formData.append('file', file);
+
+        fetch('/api/files/upload', {
+            method: 'POST',
+            body: formData
+        })
+            .then(response => response.text())
+            .then(text => {
+                alert(text);
+                loadFileList();
+                fileInput.value = '';
+            })
+            .catch(error => console.error('Error:', error));
+    }
+
+    function downloadFile(filename) {
+        window.location.href = '/api/files/download/' + filename;
+    }
+
+    function deleteFile(filename) {
+        if (confirm(`确定要删除文件 ${filename} 吗?`)) {
+            fetch(`/api/files/delete/${filename}`, {
+                method: 'DELETE'
+            })
+                .then(response => response.text())
+                .then(text => {
+                    alert(text);
+                    loadFileList();
+                })
+                .catch(error => console.error('Error:', error));
+        }
+    }
+
+    function searchFiles() {
+        const searchQuery = document.getElementById('searchInput').value;
+        fetch(`/api/files?search=${searchQuery}&page=0&size=${pageSize}`)
+            .then(response => response.json())
+            .then(files => {
+                const fileList = document.getElementById('fileList');
+                fileList.innerHTML = '';
+                files.forEach(file => {
+                    const li = document.createElement('li');
+                    li.innerHTML = `${file}
+                                    <div class="button-container">
+                                        <button onclick="downloadFile('${file}')">下载</button>
+                                        <button onclick="deleteFile('${file}')">删除</button>
+                                    </div>`;
+                    fileList.appendChild(li);
+                });
+                currentPage = 0;
+                loadPagination();
+            })
+            .catch(error => console.error('Error:', error));
+    }
+
+    function loadPagination() {
+        const pagination = document.getElementById('pagination');
+        pagination.innerHTML = '';
+        const prevButton = document.createElement('button');
+        prevButton.innerHTML = '上一页';
+        prevButton.classList.add('page-button');
+        prevButton.onclick = () => {
+            if (currentPage > 0) {
+                currentPage--;
+                loadFileList();
+            }
+        };
+        pagination.appendChild(prevButton);
+
+        const nextButton = document.createElement('button');
+        nextButton.innerHTML = '下一页';
+        nextButton.classList.add('page-button');
+        nextButton.onclick = () => {
+            currentPage++;
+            loadFileList();
+        };
+        pagination.appendChild(nextButton);
+    }
+
+    // 页面加载时加载文件列表
+    loadFileList();
+</script>
+</body>
+</html>

+ 9 - 0
上传文件.md

@@ -0,0 +1,9 @@
+1.请求类型:选择 POST。
+2.URL:输入 http://localhost:8080/api/files/upload。
+3.Body:
+选择 form-data。
+在 Key 列中,输入 file,并确保类型为 File(通常会有一个下拉框选择)。
+在 Value 列中,选择你要上传的文件。
+上传文件
+![img.png](img.png)
+4.取消默认的文件大小限制