我们在实际业务中经常能遇到将各种资源上传到云服务器,这样做第一是能更好的管理我们的比如图片资源,视频,音频资源等,同时也能节约公司的网络带宽,减少各种资源随着时间的推移资源越来越多造成服务器的硬盘压力过大。还有一个重要的原因是可以保护我们的资源被其他人盗用的问题.下面我就来介绍在小程序中如何将各种资源直传到阿里云OSS。话不多说直接上代码
小程序 index.js
在每次调用读取文件之前之前,需要重新获得零时授权,防止授权凭证过期导致无法上传
import UploadAliOss from "../../common/aliyunOss/uploadOssClass";
const AliyunOss = new UploadAliOss();
// 读取文件之前 需要重新获得零时授权
async beforeRead(event) {
await AliyunOss.GetOSSKeyInfo();
Toast.loading({
message: '上传中...',
forbidClick: true,
duration: 0
});
event.detail.callback(true);
},
读取文件之后调用上传方法,
// 文件读取完成后
async afterRead(event) {
const {
file
} = event.detail;
const {
Code,
Data
} = await AliyunOss.uploadFile(file.url)
console.log("AliyunOss.uploadFile", Code, Data);
if (Code == 200) {
const imgInfo = new ImgClass(BaseImgUrl + Data);
Toast.clear();
this.setData({
fileList: [...this.data.fileList, imgInfo]
})
} else {
Toast.fail('上传失败');
}
},
uploadOssClass.js 注意 uploadImageUrl 这个地址需要配置到,合法域名中
const crypto = require('crypto.js');
const base64 = require('base64.js'); // Base64,hmac,sha1,crypto相关算法
import {
GetOSSKey
} from "../../api/api";
const uploadImageUrl = "xxxxxxxx"; //你的阿里云OSS地址 在你当前小程序的公众号后台的uploadFile 合法域名也要配上这个域名
class UploadAliOss {
constructor(options = {}) {
// 限制参数的生效时间,单位为小时,默认值为1。
this.timeout = options.timeout || 1;
// 限制上传文件的大小,单位为MB,默认值为10。
this.maxSize = options.maxSize || 10;
}
// 服务端获取上传秘钥 和 临时授权
async GetOSSKeyInfo() {
const result = await GetOSSKey();
this.securityToken = JSON.parse(result).SecurityToken;
this.accessKeyId = JSON.parse(result).AccessKeyId;
this.accessKeySecret = JSON.parse(result).AccessKeySecret;
};
// 上传文件 filePath 文件的临时地址 dir 文件夹 生成的文件反正那个文件夹下 方便管理
uploadFile(filePath, dir = "xlya") {
return new Promise((resolve, reject) => {
if (!filePath) {
reject({
Code: 501,
Msg: "上传失败,请稍后再试"
})
return
}
// 设置文件存放的地址以及为文件命名 随机数防止文件重名被覆盖
const aliyunFileKey = dir + "/" + new Date().getTime() + Math.floor(Math.random() * 150);
wx.uploadFile({
url: uploadImageUrl, //开发者服务器 url
filePath: filePath, //要上传文件资源的路径
name: 'file', //必须填file
formData: {
'key': aliyunFileKey, // 设置文件上传至OSS后的文件路径
'success_action_status': '200',
...this.getUploadParams()
},
success: function (res) {
if (res.statusCode == 200) {
resolve({
Code: 200,
Data: "/" + aliyunFileKey
})
} else {
reject({
Code: 501,
Msg: "上传失败,请稍后再试"
})
}
},
fail: function (err) {
reject({
Code: 501,
Msg: "上传失败,请稍后再试"
})
},
})
})
}
// 获取上传接口需要的参数
getUploadParams() {
const policy = this.getPolicyBase64();
const signature = this.signature(policy);
return {
OSSAccessKeyId: this.accessKeyId,
policy: policy,
signature: signature,
'x-oss-security-token': this.securityToken,
};
}
getPolicyBase64() {
let date = new Date();
// 设置policy过期时间。
date.setHours(date.getHours() + this.timeout);
let srcT = date.toISOString();
const policyText = {
expiration: srcT,
conditions: [
// 限制上传文件大小。
["content-length-range", 0, this.maxSize * 1024 * 1024],
],
};
return base64.encode(JSON.stringify(policyText));
}
// 获取签名
signature(policyBase64) {
const accesskey = this.accessKeySecret;
const bytes = crypto.HMAC(crypto.SHA1, policyBase64, accesskey, {
asBytes: true
});
const signature = crypto.util.bytesToBase64(bytes);
return signature;
}
}
export default UploadAliOss