項目在須要使用到大文件上傳時,選擇經過前端直連阿里Oss,我的感受是個不錯的選擇。
一方面不須要本身搭建文件服務器,另外一個能節約服務器的帶寬壓力。
在這記錄一下,本身寫的Oss圖片上傳組件
獲取Token
雖然說是前端直連,可是Token仍是從後臺獲取的。這個時候就須要後臺大哥搞個獲取Oss的Token接口,接下來就能夠愉快地上傳圖片啦。
import { getOssToken } from "@/util/common";
const OSS = require("ali-oss");
let client;
created() {
getOssToken().then((res) => {
client = new OSS({
// yourRegion填寫Bucket所在地域。以華東1(杭州)爲例,Region填寫爲oss-cn-hangzhou。
region: "oss-cn-hangzhou",
// 從STS服務獲取的臨時訪問憑證。臨時訪問憑證包括臨時訪問密鑰(AccessKeyId和AccessKeySecret)和安全令牌(SecurityToken)。
accessKeyId: res.data.accessKeyId,
accessKeySecret: res.data.accessKeySecret,
stsToken: res.data.securityToken,
// 填寫Bucket名稱。
bucket: "Bucket",
});
});
},
上傳圖片用到的仍是咱們的熟悉的el-upload
<el-upload
class="avatar-uploader"
action="#"
ref="upload"
v-loading="loading"
list-type="picture-card"
:on-success="handleSuccess"
:before-upload="uploadBefore"
:on-preview="handlePictureCardPreview"
:on-remove="handleRemove"
:file-list="imgList"
>
<i class="el-icon-plus"></i>
</el-upload>
主要的上傳方法就是改變el-upload的默認上傳方法
// oss上傳圖片
async uploadBefore(file, loading, column) {
this.loading = true;
let fileName = this.product + '/' + new Date().getTime() + file.name;
let result = await client.put("/picture/" + fileName, file);
this.imgList.push({
name: fileName,
url: this.url + fileName,
fileName: fileName,
});
let _this = this;
setTimeout(function () {
_this.loading = false;
}, 600);
},
完整代碼以下
<template>
<div>
<el-upload
class="avatar-uploader"
action="#"
ref="upload"
v-loading="loading"
list-type="picture-card"
:on-success="handleSuccess"
:before-upload="uploadBefore"
:on-preview="handlePictureCardPreview"
:on-remove="handleRemove"
:file-list="imgList"
>
<i class="el-icon-plus"></i>
</el-upload>
<el-dialog
:visible.sync="dialogVisible"
:modal-append-to-body="false"
:append-to-body="true"
>
<img width="100%" :src="dialogImageUrl" alt="" />
</el-dialog>
</div>
</template>
<script>
import { getOssToken } from "@/util/common";
const OSS = require("ali-oss");
let client;
export default {
name: "uploadImg",
props: {
product: {
default: function () {
return '0'
},
type: String
}
},
created() {
this.loading = true;
getOssToken().then((res) => {
this.loading = false;
client = new OSS({
// yourRegion填寫Bucket所在地域。以華東1(杭州)爲例,Region填寫爲oss-cn-hangzhou。
region: "oss-cn-hangzhou",
// 從STS服務獲取的臨時訪問憑證。臨時訪問憑證包括臨時訪問密鑰(AccessKeyId和AccessKeySecret)和安全令牌(SecurityToken)。
accessKeyId: res.data.accessKeyId,
accessKeySecret: res.data.accessKeySecret,
stsToken: res.data.securityToken,
// 填寫Bucket名稱。
bucket: "Bucket",
});
});
},
data() {
return {
loading: false,
dialogVisible: false,
src: "",
imgList: [],
dialogImageUrl: "",
url: "picture/",
};
},
methods: {
handlePictureCardPreview(file) {
this.dialogImageUrl = file.url;
this.dialogVisible = true;
},
// oss上傳圖片
async uploadBefore(file, loading, column) {
this.loading = true;
let fileName = this.product + '/' + new Date().getTime() + file.name;
let result = await client.put("/picture/" + fileName, file);
this.imgList.push({
name: fileName,
url: this.url + fileName,
fileName: fileName,
});
let _this = this;
setTimeout(function () {
_this.loading = false;
}, 600);
},
uploadAfter(res, loading, column) {},
handleRemove(file, fileList) {
this.imgList.forEach((item, index) => {
if (item.fileName == file.fileName) {
this.imgList.splice(index, 1);
}
});
},
clearFiles() {
this.imgList = []
this.$refs.upload.clearFiles();
},
getImList() {
return this.imgList;
},
//上傳成功
handleSuccess(res, file) {
this.imagesUrl = res.data;
//圖片路徑返回給父組件
return this.imgList;
},
// 上傳成功以前 對圖片格式要求
beforeAvatarUpload(file) {
const isPNG = file.type === "image/png";
const isJPG = file.type === "image/jpeg";
const isLt2M = file.size / 1024 / 1024 < 2;
if (!isPNG && !isJPG) {
this.$message.error("上傳圖片只能是 JPG 格式和PNG格式!");
}
if (!isLt2M) {
this.$message.error("上傳圖片大小不能超過 2MB!");
}
return (isPNG && isLt2M) || (isJPG && isLt2M);
},
},
};
</script>