分享一个自己弄的FTP上传脚本

项目的远程资源是放在ftp上面的,每次上传资源都需要手动拖拽上去,于是就弄了一个自动构建插件,一键构建,然后资源自动上传,需要先安装fpt模块,参考ftp;设置完以后,直接就能用;

    const ftp = require('ftp');//连接FTP
    const path = require('path');
    const client = new ftp();
    const fs = require('fs');
    //本地文件夹路径;
    const localDirPath = '/test/';
    //远程地址,打开ftp以后的地址,不需要加入host;
    const remotePath = '/';
    const uploadFiles = [];
    const mkDirPromiseArr = [];

    const connectionProperties = {
        host: '',                       //ftp地址;
        user: '',                       //用户名;
        password: '',                   //密码;
        port: 21                        //端口;
    };
    client.connect(connectionProperties);
    client.on('ready', () => {
        console.log('ftp client is ready');
        start();
    });

    async function start() {
        const { err: ea, dir } = await cwd(remotePath);//此处应对err做处理
        if (ea) {
            client.mkdir(remotePath, true, (err) => {
                if (err) {
                    console.log('创建' + remotePath + '文件夹失败');
                    upload();
                } else {
                    console.log('创建' + remotePath + '成功');
                    upload();
                }
            });
        } else {
            upload();
        }

        function upload() {
            const filesPath = { files: [] };
            getDirAllFilePath(localDirPath, filesPath);
            remoteMkDir(filesPath, '');
            console.log('准备上传...');
            setTimeout(() => {
                Promise.all(mkDirPromiseArr).then(() => {
                    console.log('开始上传...');
                    const tasks = uploadFile();
                    runPromiseArray(tasks).then(() => {
                        client.end();
                        console.warn('上传完成~');
                    });
                });
            }, 3000);
        }
    }


    // 获取本地的文件地址和路径;
    function getDirAllFilePath(paths, parent) {
        const files = fs.readdirSync(paths);
        files.forEach(item => {
            if (item != '.DS_Store') {
                const path = `${paths}/${item}`;
                if (isDir(path)) {
                    getDirAllFilePath(path, parent[item] = { files: [] });
                } else if (isFile(path)) {
                    parent.files.push(item);
                }
            }
        })
    }


    //创建远程确实的文件夹;
    async function remoteMkDir(obj, _path) {
        for (const key in obj) {
            if (key === 'files') {
                for (let i = 0, len = obj[key].length; i < len; i++) {
                    const promise = new Promise(async resolve => {
                        let p = '';
                        if (_path) {
                            p = _path + '/';
                        }
                        const filePathName = p + obj[key][i];
                        uploadFiles.push({ path: filePathName, fileName: obj[key][i] });
                        const ph = remotePath + filePathName.substring(0, filePathName.lastIndexOf('/') + 1);
                        let { err: ea, dir } = await cwd(ph);//此处应对err做处理
                        if (ea) {
                            client.mkdir(ph, true, (err) => {
                                if (err) {
                                    console.log('mkdir' + ph + 'err', err);
                                    resolve(null);
                                    return;
                                }
                                console.log('mkdir ' + ph + '  success');
                                resolve(null);
                            });
                        } else {
                            resolve(null);
                        }
                    });

                    mkDirPromiseArr.push(promise);
                }
            } else {
                let p = '';
                if (_path) {
                    p = _path + '/';
                }
                remoteMkDir(obj[key], p + key);
            }
        }
    }

    //上传文件;
    function uploadFile() {
        const tasks = [];
        const resourcesPath = localDirPath;
        //目标路径文件夹;
        const checkPath = remotePath;
        for (let i = 0, len = uploadFiles.length; i < len; i++) {
            const task = () => {
                return new Promise(async (resolve, reject) => {
                    const _path = uploadFiles[i].path;
                    const targetPath = checkPath + _path;
                    const putPath = resourcesPath + '/' + _path;
                    const dirpath = path.dirname(targetPath);
                    const fileName = path.basename(targetPath);

                    client.cwd(dirpath, (cwdErr, dir) => {
                        client.pwd((pwdErr, cwd) => {
                            if (pwdErr) {
                                resolve(pwdErr)
                            } else {
                                client.get(fileName, (err, res) => {
                                    if (res) {
                                        console.log(`${targetPath} =====================已经存在了`);
                                        resolve(true);
                                    } else {
                                        const rs = fs.createReadStream(putPath);
                                        client.put(rs, fileName, (putErr, data) => {
                                            if (putErr) {
                                                resolve(err);
                                            } else {
                                                console.log(targetPath + '文件上传成功');
                                                resolve(true);
                                            }
                                        })
                                    }
                                });
                            }
                        });
                    })
                });
            }
            tasks.push(task);
        }
        return tasks;
    }

    //执行Promise的队列动作;
    function runPromiseArray(parray) { //这个方法可以放到G里
        let p = Promise.resolve();
        for (let promise of parray) {
            p = p.then(promise);
        }
        return p;
    }

    //切换目录
    async function cwd(dirpath) {
        return new Promise((resolve, reject) => {
            client.cwd(dirpath, (err, dir) => {
                resolve({ err: err, dir: dir });
            })
        });
    }

    function isFile(filepath) {  //判断是否是文件 Boolean
        let stat = fs.statSync(filepath)
        return stat.isFile()
    }

    function isDir(filepath) {  //判断是否是文件夹 Boolean
        let stat = fs.statSync(filepath);
        return stat.isDirectory();
    }
4赞

大佬牛逼,文件太多了上传太慢,有没有方法上传zip后执行zip解压?

有没有方法上传zip后执行zip解压?

前端可以执行压缩上传 云端得支持解压