0
点赞
收藏
分享

微信扫一扫

前端vue通过oss直接上传文件到阿里云

以沫的窝 2022-03-10 阅读 59

通过后端获取oss需要的参数

 

注意:oss时要加上headers,否则vue会报错

 原码:uploadByOss.vue

<template>
  <div>
    <el-upload
      ref="uploadMutiple"
      action=""
      :show-file-list="false"
      :multiple="true"
      :limit="limit"
      :before-upload="beforeUpload"
       :on-exceed="handleExceed"
    >
      <el-button slot="trigger" size="small" type="primary" :disabled="btnDisabled">{{
        btnText
      }}</el-button>
      <!-- 上传提示 -->
      <div class="el-upload__tip" slot="tip" v-if="showTip">
        支持格式
        <template v-if="fileType"> {{ fileType.join("/") }},</template>
        <template v-if="fileSize"> 单个文件不能超过 {{ fileSize }}MB,</template>
        <template v-if="limit"> 且最大数量为 {{ limit }} </template>
      </div>
    </el-upload>
    <el-table
      :data="fileList"
      style="width: 100%"
      v-if="fileList.length > 0"
      border
    >
      <el-table-column prop="name" :show-overflow-tooltip="true" label="名称">
        <template slot-scope="scope">
          <i style="color: #409eff" class="el-icon-s-order" />{{
            scope.row.name
          }}
        </template>
      </el-table-column>
      <el-table-column prop="name" label="是否成功">
        <template slot-scope="scope">
          <template v-if="scope.row.status === 'success'">上传成功!</template>
          <template v-else-if="scope.row.status === 'error'"
            >上传失败!</template
          >
          <el-progress v-else :percentage="scope.row.progress" />
        </template>
      </el-table-column>
      <el-table-column prop="size" label="大小(KB)" />
      <el-table-column prop="name" :show-overflow-tooltip="true" label="操作">
        <template slot-scope="scope">
          <el-button type="primary" size="mini" @click="handleRemove(scope.row)" :disabled="btnDisabled"
            >删除</el-button
          >
        </template>
      </el-table-column>
    </el-table>
  </div>
</template>

<script>
import { StsTokens } from "@/api/general/companyTask/index";

import OSS from "ali-oss";
export default {
  name: "upload_by_oss",
  props: {
    // 按钮文字
    btnText: {
      type: String,
      default: "上传文件",
    },
    // 文件上传路径
    fileURL: {
      type: String,
      default: "",
    },
    // 文件上传个数
    limit: {
      type: Number,
    },
    // 文件类型
    fileType: {
      type: Array,
      // default: () => ["png", "jpg", "jpeg"],
    },
    // 文件大小
    fileSize: {
      type: Number,
    },
    // 是否显示提示
    isShowTip: {
      type: Boolean,
      default: true,
    },
     // 按钮是否禁用
    btnDisabled:{
         type: Boolean,
      default: false,
    },
     // 文件list
    fileList:{
      type:Array,
      default:[]
    }
  },
  data() {
    return {
      // oss参数
      ossParams: undefined,
      // oss对象
      client: undefined,
    };
  },
  computed: {
    // 是否显示提示
    showTip() {
      return this.isShowTip && (this.fileType || this.fileSize || this.limit);
    },
  },
  created() {
    // 获取oss参数
    StsTokens({}).then((response) => {
      this.ossParams = response;
      this.client = new OSS({
        region: this.ossParams.region,
        accessKeyId: this.ossParams.accessKeyId,
        accessKeySecret: this.ossParams.accessKeySecret,
        stsToken: this.ossParams.securityToken,
        bucket: this.ossParams.bucket,
        endpoint: this.ossParams.endpoint,
      });
    });
  },
  methods: {
     handleExceed(files, fileList) {
      this.$message.error(
        `当前限制选择${this.limit}个文件,本次选择了 ${files.length} 个文件,共选择了 ${
          files.length + this.fileList.length
        } 个文件`
      );
    },
    beforeUpload(file) {
      // 校验文件数量
      if (this.fileList.length >= this.limit) {
        this.$message.error(`当前限制选择${this.limit}个文件`);
        return false;
      }
      // 校检文件类型
      if (this.fileType) {
        let fileExtension = "";
        if (file.name.lastIndexOf(".") > -1) {
          fileExtension = file.name.slice(file.name.lastIndexOf(".") + 1);
        }
        const isTypeOk = this.fileType.some((type) => {
          if (file.type.indexOf(type) > -1) return true;
          if (fileExtension && fileExtension.indexOf(type) > -1) return true;
          return false;
        });
        if (!isTypeOk) {
          this.$message.error(
            `文件格式不正确, 请上传${this.fileType.join("/")}格式文件!`
          );
          return false;
        }
      }
      // 校检文件大小
      if (this.fileSize) {
        const isLt = file.size / 1024 / 1024 < this.fileSize;
        if (!isLt) {
          this.$message.error(`上传文件大小不能超过 ${this.fileSize} MB!`);
          return false;
        }
      }
      // zwy后添加 ↑

      const fileList = {};
      for (const key in file) {
        fileList[key] = file[key];
      }
      // status:uploading、success、error 文件上传状态
      // progress 文件上传进度
      this.fileList.push({ ...fileList, progress: 0, status: "uploading" });
      this.sendFile(file, (parms) => {
        this.showProgress(fileList, parms);
      });
      // 阻止 el-upload的默认上传
      return false;
    },
    showProgress(file, parms) {
      const { progress, status } = parms;
      const arr = [...this.fileList].map((items) => {
        if (items.uid === file.uid) {
          items.progress = progress;
          items.status = status;
        }
        return items;
      });
      this.fileList = [...arr];
    },

    /**
     * 删除文件
     */
    handleRemove(file) {
      this.fileList.forEach((item, index) => {
        if (item.uid == file.uid) {
          this.fileList.splice(index, 1);
        }
      });
      this.$emit("uploadFile", this.fileList);
    },
    sendFile(file, callback) {
      var that = this;
      //  这里是OSS
      let progress = 0;
      var f = file;
      const Name = f.name;
      const fileName = Name.substr(0, Name.indexOf("."));
      const suffix = Name.substr(Name.indexOf("."));
      const obj = this.timestamp("{y}{m}{d}{h}{i}{s}");
      const storeAs =
        this.ossParams.bucket +
        "/" +
        this.timestamp("{y}-{m}-{d}") +
        this.fileURL +
        "/" +
        fileName +
        obj +
        suffix; //  路径+时间戳+后缀名
      this.client
        .multipartUpload(storeAs, f, {
          progress: function (p, checkpoint) {
            // 如果需要显示上传进度则需要使用progress函数
            progress = Math.floor(p * 100);
            callback({ progress, status: "uploading" });
          },
          headers: {
            "Content-Disposition": `attachment; filename=${encodeURIComponent(
              Name
            )}`,
            "Cache-Control": "public, no-cache",
          },
        })
        .then(function (result) {
          that.fileList[that.fileList.length - 1].ossUrl =
            result.res.requestUrls[0];
          callback({ progress, status: "success" });
          that.$emit("uploadFile", that.fileList);
        });
    },
    //  时间戳
    timestamp: function (format) {
      const time = new Date();
      const y = time.getFullYear();
      const m = time.getMonth() + 1;
      const d = time.getDate();
      const h = time.getHours();
      const mm = time.getMinutes();
      const s = time.getSeconds();
      const ms = time.getMilliseconds();
      if (format == "{y}{m}{d}{h}{i}{s}") {
        return (
          "" +
          y +
          this.Add0(m) +
          this.Add0(d) +
          this.Add0(h) +
          this.Add0(mm) +
          this.Add0(s) +
          this.Add0(ms)
        );
      }
      if (format == "{y}-{m}-{d}") {
        return y + "-" + this.Add0(m) + "-" + this.Add0(d);
      }
    },
    Add0: function (m) {
      return m < 10 ? "0" + m : m;
    },
  },
};
</script>

调用组件:

<upload-by-oss
                @uploadFile="getUploadFile"
                :fileType="['rar', 'zip', 'doc', 'docx', 'pdf']"
                :fileSize="0"
                :limit="5"
                :fileURL="fileURL"
                :fileList="form.companyUrlList ? form.companyUrlList : []"
                :btnDisabled="title == '添加公司任务' ? false : true"
              ></upload-by-oss>
举报

相关推荐

0 条评论