ZBLOG

Document

要在上传文件时使用 chunked 传输编码(Transfer-Encoding: chunked)将文件分块传输给上游服务器,你需要在前端和后端都进行相应配置。以下是完整解决方案:

前端修改(纯HTML无法直接控制)

由于HTML表单本身无法直接控制chunked传输,需要通过JavaScript实现:

  1. <!DOCTYPE html>
  2. <html lang="en">
  3. <head>
  4. <meta charset="UTF-8">
  5. <meta name="viewport" content="width=device-width, initial-scale=1.0">
  6. <title>Chunked Upload Demo</title>
  7. </head>
  8. <body>
  9. <input type="file" id="fileInput">
  10. <button onclick="uploadFile()">提交</button>
  11. <script>
  12. async function uploadFile() {
  13. const file = document.getElementById('fileInput').files[0];
  14. if (!file) return;
  15. const chunkSize = 1024 * 1024; // 1MB每块
  16. const totalChunks = Math.ceil(file.size / chunkSize);
  17. for (let i = 0; i < totalChunks; i++) {
  18. const start = i * chunkSize;
  19. const end = Math.min(start + chunkSize, file.size);
  20. const chunk = file.slice(start, end);
  21. await fetch('/upload', {
  22. method: 'POST',
  23. headers: {
  24. 'Content-Type': 'application/octet-stream',
  25. 'X-Chunk-Index': i,
  26. 'X-Total-Chunks': totalChunks,
  27. 'X-File-Name': encodeURIComponent(file.name),
  28. 'X-File-Size': file.size
  29. },
  30. body: chunk
  31. });
  32. console.log(`Uploaded chunk ${i + 1}/${totalChunks}`);
  33. }
  34. console.log('Upload complete!');
  35. }
  36. </script>
  37. </body>
  38. </html>

后端处理示例(Node.js版)

  1. const express = require('express');
  2. const fs = require('fs');
  3. const path = require('path');
  4. const app = express();
  5. app.use(express.json());
  6. app.post('/upload', async (req, res) => {
  7. try {
  8. const fileName = decodeURIComponent(req.headers['x-file-name']);
  9. const tempDir = './temp';
  10. if (!fs.existsSync(tempDir)) {
  11. fs.mkdirSync(tempDir);
  12. }
  13. const tempFilePath = path.join(tempDir, fileName + '.part');
  14. // 追加写入分块数据
  15. req.on('data', chunk => {
  16. fs.appendFileSync(tempFilePath, chunk);
  17. });
  18. req.on('end', () => {
  19. if (parseInt(req.headers['x-chunk-index']) === parseInt(req.headers['x-total-chunks']) - 1) {
  20. // 如果是最后一个分块则重命名文件
  21. fs.renameSync(tempFilePath, path.join(tempDir, fileName));
  22. res.status(200).send('Upload complete');
  23. } else {
  24. res.status(200).send('Chunk received');
  25. }
  26. });
  27. } catch (err) {
  28. res.status(500).send(err.message);
  29. }
  30. });
  31. app.listen(3000, () => console.log('Server running on port 3000'));

关键点说明:

  1. 前端实现

    • 使用fetch APIBlob.slice()方法手动分块
    • 每个分块通过独立的HTTP请求发送
  2. 后端实现

    • Node.js会自动处理chunked传输编码的请求体
    • 通过监听data事件获取分片数据
  3. 注意事项

    • Nginx默认支持chunked传输,但可能需要调整client_max_body_size
    • Tomcat等Java容器需要确保配置了maxSwallowSize

如果需要完整的商业级解决方案,零声教育提供包含以下内容的高性能网络课程:

  1. HTTP协议深度解析
  2. Chunked传输编码优化
  3. 断点续传实现
  4. 大文件上传加速方案


    内容由零声教学AI助手提供,问题来源于学员提问

本站部分文章来源于网络,版权归原作者所有,如有侵权请联系站长删除。
转载请注明出处:https://golang.0voice.com/?id=23291

分享:
扫描分享到社交APP
上一篇
下一篇
发表列表
游客 游客
此处应有掌声~
评论列表

还没有评论,快来说点什么吧~

联系我们

在线咨询: 点击这里给我发消息

微信号:3007537140

上班时间: 10:30-22:30

关注我们
x

注册

已经有帐号?