打包解压工具

package-file-h5

github地址:https://github.com/Nangxif/package-file-h5   (可以给个星星满足我的虚荣心吗)

一、开发背景

这个工具是我在很无聊很无聊的时候写的,一开始只是想实现一下上传本地文件或者文件夹,然后在前端生成目录树。后来想想,要不就再弄个打包的吧,于是就有了这个没用的工具……其实这个工具有个缺点,就是,还打包不了gzip和rar,这个我有空再搞搞吧!

二、接口

baseUrl:http://localhost:3000/api

  • POST /relativePath
  • POST /package
  • POST /newpackage
  • POST /decompression
  • GET /downloadpackage
  • GET /downloaddecompression

具体接口文档请看https://github.com/Nangxif/package-file-server

三、部分实现思路

一开始,我能获取到的数据是这样的

{
    file0: "src/App.vue"
    file1: "src/main.js"
    file2: "src/assets/logo.png"
    file3: "src/api/index.js"
}

但是,ElementUI的树形组件el-tree需要的数据格式是这样的

[{
    label: '一级 1',
    children: [{
      label: '二级 1-1',
      children: [{
        label: '三级 1-1-1'
      }]
    }]
  }, {
    label: '一级 2',
    children: [{
      label: '二级 2-1',
      children: [{
        label: '三级 2-1-1'
      }]
    }]
  }
 }]

所以第一步,先把上面能拿到的数据通过下面这个方法转换成这种形式

/*
文件夹用对象表示,文件用空字符表示
[
  { src: { "App.vue": "" } },
  { src: { "main.js": "" } },
  { src: { assets: { "logo.png": "" } } },
  { src: { api: { "index.js": "" } } },
];*/
Object.values(this.relativePath).forEach(item => {
  // 这里拿到的是a/b/c.vue这样的结构
  let target = {};
  item.split('/').reduce((total, val, index) => {
    if (index < item.split('/').length - 1) {
      total[val] = {};
      return total[val];
    } else {
      total[val] = '';
      return target;
    }
  }, target);
  // 这样生成的数据结构是[{a:{b:{c.vue:""}}}]
  this.fileArray.push(target);
});

但是这样的话,其实有好多个元素对象里面都有同样的src键,这个时候我们要进行合并

this.fileArray.forEach((item, index) => {
  let abstObj = { ...this.fileObj };
  this.fileObj = this.deWeight(
    item,
    Object.values(this.relativePath)[index].split('/'),
    undefined,
    abstObj
  );
});


deWeight(obj, format, level = 0, targetObj) {
  let levelObj = obj[format[level]];
  if (level < format.length - 1) {
    if (targetObj[format[level]]) {
      return {
        ...targetObj,
        [format[level]]: this.deWeight(
          levelObj,
          format,
          level + 1,
          targetObj[format[level]]
        )
      };
    } else {
      // 如果没有重复了,直接返回全部对象
      return {
        ...targetObj,
        [format[level]]: levelObj
      };
    }
  } else {
    return {
      ...targetObj,
      [format[level]]: levelObj
    };
  }
}

然后拿到的数据是这样的

{
  src: {
    "App.vue": "",
    "main.js": "",
    assets: { "logo.png": "" },
    api: { "index.js": "" },
  }
}

最后一步

// 去重完成之后生成文件夹数组
this.filedata = [
  {
    label: `download${time.timestamp}.zip`,
    children: this.creatFileArray(this.fileObj)
  }
];


creatFileArray(target) {
  let targetArr = [];
  Object.keys(target).forEach((item, index) => {
    if (typeof Object.values(target)[index] == 'object') {
      targetArr.push({
        label: item,
        children: this.creatFileArray(Object.values(target)[index])
      });
    } else {
      targetArr.push({
        label: item
      });
    }
  });
  return targetArr;
}

emmm,代码没有怎么解释,里面好多递归,作者很懒,就写到这……

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值