Vue上传阿里云OSS(STS方式)
一、准备工作1. 开通阿里云OSS服务,从控制台上获取AccessKeyId和AccessKeySecret。2. 创建Bucket,并登录OSS控制台3. 配置Bucket (很重要)将allowed origins(来源)设置成 *将allowed methods(允许methods)设置成 PUT, GET, POST, DELETE, HEAD将allowed he...
·
一、准备工作
1. 开通阿里云OSS服务,从控制台上获取AccessKeyId和AccessKeySecret。
2. 创建Bucket,并登录OSS控制台
3. 配置Bucket (很重要)
- 将allowed origins(来源)设置成 *
- 将allowed methods(允许methods)设置成 PUT, GET, POST, DELETE, HEAD
- 将allowed headers(允许headers)设置成 *
- 将expose headers(暴露headers)设置成 ETag (这里需要换行) x-oss-request-id
可参考阿里官方文档:https://help.aliyun.com/docum...
二、引入ali-oss
有两种方式:
1. 在HTML文件的<head>中包含如下标签:
<script src="http://gosspublic.alicdn.com/aliyun-oss-sdk-6.0.1.min.js"></script>
2. 项目中安装ali-oss
npm install ali-oss --save
可参考阿里官方文档:https://github.com/ali-sdk/al...
这里使用第二种。
三、使用OSS
关于直传,阿里官方给了三种方案:
- 客户端 JavaScript 签名后直传;
- 客户端申请服务端签名,然后打包上传;
- 客户端申请服务端签名,打包上传OSS后回调服务端。
这里使用第一种。
vue中使用步骤:
- 在src目录中创建utils文件夹
- utils文件夹中创建Client.js
- 在组件中创建testUpload.vue文件
//Client.js
const OSS = require('ali-oss');
export default function Client(data) {
//后端提供数据
return new OSS({
region: data.region, //oss-cn-beijing-internal.aliyuncs.com
accessKeyId: data.accessKeyId,
accessKeySecret: data.accessKeySecret,
stsToken: data.stsToken,
bucket: data.bucket
})
}
//testUpload.vue
<template>
<!--在此处添加渲染的内容-->
<div>
<el-upload
class="upload-demo"
ref="upload"
drag
:before-upload="beforeUpload"
:on-success="handleSuccess"
:http-request="handleHttpRequest"
:headers="uploadHeaders"
:limit="files"
:disabled="disabled"
multiple
action=""
:file-list="fileList">
<i class="el-icon-upload"></i>
<div class="el-upload__text">将文件拖到此处,或<em>点击上传</em></div>
<div slot="tip" class="el-upload__tip">上传文件大小不能超过 1G</div>
</el-upload>
</div>
</template>
<script type="text/ecmascript-6">
import Client from '../../utils/Client'
//将渲染的内容导出
export default{
props: {},
data(){
return {
region: 'oss-cn-beijing',
bucket: '',//这里选择OSS容器
percentage: 0,
url: '',//后台获取token地址
ClientObj: null,
dataObj: {},
expiration: '',
fileList: [],
files: 10,
uploadHeaders: {
authorization: '*'
},
disabled: false,
}
},
methods: {
getDate(){
const date = new Date(),
year = date.getFullYear(),
month = date.getMonth() > 9 ? date.getMonth() + 1 : `0${date.getMonth() + 1}`,
day = date.getDate() > 9 ? date.getDate() : `0${date.getDate()}`,
hh = date.getHours() > 9 ? date.getHours() : `0${date.getHours()}`,
mm = date.getMinutes() > 9 ? date.getMinutes() : `0${date.getMinutes()}`;
return `${year}${month}${day}${hh}${mm}`;
},
getAliToken(){ //获取Token
return new Promise((resolve, reject) => {
this.$axios({
method: 'POST',
url: this.url
}).then(res => {
if (res.success) {
const {expiration, tempAk, tempSk, token} = res.data;
this.expiration = expiration;
this.dataObj = {
region: this.region,
bucket: this.bucket,
accessKeyId: tempAk,
accessKeySecret: tempSk,
stsToken: token
};
resolve(true);
} else {
reject(false);
}
}).catch(err => {
console.log(err);
reject(false);
})
})
},
beforeUpload(file){
return new Promise((resolve, reject) => {
this.getAliToken().then(response => {
if (response) {
resolve(response);
} else {
reject(response);
}
}).catch(err => {
console.log(err);
reject(err);
});
})
},
async handleHttpRequest(option){ //上传OSS
try {
let vm = this;
vm.disabled = true;
const client = Client(this.dataObj), file = option.file;
//随机命名
const random_name = this.random_string(6) + '_' + new Date().getTime() + '.' + file.name.split('.').pop();
// 分片上传文件
await client.multipartUpload(random_name, file, {
progress: async function (p) {
let e = {};
e.percent = p * 100;
option.onProgress(e)
}
}).then(({res}) => {
console.log(res);
if (res.statusCode === 200) {
// option.onSuccess(ret)
return res.requestUrls
} else {
vm.disabled = false;
option.onError('上传失败');
}
}).catch(error => {
vm.disabled = false;
option.onError('上传失败');
});
} catch (error) {
console.error(error);
this.disabled = false;
option.onError('上传失败');
}
},
handleSuccess(response, file, fileList){
console.log(response);
console.log(file);
console.log(fileList);
},
// 随机生成文件名
random_string(len) {
len = len || 32;
let chars = 'ABCDEFGHJKMNPQRSTWXYZabcdefhijkmnprstwxyz12345678', maxPos = chars.length, pwd = '';
for (let i = 0; i < len; i++) {
pwd += chars.charAt(Math.floor(Math.random() * maxPos));
}
return pwd;
}
},
watch: {
url(val){
if (val) {
this.urls.push(val);
}
}
},
components: {},
computed: {},
watch: {},
created(){
this.getAliToken();
},
mounted(){
},
}
</script>
<style scoped>
/**渲染内容的样式**/
</style>
完成上传
更多推荐
已为社区贡献7条内容
所有评论(0)