element UI upload组件-前端直接上传阿里云OSS阿里云官方有示例代码可以参考 我是将上传组件统一封装了下
我是将上传组件统一封装了下,下面是一些开发过程...
一、安装插件
1、npm i --save ali-oss
2、引用方法
const OSS = require("ali-oss");
二、实例使用
<el-upload
ref="upload"
:disabled="isonlyShow"
action="#"
:http-request="handleUpload"
:file-list="itemFileList"
:on-exceed="handleExceed"
:before-upload="beforeUploadHandle"
:on-success="successHandle"
:on-error="ErrorHandle"
:on-preview="previewHandle"
:on-remove="removeHandle"
class="upload-demo"
list-type="picture"
drag
>
<!-- 上传按钮 -->
<i class="el-icon-upload" />
<div class="el-upload__text">将文件拖到此处,或<em>点击上传</em></div>
<!-- 上传提示 -->
<div class="el-upload__tip" slot="tip" v-if="showTip">
请上传图片文件,
<template v-if="fileSize">
大小不超过<b style="color: #f56c6c">{{ fileSize }}MB,</b>
</template>
</div>
</el-upload>
不使用组件原有的上传方式,action="#",采用自定义上传方式:http-request="handleUpload",在自定义的方法里加入oss上传逻辑;
获取临时凭证
// 校验临时凭证时效并获取
async getOssToken() {
let flag = this.isCredentialsExpired(this.credentialsObj);
if (flag) {
// 失效
let tokenRes = await this.refreshSTSTsToken();
if (tokenRes.success) {
this.credentialsObj = tokenRes.data;
return true;
} else {
this.$message.error(tokenRes.msg);
return false;
}
} else {
return true;
}
},
// 刷新临时凭证
refreshSTSTsToken() {
return getAlibabaStsToken().then((res) => res);
},
下面是一些开发过程中的小tips
我这里因为不想去重新发改fileList的值(会造成显示列表上闪一下有重新渲染的动画),得到上传结果后主动触发了组件成功或者失败的方法,:on-success,:on-error就能监听到结果;也可以得到返回值直接处理逻辑,不用触发组件的方法;
后端开放了公共浏览权限,所以oss返回的链接能直接访问到;如果没有开放的话,就要通过client.signatureUrl转化成真实路径,也就是链接上会带上参数token 去访问;
client .put(
${file.name}
, file)这里是传文件名,文件。我这里put(${nowDate}/${uuidName}_${file.name}
, file)是通过/去创建或者存入文件夹内,YYYY/MM/DD/${file.name}就是存入2024文件夹下07月文件夹下的19日文件夹下,没有相应的文件夹会自动创建
同一文件夹下文件名重复的文件会自动覆盖,要注意(如覆盖官方会有历史版本,具体就要仔细研究下);这里生成uuid拼接文件名防止文件名重复;
// 文件上传
async handleUpload(option) {
let flag = await this.getOssToken();
if (flag) this.ossup(option, this.credentialsObj);
},
async ossup(option, credentials) {
let file = option.file;
let OSS = require("ali-oss");
const client = new OSS({
// endpoint: "oss.lhinspec.com",
// cname: true,
// 将<YOUR_BUCKET>设置为OSS Bucket名称。
bucket: <YOUR_BUCKET>,
// 将<YOUR_REGION>设置为OSS Bucket所在地域,例如region: 'oss-cn-hangzhou'。
region: <YOUR_REGION>,
accessKeyId: credentials.accessKeyId,
accessKeySecret: credentials.accessKeySecret,
expiration: credentials.expiration,
stsToken: credentials.securityToken,
});
let uuidName = this.getFileNameUUID();
let nowDate = this.$moment().format("YYYY/MM/DD");
const result = await client
.put(`${nowDate}/${uuidName}_${file.name}`, file)
.then((result) => result)
.catch((err) => err);
this.upResultHandle(option, result);
// 转换真实路径
// let realresult = await client.signatureUrl(file.name);
// console.log(realresult, "---realresult---");
},
// 上传结果
upResultHandle(option, result) {
if (result.res && result.res.status == 200) {
option.onSuccess(result);
} else {
option.onError(result);
}
this.loading.close();
},
// 上传成功
successHandle(res, file, fileList) {
if (res) {
this.notifySuccess("上传成功");
this.formatlistEmit(fileList);
}
},
// 上传失败
ErrorHandle(err) {
// this.$refs.upload.uploadFiles.splice(-1, 1);
this.$message.error("上传失败, 请重试");
},
/**
* 判断临时凭证是否到期。
**/
isCredentialsExpired(credentials) {
if (!credentials) {
return true;
}
const expireDate = new Date(credentials.expiration);
const now = new Date();
// 如果有效期不足一分钟,视为过期。
return expireDate.getTime() - now.getTime() <= 120000;
},
// 获取uuid
getFileNameUUID() {
function rx() {
return (((1 + Math.random()) * 0x10000) | 0)
.toString(16)
.substring(1);
}
return `${+new Date()}_${rx()}${rx()}`;
},
记录一下,有不准确的地方再修改哈~ 希望有帮助
转载自:https://juejin.cn/post/7393198696924364836