webuploader 文件分片上傳 ➕node接口

webuploader 文件分片上傳javascript

爲了預研技術大文件分片上傳, 找到百度團隊維護的webuploader庫做爲基礎。github L6zt
調研策略:css

  1. 看看 webupload 前端 如何調用,看看基本demo,接着看看api,結局是貌似文檔看着不明白。
  2. 接着看看後端是如何操做,看了看 官方GitHub 裏的server 目錄,看看對應的後端處理。裏面的PHP 也看的不太清晰。

圖片描述

不知道是文檔寫的差,仍是我理解差,或者本身沒看全。總之是不太清晰的,可是比我司寫的wiki要好多了👍html


接着就是一頓蒙搞,同時借鑑前人的東西... 後端本身用 node(epxress)寫了簡單的上傳接口。前端 照着demo搞了搞結果就成功了。 只是demo裏面有其餘問題。
// node 服務器 只是爲了作測試前端

const fs = require('fs');
const path = require('path');
const md5  = require('md5');
const express = require('express');
const fileUpload = require('express-fileupload');
const bodyParser = require('body-parser');
const multipart = require('connect-multiparty');
const app = express();
const uploadFileP = path.resolve(__dirname, `./upload`);
fs.existsSync(uploadFileP) || fs.mkdirSync(uploadFileP);
app.use(bodyParser.urlencoded({ extended: true }));
app.use(fileUpload());
app.use('/assert',  express.static(path.resolve(__dirname, `./assert`)));
// 上傳 分片文件 接口
app.post('/upload', (req, res) => {
    if (!req.files) {
        return res.status(500).send('no files were uploaded');
    }
    let file = req.files.file;
    let body = req.body;
    let {chunk, chunks} = body;
    // 生成文件
    let filePath = path.resolve(__dirname, `./upload/${req.body.guid}`);
    if(!fs.existsSync(filePath)) fs.mkdirSync(filePath);
    file.mv(path.resolve(filePath, `./${chunk}.part`), function(err) {
        let done = true;
        if (err)
            return res.status(500).send(err);
        for (let i = 0 ; i < chunks; i++) {
            if(!fs.existsSync(path.resolve(filePath, `./${i}.part`))) {
                done = false;
                break;
            }
        }
        if (done === true) {
// chunked 這個參數 貌似很重要
            res.json({flag: true, chunked: true, hasError: false, ext: path.extname(file.name), chunks});
        } else {
            res.json({
                flag: true, chunked: false, hasError: false
            })
        }
    });
});
// 混合分片文件接口 (確定不能這麼寫,偷懶作的)
app.post('/merge', function (req, res) {
    const  body = req.body;
    const {guid, chunks, ext} = body;
    let md = md5(`${guid}${new Date().toString()}${chunks}`);
    let basePath  = path.resolve(__dirname, `./upload/${guid}`);
    let filePh = path.resolve(__dirname, `./upload/${md}${ext}`)
    for (let i = 0; i< chunks; i++) {
        try {
            fs.appendFileSync(filePh, fs.readFileSync(path.resolve(basePath, `./${i}.part`)));
        } catch (e) {
            return req.json({flag: 0})
        }
    }
    return res.json({flag: 1})
    
})
app.listen(3000, () => {
    console.log('sever start..')
});

// 前端資源html5

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>upload img</title>
    <link rel="stylesheet" href="/assert/css/webuploader.css" />
    <script src="/assert/js/jquery.js"></script>
    <script src="/assert/js/webuploader.html5only.js"></script>
</head>
<body>
<a href="javascript:;" id="upload">上傳</a>
<script>
    var guid = WebUploader.guid();
    var chunks = null;
    var ext = null;
    var uploader = WebUploader.create({

        auto: true,
        server: '/upload',
        pick: '#upload',
        chunked: true,
        chunkSize: 1024 * 100,
        chunkRetry: 3,
        thread: 5,
        formData: {
            guid,
        }
    });
  // 貌似檢查分片上傳 是否是 對的
    uploader.on( 'uploadAccept', function( file, response ) {
        // resopnse 後端返回數據
        if (!response.flag ) {
            return false;
        }else{
            chunks = response.chunks;
            ext = response.ext;
            return true
        }
    });
    uploader.on('uploadError', function (file, reason) {
        console.log(reason, 'error')
    });
    // 分片上傳(all)成功後 調用合併接口 
    uploader.on('uploadSuccess', function (file, reason) {
        $.ajax({
            type: 'POST',
            url: '/merge',
            data: {
                guid,
                chunks,
                ext
            },
            success (data) {
                const {flag} = data;
                console.log(flag)
            }
        })
    });
    uploader.on('error', function (type) {
        console.log(type);
    });
    uploader.on('uploadComplete', function (file) {
        console.log(file)
    })
</script>
</body>
</html>

// 效果圖
圖片描述
項目地址java

相關文章
相關標籤/搜索