当前位置:网站首页>华为云OBS文件上传下载工具类
华为云OBS文件上传下载工具类
2022-07-06 07:58:00 【Java小白笔记】
Java-华为云OBS文件上传下载工具类
文章目录
1.华为云obs文件上传下载
package com.xxx.util;
import cn.hutool.core.io.FileUtil;
import com.obs.services.ObsClient;
import com.obs.services.exception.ObsException;
import com.obs.services.model.*;
import com.xxx.web.exception.BizErrorException;
import com.xxx.web.exception.enums.BizErrorCodeEnum;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.cloud.context.config.annotation.RefreshScope;
import org.springframework.stereotype.Component;
import org.springframework.util.CollectionUtils;
import org.springframework.web.multipart.MultipartFile;
import java.io.*;
import java.net.URLDecoder;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
/**
* @author xxx
* @createTime 2021/12/6 16:31
* @description 华为OBS工具类
*/
@Slf4j
@Component
@RefreshScope
public class HuaweiOBSUtil {
private static String endPoint;
private static String ak;
private static String sk;
private static String bucketName;
@Value("${obs.endPoint}")
public void setEndPoint(String endPoint) {
HuaweiOBSUtil.endPoint = endPoint;
}
@Value("${obs.ak}")
public void setAk(String ak) {
HuaweiOBSUtil.ak = ak;
}
@Value("${obs.sk}")
public void setSk(String sk) {
HuaweiOBSUtil.sk = sk;
}
@Value("${obs.bucketName}")
public void setBucketName(String bucketName) {
HuaweiOBSUtil.bucketName = bucketName;
}
/**
* 上传File类型文件
*
* @param file
* @return
*/
public static String uploadFile(File file) {
return getUploadFileUrl(file);
}
/**
* 上传MultipartFile类型文件
*
* @param multipartFile
* @return
*/
public static String uploadFile(MultipartFile multipartFile) {
return getUploadFileUrl(com.xxx.util.FileUtil.MultipartFileToFile(multipartFile));
}
private static String getUploadFileUrl(File file) {
if (com.xxx.util.FileUtil.checkFileNotNull(file)) {
String fileName = FileUtil.getName(file);
log.info("上传图片:" + fileName);
/*log.info("ak:" + ak);
log.info("sk:" + sk);
log.info("endPoint:" + endPoint);*/
ObsClient obsClient = new ObsClient(ak, sk, endPoint);
try {
//判断桶是否存在,不存在则创建
if (!obsClient.headBucket(bucketName)) {
obsClient.createBucket(bucketName);
}
PutObjectRequest request = new PutObjectRequest();
request.setBucketName(bucketName);
request.setObjectKey(fileName);
request.setFile(file);
request.setAcl(AccessControlList.REST_CANNED_PUBLIC_READ);
PutObjectResult result = obsClient.putObject(request);
String url = result.getObjectUrl();
log.info("图片路径:" + url);
return url;
} catch (Exception e) {
log.error("图片上传错误:{}", e);
throw new BizErrorException(BizErrorCodeEnum.FILE_UPLOAD_FAILURE);
}/* finally {
删除本地临时文件
HuaweiOBSUtil.deleteTempFile(file);
}*/
}
return null;
}
/**
* 上传图片自定义code
*
* @param ak
* @param sk
* @param endPoint
* @param file
* @return
*/
public static String uploadFileByCode(String ak, String sk, String endPoint, String bucket, File file) {
//String pathname = objectName;
try {
String fileName = FileUtil.getName(file);
log.info("上传图片:" + fileName);
ObsClient obsClient = new ObsClient(ak, sk, endPoint);
//判断桶是否存在,不存在则创建
if (!obsClient.headBucket(bucket)) {
obsClient.createBucket(bucket);
}
PutObjectRequest request = new PutObjectRequest();
request.setBucketName(bucket);
request.setObjectKey(fileName);
request.setFile(file);
request.setAcl(AccessControlList.REST_CANNED_PUBLIC_READ);
PutObjectResult result = obsClient.putObject(request);
String url = result.getObjectUrl();
log.info("文件名称:"+fileName+"图片路径:" + url);
return url;
} catch (Exception e) {
log.error("图片上传错误:{}", e);
} /*finally {
HuaweiOBSUtil.deleteTempFile(file);
}*/
return null;
}
/**
* 删除本地临时文件
*
* @param file
*/
public static void deleteTempFile(File file) {
if (file != null) {
File del = new File(file.toURI());
del.delete();
}
}
/**
* 根据文件地址获取名称下载File类型的文件
* @param fileUrl
* @return
*/
public static MultipartFile downloadFileByUrl(String fileUrl){
try {
String fileName = getFilenameByUrl(fileUrl);
// 创建ObsClient实例
ObsClient obsClient = new ObsClient(ak, sk, endPoint);
ObsObject obsObject = obsClient.getObject(bucketName, fileName);
InputStream inputStream = obsObject.getObjectContent();
//转成MultipartFile
MultipartFile multipartFile = InputStreamConvertMultipartFileUtil.getMultipartFile(inputStream, fileName);
//File file = com.xxx.util.FileUtil.MultipartFileToFile(multipartFile);
return multipartFile;
} catch (ObsException e) {
log.error("文件下载失败:{}", e.getMessage());
throw new BizErrorException(BizErrorCodeEnum.GET_FILE_DOWNLOAD_URL_FAIL);
}
}
/**
* 批量n天删除之前的文件
*
* @param ak
* @param sk
* @param endPoint
* @param bucket
* @param requireHours
*/
public static void batchDeleteForHoursago(String ak, String sk, String endPoint, String bucket, int requireHours) {
ObsClient obsClient = new ObsClient(ak, sk, endPoint);
long currentTime = new Date().getTime();
try {
ListObjectsRequest listRequest = new ListObjectsRequest(bucket);
listRequest.setMaxKeys(1000); // 每次至多返回1000个对象
ObjectListing listResult;
Date lastModified;
long hourMillisecond = 1000 * 3600 * 1;
// 分页查询
do {
List<KeyAndVersion> toDelete = new ArrayList<>();
listResult = obsClient.listObjects(listRequest);
for (ObsObject obsObject : listResult.getObjects()) {
lastModified = obsObject.getMetadata().getLastModified();
long diffs = (currentTime - lastModified.getTime()) / hourMillisecond; // 当前时间减去文件修改时间
if (diffs > requireHours
&& (obsObject.getObjectKey().endsWith(".ts") || obsObject.getObjectKey().endsWith(".mp4"))) {
log.info("文件距现在{}小时,对象更改日期:{},文件对象:{}", diffs, lastModified, obsObject.getObjectKey());
toDelete.add(new KeyAndVersion(obsObject.getObjectKey()));
}
}
// 设置下次列举的起始位置
listRequest.setMarker(listResult.getNextMarker());
//批量删除文件
log.info("待删除的OBS对象数量:{}", toDelete.size());
if (!CollectionUtils.isEmpty(toDelete)) {
DeleteObjectsRequest deleteRequest = new DeleteObjectsRequest(bucket);
deleteRequest.setQuiet(true); // 设置为quiet模式,只返回删除失败的对象
deleteRequest.setKeyAndVersions(toDelete.toArray(new KeyAndVersion[toDelete.size()]));
DeleteObjectsResult deleteResult = obsClient.deleteObjects(deleteRequest);
if (!CollectionUtils.isEmpty(deleteResult.getErrorResults())) {
log.error("删除失败的OBS对象数量:{}", deleteResult.getErrorResults().size());
}
}
} while (listResult.isTruncated());
} catch (Exception e) {
log.error("华为OBS批量删除异常", e);
} finally {
try {
obsClient.close();
} catch (IOException e) {
log.error("华为OBS关闭客户端失败", e);
}
}
}
/**
* 删除单个对象
*
* @param ak
* @param sk
* @param endPoint
* @param bucket
* @param objectKey
* @return
*/
public static boolean deleteFile(String ak, String sk, String endPoint, String bucket, String objectKey) {
ObsClient obsClient = new ObsClient(ak, sk, endPoint);
DeleteObjectResult deleteObjectResult = obsClient.deleteObject(bucket, objectKey);
boolean deleteMarker = deleteObjectResult.isDeleteMarker();
try {
obsClient.close();
} catch (IOException e) {
log.error("华为OBS关闭客户端失败", e);
}
return deleteMarker;
}
/**
* 查询桶内已使用空间大小
*
* @param ak
* @param sk
* @param endPoint
* @param bucket
* @return 单位字节
*/
public static long getBucketUseSize(String ak, String sk, String endPoint, String bucket) {
ObsClient obsClient = new ObsClient(ak, sk, endPoint);
BucketStorageInfo storageInfo = obsClient.getBucketStorageInfo(bucket);
log.info("{} 桶内对象数:{} 已使用的空间大小B:{} GB:{}", bucket, storageInfo.getObjectNumber(), storageInfo.getSize(), storageInfo.getSize() / 1024 / 1024 / 1024);
try {
obsClient.close();
} catch (IOException e) {
log.error("华为OBS关闭客户端失败", e);
}
return storageInfo.getSize();
}
public static String readFileContent(String fileName) {
File file = new File(fileName);
BufferedReader reader = null;
StringBuffer sbf = new StringBuffer();
try {
reader = new BufferedReader(new FileReader(file));
String tempStr;
while ((tempStr = reader.readLine()) != null) {
sbf.append(tempStr);
}
reader.close();
return sbf.toString();
} catch (IOException e) {
e.printStackTrace();
} finally {
if (reader != null) {
try {
reader.close();
} catch (IOException e1) {
e1.printStackTrace();
}
}
}
return sbf.toString();
}
/**
* 根据下载地址url获取文件名称
* @param url
* @throws IOException
*/
public static String getFilenameByUrl(String url){
String fileName= null;
try {
//url编码处理,中文名称会变成百分号编码
String decode = URLDecoder.decode(url, "utf-8");
fileName = decode.substring(decode.lastIndexOf("/")+1);
log.info("fileName :" + fileName);
} catch (UnsupportedEncodingException e) {
log.error("getFilenameByUrl() called with exception => 【url = {}】", url,e);
e.printStackTrace();
}
return fileName;
}
}
2.文件流转MultipartFile
package com.xxx.util;
import org.apache.commons.fileupload.FileItem;
import org.apache.commons.fileupload.FileItemFactory;
import org.apache.commons.fileupload.disk.DiskFileItemFactory;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.http.MediaType;
import org.springframework.web.multipart.MultipartFile;
import org.springframework.web.multipart.commons.CommonsMultipartFile;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
/**
* 将输入流转成文件
* @author xiaoxiangyuan
*
*/
public class InputStreamConvertMultipartFileUtil {
private static Logger log = LoggerFactory.getLogger(InputStreamConvertMultipartFileUtil.class);
/**
* 获取封装得MultipartFile
*
* @param inputStream inputStream
* @param fileName fileName
* @return MultipartFile
*/
public static MultipartFile getMultipartFile(InputStream inputStream, String fileName) {
FileItem fileItem = createFileItem(inputStream, fileName);
//CommonsMultipartFile是feign对multipartFile的封装,但是要FileItem类对象
return new CommonsMultipartFile(fileItem);
}
/**
* FileItem类对象创建
*
* @param inputStream inputStream
* @param fileName fileName
* @return FileItem
*/
public static FileItem createFileItem(InputStream inputStream, String fileName) {
FileItemFactory factory = new DiskFileItemFactory(16, null);
String textFieldName = "file";
FileItem item = factory.createItem(textFieldName, MediaType.MULTIPART_FORM_DATA_VALUE, true, fileName);
int bytesRead = 0;
byte[] buffer = new byte[10 * 1024 * 1024];
OutputStream os = null;
//使用输出流输出输入流的字节
try {
os = item.getOutputStream();
while ((bytesRead = inputStream.read(buffer, 0, 8192)) != -1) {
os.write(buffer, 0, bytesRead);
}
inputStream.close();
} catch (IOException e) {
log.error("Stream copy exception", e);
throw new IllegalArgumentException("文件上传失败");
} finally {
if (os != null) {
try {
os.close();
} catch (IOException e) {
log.error("Stream close exception", e);
}
}
if (inputStream != null) {
try {
inputStream.close();
} catch (IOException e) {
log.error("Stream close exception", e);
}
}
}
return item;
}
public static void main(String[] args) {
}
}
package com.xxx.util.img;
import org.springframework.web.multipart.MultipartFile;
import java.io.*;
public class ConvertToMultipartFile implements MultipartFile {
private byte[] fileBytes;
String name;
String originalFilename;
String contentType;
boolean isEmpty;
long size;
public ConvertToMultipartFile(byte[] fileBytes, String name, String originalFilename, String contentType,
long size) {
this.fileBytes = fileBytes;
this.name = name;
this.originalFilename = originalFilename;
this.contentType = contentType;
this.size = size;
this.isEmpty = false;
}
@Override
public String getName() {
return name;
}
@Override
public String getOriginalFilename() {
return originalFilename;
}
@Override
public String getContentType() {
return contentType;
}
@Override
public boolean isEmpty() {
return isEmpty;
}
@Override
public long getSize() {
return size;
}
@Override
public byte[] getBytes() throws IOException {
return fileBytes;
}
@Override
public InputStream getInputStream() throws IOException {
return new ByteArrayInputStream(fileBytes);
}
@Override
public void transferTo(File dest) throws IOException, IllegalStateException {
new FileOutputStream(dest).write(fileBytes);
}
}
3.File转换为MultipartFile
/**
* File转换为MultipartFile
* @param file
* @return
*/
public static MultipartFile fileToMultipartFile(File file) {
FileItem item = new org.apache.commons.fileupload.disk.DiskFileItemFactory().createItem("file"
, MediaType.MULTIPART_FORM_DATA_VALUE
, true
, file.getName());
try (InputStream input = new FileInputStream(file);
OutputStream os = item.getOutputStream()) {
// 流转移
IOUtils.copy(input, os);
} catch (Exception e) {
throw new IllegalArgumentException("Invalid file: " + e, e);
}
return new CommonsMultipartFile(item);
}
4.将MultipartFile转换为File
/**
* 将MultipartFile转换为File
* @param multiFile
* @return
*/
public static File MultipartFileToFile(MultipartFile multiFile) {
// 获取文件名
String fileName = multiFile.getOriginalFilename();
// 获取文件后缀
String prefix = fileName.substring(fileName.lastIndexOf("."));
// 若须要防止生成的临时文件重复,能够在文件名后添加随机码
try {
File file = File.createTempFile(FileUtil.getFileNameNotPrefix(fileName), prefix);
multiFile.transferTo(file);
return file;
} catch (Exception e) {
e.printStackTrace();
}
return null;
}
5.MultipartFile 获取文件编码为base64
/** * 将MultipartFile 图片文件编码为base64 * @param file * @param status true加:data:multipart/form-data;base64,前缀 false 不加前缀 * @return */
public static String generateBase64(MultipartFile file,Boolean status){
if (file == null || file.isEmpty()) {
throw new RuntimeException("图片不能为空!");
}
String fileName = file.getOriginalFilename();
String fileType = fileName.substring(fileName.lastIndexOf("."));
String contentType = file.getContentType();
byte[] imageBytes = null;
String base64EncoderImg="";
try {
imageBytes = file.getBytes();
BASE64Encoder base64Encoder =new BASE64Encoder();
/** * 1.Java使用BASE64Encoder 需要添加图片头("data:" + contentType + ";base64,"), * 其中contentType是文件的内容格式。 * 2.Java中在使用BASE64Enconder().encode()会出现字符串换行问题,这是因为RFC 822中规定, * 每72个字符中加一个换行符号,这样会造成在使用base64字符串时出现问题, * 所以我们在使用时要先用replaceAll("[\\s*\t\n\r]", "")解决换行的问题。 */
if (status) {
base64EncoderImg = "data:" + contentType + ";base64," + base64Encoder.encode(imageBytes);
}else{
base64EncoderImg = base64Encoder.encode(imageBytes);
}
base64EncoderImg = base64EncoderImg.replaceAll("[\\s*\t\n\r]", "");
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return base64EncoderImg;
}
边栏推荐
- Redis list detailed explanation of character types yyds dry goods inventory
- Interview Reply of Zhuhai Jinshan
- Simulation of Teman green interferometer based on MATLAB
- [cf gym101196-i] waif until dark network maximum flow
- 珠海金山面试复盘
- Luogu p1836 number page solution
- NFT smart contract release, blind box, public offering technology practice -- jigsaw puzzle
- 二叉树创建 & 遍历
- . Net 6 learning notes: what is NET Core
- 23. Update data
猜你喜欢
Nft智能合约发行,盲盒,公开发售技术实战--合约篇
Sanzi chess (C language)
Asia Pacific Financial Media | art cube of "designer universe": Guangzhou community designers achieve "great improvement" in urban quality | observation of stable strategy industry fund
Opencv learning notes 9 -- background modeling + optical flow estimation
Secure captcha (unsafe verification code) of DVWA range
A Closer Look at How Fine-tuning Changes BERT
[redis] Introduction to NoSQL database and redis
datax自检报错 /datax/plugin/reader/._drdsreader/plugin.json]不存在
"Designer universe" Guangdong responds to the opinions of the national development and Reform Commission. Primary school students incarnate as small community designers | national economic and Informa
数据治理:主数据的3特征、4超越和3二八原则
随机推荐
Oracle time display adjustment
Golang DNS write casually
Artcube information of "designer universe": Guangzhou implements the community designer system to achieve "great improvement" of urban quality | national economic and Information Center
Step by step guide to setting NFT as an ens profile Avatar
Key value judgment in the cycle of TS type gymnastics, as keyword use
The State Economic Information Center "APEC industry +" Western Silicon Valley will invest 2trillion yuan in Chengdu Chongqing economic circle, which will surpass the observation of Shanghai | stable
Yu Xia looks at win system kernel -- message mechanism
NFT smart contract release, blind box, public offering technology practice -- jigsaw puzzle
Entity class design for calculating age based on birthday
Circuit breaker: use of hystrix
National economic information center "APEC industry +": economic data released at the night of the Spring Festival | observation of stable strategy industry fund
Asia Pacific Financial Media | art cube of "designer universe": Guangzhou community designers achieve "great improvement" in urban quality | observation of stable strategy industry fund
Data governance: data quality
Learn Arduino with examples
A Closer Look at How Fine-tuning Changes BERT
MySQL view tablespace and create table statements
datax自检报错 /datax/plugin/reader/._drdsreader/plugin.json]不存在
Luogu p4127 [ahoi2009] similar distribution problem solution
[computer skills]
"Designer universe": "benefit dimension" APEC public welfare + 2022 the latest slogan and the new platform will be launched soon | Asia Pacific Financial Media