com.healthy.common.qcloud.cos.QcloudCos Maven / Gradle / Ivy
package com.healthy.common.qcloud.cos;
import cn.hutool.core.date.DateTime;
import cn.hutool.core.date.DateUtil;
import cn.hutool.core.io.FileTypeUtil;
import cn.hutool.core.io.file.FileNameUtil;
import cn.hutool.core.lang.Validator;
import cn.hutool.core.util.CharUtil;
import cn.hutool.core.util.HexUtil;
import cn.hutool.core.util.IdUtil;
import cn.hutool.core.util.StrUtil;
import com.healthy.common.qcloud.cos.exception.QcloudCosException;
import com.qcloud.cos.COSClient;
import com.qcloud.cos.ClientConfig;
import com.qcloud.cos.auth.AnonymousCOSCredentials;
import com.qcloud.cos.auth.BasicCOSCredentials;
import com.qcloud.cos.auth.COSCredentials;
import com.qcloud.cos.http.HttpMethodName;
import com.qcloud.cos.http.HttpProtocol;
import com.qcloud.cos.model.GeneratePresignedUrlRequest;
import com.qcloud.cos.model.ObjectMetadata;
import com.qcloud.cos.region.Region;
import org.springframework.beans.BeansException;
import org.springframework.context.ApplicationContext;
import org.springframework.context.ApplicationContextAware;
import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.util.Optional;
/**
* QCloudCos
*
* @author xiaomingzhang
*/
public class QcloudCos implements ApplicationContextAware {
private static COSCredentials credentials;
private static QcloudCosProperties cosProperties;
public static COSClient getCosClient(String storageName) {
return getCosClient(getStorage(storageName));
}
public static COSClient getCosClient(QcloudCosProperties.Storage storage) {
if (cosProperties == null || credentials == null) {
throw new QcloudCosException("请配置腾讯云存储相关密钥信息");
}
ClientConfig clientConfig = new ClientConfig(new Region(storage.getRegion()));
clientConfig.setHttpProtocol(HttpProtocol.https);
return new COSClient(credentials, clientConfig);
}
public static QcloudCosProperties.Storage getStorage(String storageName) {
return Optional.ofNullable(cosProperties).orElseThrow(() -> new QcloudCosException("请配置腾讯云存储相关密钥信息"))
.getStorages().stream().filter(v -> v.getName().equals(storageName)).findFirst()
.orElseThrow(() -> new QcloudCosException("无效的腾讯云存储配置: " + storageName));
}
/**
* 构建上传文件名称
*
* 示例:{folderName}/{alias}.{suffix}
* @param folderName 文件夹名称
* @param alias 文件别名
* @param suffix 文件扩展名
* @return 文件名称
*/
public static String buildKey(String folderName, String alias, String suffix) {
StringBuilder key = new StringBuilder(folderName + CharUtil.SLASH + alias);
if (StrUtil.isNotBlank(suffix)) {
key.append(CharUtil.DOT).append(suffix);
}
return key.toString();
}
/**
* 文件上传
* @param storageName 存储名称
* @param folderName 文件夹名称
* @param bytes 文件字节数组
* @return {@link KeyPath}
* @throws IOException exception
*/
public static KeyPath upload(String storageName, String folderName, byte[] bytes) throws IOException {
return upload(getStorage(storageName), folderName, bytes);
}
/**
* 文件上传
* @param storage 存储配置
* @param folderName 文件夹名称
* @param bytes 文件字节数组
* @return {@link KeyPath}
* @throws IOException exception
*/
public static KeyPath upload(QcloudCosProperties.Storage storage, String folderName, byte[] bytes)
throws IOException {
String suffix = FileTypeUtil.getType(HexUtil.encodeHexStr(bytes, false));
return upload(storage, folderName, suffix, bytes);
}
/**
* 文件上传
* @param storageName 存储名称
* @param folderName 文件夹名称
* @param suffix 文件扩展名
* @param bytes 文件字节数组
* @return {@link KeyPath}
* @throws IOException exception
*/
public static KeyPath upload(String storageName, String folderName, String suffix, byte[] bytes)
throws IOException {
return upload(getStorage(storageName), folderName, suffix, bytes);
}
/**
* 文件上传
* @param storage 存储配置
* @param folderName 文件夹名称
* @param suffix 文件扩展名
* @param bytes 文件字节数组
* @return {@link KeyPath}
* @throws IOException this exception
*/
public static KeyPath upload(QcloudCosProperties.Storage storage, String folderName, String suffix, byte[] bytes)
throws IOException {
return upload(storage, folderName, IdUtil.fastSimpleUUID(), suffix, bytes);
}
/**
* 文件上传
* @param storageName 存储名称
* @param folderName 文件夹名称
* @param file 上传的文件
* @return {@link KeyPath}
*/
public static KeyPath upload(String storageName, String folderName, File file) {
return upload(getStorage(storageName), folderName, file);
}
/**
* 文件上传
* @param storage 存储配置
* @param folderName 文件夹名称
* @param file 上传的文件
* @return {@link KeyPath}
*/
public static KeyPath upload(QcloudCosProperties.Storage storage, String folderName, File file) {
String suffix = StrUtil.blankToDefault(FileNameUtil.getSuffix(file), FileTypeUtil.getType(file));
return upload(storage, folderName, suffix, file);
}
/**
* 文件上传
* @param storageName 存储名称
* @param folderName 文件夹名称
* @param suffix 文件扩展名
* @param file 上传的文件
* @return {@link KeyPath}
*/
public static KeyPath upload(String storageName, String folderName, String suffix, File file) {
return upload(getStorage(storageName), folderName, suffix, file);
}
/**
* 文件上传
* @param storage 存储配置
* @param folderName 文件夹名称
* @param suffix 文件扩展名
* @param file 上传的文件
* @return {@link KeyPath}
*/
public static KeyPath upload(QcloudCosProperties.Storage storage, String folderName, String suffix, File file) {
return upload(storage, folderName, IdUtil.fastSimpleUUID(), suffix, file);
}
/**
* 文件上传
* @param storage 存储配置
* @param folderName 文件夹名称
* @param alias 文件别名
* @param suffix 文件扩展名
* @param bytes 文件字节数组
* @return {@link KeyPath}
* @throws IOException exception
*/
public static KeyPath upload(QcloudCosProperties.Storage storage, String folderName, String alias, String suffix,
byte[] bytes) throws IOException {
KeyPath keyPath;
try (InputStream inputStream = new ByteArrayInputStream(bytes)) {
String key = buildKey(folderName, alias, suffix);
COSClient cosClient = getCosClient(storage);
ObjectMetadata meta = new ObjectMetadata();
// 必须设置ContentLength
meta.setContentLength(bytes.length);
cosClient.putObject(storage.getBucketName(), key, inputStream, meta);
String url = generatePreSignUrl(cosClient, storage, HttpMethodName.GET, key);
keyPath = new KeyPath(key, url);
}
return keyPath;
}
/**
* 文件上传
* @param storage 存储配置
* @param folderName 文件夹名称
* @param alias 文件别名
* @param suffix 文件扩展名
* @param cosFile 上传的文件
* @return {@link KeyPath}
*/
public static KeyPath upload(QcloudCosProperties.Storage storage, String folderName, String alias, String suffix,
File cosFile) {
String key = buildKey(folderName, alias, suffix);
COSClient cosClient = getCosClient(storage);
String bucketName = storage.getBucketName();
cosClient.putObject(bucketName, key, cosFile);
String url = generatePreSignUrl(cosClient, storage, HttpMethodName.GET, key);
return new KeyPath(key, url);
}
/**
* 文件删除
* @param storageName 存储名称
* @param key 文件名
*/
public static void delKey(String storageName, String key) {
delKey(getStorage(storageName), key);
}
/**
* 文件删除
* @param storage 存储配置
* @param key 文件名
*/
public static void delKey(QcloudCosProperties.Storage storage, String key) {
COSClient cosClient = getCosClient(storage);
cosClient.deleteObject(storage.getBucketName(), key);
cosClient.shutdown();
}
/**
* 生成预签名网址
*
* 默认GET请求方式
* @param storageName 存储名称
* @param key 文件名
* @return 访问地址
*/
public static String generatePreSignUrl(String storageName, String key) {
return generatePreSignUrl(getStorage(storageName), HttpMethodName.GET, key);
}
/**
* 生成预签名网址
*
* 默认GET请求方式
* @param storage 存储配置
* @param key 文件名
* @return 访问地址
*/
public static String generatePreSignUrl(QcloudCosProperties.Storage storage, String key) {
return generatePreSignUrl(storage, HttpMethodName.GET, key);
}
/**
* 生成预签名网址
* @param storage 存储配置
* @param method 请求方式
* @param key 文件名
* @return 访问地址
*/
public static String generatePreSignUrl(QcloudCosProperties.Storage storage, HttpMethodName method, String key) {
return generatePreSignUrl(getCosClient(storage), storage, method, key);
}
/**
* 生成预签名网址
* @param cosClient 存储客户端
* @param storage 存储配置
* @param method 请求方式
* @param key 文件名
* @return 访问地址
*/
public static String generatePreSignUrl(COSClient cosClient, QcloudCosProperties.Storage storage,
HttpMethodName method, String key) {
try {
if (StrUtil.isNotBlank(key) && !Validator.isUrl(key)) {
GeneratePresignedUrlRequest generatePresignedUrlRequest = new GeneratePresignedUrlRequest(
storage.getBucketName(), key, method);
if (storage.isSign()) {
DateTime expiration = DateUtil.offsetMinute(DateUtil.date(), storage.getExpiration());
generatePresignedUrlRequest.setExpiration(expiration);
}
else {
cosClient.setCOSCredentials(new AnonymousCOSCredentials());
}
key = cosClient.generatePresignedUrl(generatePresignedUrlRequest).toString();
generatePresignedUrlRequest.clone();
}
}
finally {
if (cosClient != null) {
cosClient.shutdown();
}
}
return key;
}
@Override
public void setApplicationContext(ApplicationContext applicationContext) throws BeansException {
QcloudCos.cosProperties = applicationContext.getBean(QcloudCosProperties.class);
QcloudCos.credentials = new BasicCOSCredentials(cosProperties.getSecretId(), cosProperties.getSecretKey());
}
}