使用el-upload组件上传图片至七牛云

最近有个上传七牛的需求,上传框样式和逻辑都比较复杂,手写的话挺麻烦的,于是想到了 element 里的 upload 组件。

前端用的是 vue3 + elementPlus。

属性可以参考官方文档 : Upload 上传 | Element Plus

直接上代码:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
<el-upload
class="uploader"
:action="uploadQiniuUrl"
accept="image/jpeg,image/gif,image/png"
auto-upload
:show-file-list="false"
:before-upload="beforeUpload"
:data="form"
:on-success="uploadSuccess"
:on-error="handleError"
>
<el-image
class="img"
v-if="uploadImg"
:src="uploadImg"
fit="cover"
></el-image>
<img
v-if="uploadImg"
class="remove"
src="@/static/image/upload/remove.png"
@click.prevent.stop="removeImg"
/>
<el-image
v-else
class="img"
src="@/static/image/upload/cover.png"
fit="cover"
></el-image>
</el-upload>

这里的属性首先添加了action,就是七牛的地址,不同地区的存储空间对应不同链接,这里的是 https://up-z2.qiniup.com

auto-upload,图片上传至前端后自动上传至七牛。不需要可以不加,手动调用submit方法即可。

show-file-list 改为false,只需要展示一张图片,因此在默认插槽中手动展示。

在上传七牛的时候,我们需要拿到一个token,在上传的时候需要带上token才能成功。upload组件提供了一个before-upload方法,我们可以在这里面实现这个逻辑,也可以进行一些相关判断,比如类型大小时候符合。data是我们要上传的数据对象,token就放在data里面。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
const beforeUpload = async (file) => {
const key = `data/img_${new Date().getTime()}.${file.type.split('/')[1]}`;
const isLt20M = file.size / 1024 / 1024 < 20;
if (!isLt20M) {
ElMessage.error('图片大小不能超过20M!');
return isLt20M;
}
try {
const token = await this.getToken();
form = {
key,
token,
};
return true;
} catch (error) {
return error;
}
};

这个函数返回true,就会走上传流程,返回其他就会停住。

成功和错误的回调:

1
2
3
4
5
6
const uploadSuccess = (res, file, fileList) => {
uploadImg = qiniuBaseUrl + res.key;
};
const handleError = (res) => {
ElMessage.error('上传失败');
};

成功回调里可以拿到上传成功后的图片相对路径key,拼上域名,就可以访问了。

tips:成功回调会接收三个参数,而当我们想要自定义参数的时候,使用$event肯定是不行的,可以使用如下方式。这里把 table 的行序号传入成功回调,方便对应行中图片的赋值。

1
:on-success="(res, file, fileList) =>ImgUploadSuccess(res, file, fileList, scope.$index)"