前言
阿里云oss上传文件蕴含有好多SDK,个别像客户端的百度云盘这样的C端会应用如java相干的SDK,而浏览器端,也就是web端最好应用browser.js相干的SDK,上面就来解说下如何应用,心愿可能帮忙到大家。
配置ram权限获取sts token和跨域反对
在应用阿里云OSS上传文件之前,要提前配置好ram相干权限,官网文档有阐明,具体请看应用STS长期拜访凭证拜访OSS,配置时,要留神两点:
1、因为会应用上传和下载两种权限,所以应该应用上面权限策略(xxx为你的门路):
{
"Version": "1",
"Statement": [
{
"Effect": "Allow",
"Action": [
"oss:PutObject",
"oss:GetObject"
],
"Resource": [
"acs:oss:*:*:xxx",
"acs:oss:*:*:xxx/*"
]
}
]
}
配置好之后,咱们再来配置后盾,返回sts token
给前端
@Override
public AssumeRoleResponse getAcsForUploadFile(String userName) {
// STS接入地址,例如sts.cn-hangzhou.aliyuncs.com。
String endpoint = aliyunOssConfig.getRamStsEndpoint();
// 填写步骤1生成的拜访密钥AccessKey ID和AccessKey Secret。
String AccessKeyId = aliyunOssConfig.getRamAccessKeyId();
String accessKeySecret = aliyunOssConfig.getRamAccessKeySecret();
// 填写步骤3获取的角色ARN。
String roleArn = aliyunOssConfig.getRamRoleArn();
// 自定义角色会话名称,用来辨别不同的令牌,例如可填写为SessionTest。
String roleSessionName = userName;
// 以下Policy用于限度仅容许应用长期拜访凭证向指标存储空间examplebucket上传文件。
// 长期拜访凭证最初取得的权限是步骤4设置的角色权限和该Policy设置权限的交加,即仅容许将文件上传至指标存储空间examplebucket下的exampledir目录。
// String policy = "{" +
// " \"Version\": \"1\", " +
// " \"Statement\": [" +
// " {\n" +
// " \"Action\": [" +
// " \"oss:PutObject\"" +
// " ]," +
// " \"Resource\": [" +
// " \"acs:oss:*:*:com-seaurl-cdn/space\"," +
// " \"acs:oss:*:*:com-seaurl-cdn/space/*\"," +
// " ]," +
// " \"Effect\": \"Allow\"" +
// " }" +
// " ]" +
// "}";
try {
// regionId示意RAM的地区ID。以华东1(杭州)地区为例,regionID填写为cn-hangzhou。也能够保留默认值,默认值为空字符串("")。
String regionId = aliyunOssConfig.getRegion();
// 增加endpoint。实用于Java SDK 3.12.0及以上版本。
DefaultProfile.addEndpoint(regionId, "Sts", endpoint);
// 增加endpoint。实用于Java SDK 3.12.0以下版本。
// DefaultProfile.addEndpoint("",regionId, "Sts", endpoint);
// 结构default profile。
IClientProfile profile = DefaultProfile.getProfile(regionId, AccessKeyId, accessKeySecret);
// 结构client。
DefaultAcsClient client = new DefaultAcsClient(profile);
final AssumeRoleRequest request = new AssumeRoleRequest();
// 实用于Java SDK 3.12.0及以上版本。
request.setSysMethod(MethodType.POST);
// 实用于Java SDK 3.12.0以下版本。
//request.setMethod(MethodType.POST);
request.setRoleArn(roleArn);
request.setRoleSessionName(roleSessionName);
request.setPolicy(null); // 如果policy为空,则用户将取得该角色下所有权限。
request.setDurationSeconds(3600L); // 设置长期拜访凭证的无效工夫为3600秒。
final AssumeRoleResponse response = client.getAcsResponse(request);
System.out.println("Expiration: " + response.getCredentials().getExpiration());
System.out.println("Access Key Id: " + response.getCredentials().getAccessKeyId());
System.out.println("Access Key Secret: " + response.getCredentials().getAccessKeySecret());
System.out.println("Security Token: " + response.getCredentials().getSecurityToken());
System.out.println("RequestId: " + response.getRequestId());
return response;
} catch (com.aliyuncs.exceptions.ClientException e) {
System.out.println("Failed:");
System.out.println("Error code: " + e.getErrCode());
System.out.println("Error message: " + e.getErrMsg());
System.out.println("RequestId: " + e.getRequestId());
return null;
}
}
2、设置跨域反对
如果设置了跨域规定还是不起作用,能够应用上面形式进行批改:
设置跨域规定后调用OSS时依然报“No ‘Access-Control-Allow-Origin’”的谬误
上传文件(简略上传和分片上传)
下面配置好权限之后,接下来咱们来装置和应用
1、装置ali-oss
yarn add ali-oss
2、初始化oss client
留神:getAcsForUploadFile()
办法就是下面获取sts token
的申请办法
//初始化oss client客户端
async function initOssClient() {
let res = await dispatch(getAcsForUploadFile())
console.log('initOss=', res)
if (res.payload.status === 0) {
const resData = res.payload.data
const client = new OSS({
secure: true,
// yourRegion填写Bucket所在地区。以华东1(杭州)为例,Region填写为oss-cn-hangzhou。
region: 'oss-cn-hangzhou',
// 从STS服务获取的长期拜访密钥(AccessKey ID和AccessKey Secret)。
accessKeyId: resData.credentials.accessKeyId,
accessKeySecret: resData.credentials.accessKeySecret,
// 从STS服务获取的平安令牌(SecurityToken)。
stsToken: resData.credentials.securityToken,
refreshSTSToken: async () => {
// 向您搭建的STS服务获取长期拜访凭证。
const refreshRes = await dispatch(getAcsForUploadFile())
console.log('refreshSTSToken info=', refreshRes)
if (refreshRes.payload.status === 0) {
const refreshResData = refreshRes.payload.data
return {
accessKeyId: refreshResData.credentials.accessKeyId,
accessKeySecret: refreshResData.credentials.accessKeySecret,
stsToken: refreshResData.credentials.securityToken
}
}
},
// 刷新长期拜访凭证的工夫距离,单位为毫秒。
refreshSTSTokenInterval: 3000000,
// 填写Bucket名称。
bucket: 'xxx'
});
if (client) {
setOssClient(client)
}
}
}
3、上传文件
// 上传文件前判断单个文件是否超过500mb,如果超过不容许上传
function beforeUploadFile(file, fileList) {
console.log('file=', file)
const isLt500M = file.size / 1024 / 1024 > 500;
if (isLt500M) {
message.warning('超过最大文件上传大小500Mb');
return false
}
return true; // 不调用默认的上传办法
}
// 上传文件状态回调
function onUploadFileChange(info) {
console.log('info=', info)
// 把没有status的文件过滤掉(没有status的文件阐明是勾销上传的文件)
if (info.file.status) {
setFileTaskDlg({
show: true,
task: info
})
if (info.file.status === 'done') {
dispatch(getFileListByCid({
cid: query.cid
}))
}
if (info.file.status === 'error') {
dispatch(getFileListByCid({
cid: query.cid
}))
}
}
}
// 自定义上传
function uploadFileToOss(options) {
console.log('options=', options)
const {file, onProgress, onSuccess, onError} = options
return new Promise(async (resolve, reject) => {
const filePath = `space/file/${me.name}/${file.name}`
const fileType = getFileType(file.name)
let result = null;
// 判断文件是否超过100mb,如果超过则应用分片上传,否则应用简略上传
if (file.size / 1024 / 1024 > 100) {
console.log('分片上传')
// 分片上传,默认分片1Mb,如果想更改,请参考:https://help.aliyun.com/document_detail/383952.html
result = await ossClient.multipartUpload(filePath, file, {
progress: async (percent) => {
onProgress({percent: percent * 100})
},
}).catch((error) => {
onError(error)
reject(error)
})
} else {
console.log('简略上传')
// 简略上传
result = await ossClient.put(filePath, file, {
progress: async (percent) => {
onProgress({percent: percent * 100})
},
}).catch((error) => {
onError(error)
reject(error)
})
}
await uploadFileCallback(result, {
file,
filePath,
fileType
}, (res) => {
onSuccess(res)
resolve(result)
})
})
}
async function uploadFileCallback(result, data, callback) {
const ossPath = result.res.requestUrls[0].split('?')[0]
const url = ossPath.replace(/^http:\/\//i, 'https://')
const newFileRes = {
status: result?.res?.status,
name: result?.name,
url: url,
}
// 上传胜利之后往后台数据库插入一条文件数据
await dispatch(addFile({
fileName: data.file.name,
filePath: data.filePath,
fileSize: data.file.size,
fileContentType: data.fileType,
categoryId: query.cid,
}))
callback(newFileRes)
}
...
<Upload
beforeUpload={beforeUploadFile}
customRequest={uploadFileToOss}
showUploadList={false}
withCredentials={true}
disabled={btnUploadDisabled}
onChange={onUploadFileChange}>
<Button icon={<CloudUploadOutlined/>} disabled={btnUploadDisabled}>上传文件</Button>
</Upload>
beforeUploadFile()
办法是在上传文件之前做本人的业务逻辑解决,比方我这里的超过500mb的文件不容许上传
uploadFileToOss()
是Upload
组件自定义上传规定,所以你不必设置action
等属性
onUploadFileChange()
办法是上传文件时的变动回调,能够通过这个办法设置显示文件上传动静
下载文件(批量下载)
下载文件跟上传差不多,上面示例
function onDownload(d) {
if (selectedRowKeys.length <= 0) {
message.warning('请先抉择文件');
} else {
console.log('selectedRowKeys=', selectedRowKeys)
const filterFiles = files.filter(item => selectedRowKeys.includes(item.id))
console.log('filterFiles=', filterFiles)
filterFiles.forEach(item => {
const fileName = item.name
const response = {
'content-disposition': `attachment; filename=${encodeURIComponent(fileName)}`
}
// 填写Object残缺门路。Object残缺门路中不能蕴含Bucket名称。
const url = ossClient.signatureUrl(item.path, {response});
const iframe = document.createElement('iframe');
iframe.style.display = 'none';
iframe.style.height = 0;
iframe.src = url;
// 与前两种形式不同,iframe须要挂载到页面上能力触发申请
document.body.appendChild(iframe);
setTimeout(() => {
iframe.remove();
}, 1000);
})
}
}
阐明:selectedRowKeys
是我的文件列表抉择的文件ids汇合item.path
是文件在oss的残缺门路,留神:不蕴含host和bucket-name,如:a/b/c.txt
总结
1、阿里云oss上传文件一开始我应用的是java sdk上传,发现不能在web端分片,于是应用了ali-oss
组件包在浏览器端上传
2、要配置ram权限以及获取sts token还有跨域
援用
js实现单个文件下载,批量下载多个文件
async/await 捕捉谬误 捕捉catch
OSS + Ant Design Upload 网页直传
OSS文档:预览或下载文件
OSS文档
发表回复