微服务篇-深入了解 MinIO 文件服务器(你还在使用阿里云 0SS 对象存储图片服务?教你使用 MinIO 文件服务器:实现从部署到具体使用)

🔥博客主页: 【小扳_-CSDN博客】**
❤感谢大家点赞👍收藏⭐评论✍**

文章目录

[1.0 MinIO 文件服务器概述](#1.0 MinIO 文件服务器概述)

[1.1 MinIO 使用 Docker 部署](#1.1 MinIO 使用 Docker 部署)

[1.2 MinIO 控制台的使用](#1.2 MinIO 控制台的使用)

[2.0 使用 Java 操作 MinIO](#2.0 使用 Java 操作 MinIO)

[3.0 使用 minioClient 对象的方法](#3.0 使用 minioClient 对象的方法)

[3.1 判断桶是否存在](#3.1 判断桶是否存在)

[3.2 创建桶](#3.2 创建桶)

[3.3 删除桶](#3.3 删除桶)

[3.4 删除桶内的对象](#3.4 删除桶内的对象)

[3.5 获取 url](#3.5 获取 url)

[3.6 上传文件](#3.6 上传文件)

[3.7 下载文件](#3.7 下载文件)

[3.8 获取所有桶](#3.8 获取所有桶)

[3.9 获取所有桶名](#3.9 获取所有桶名)

[3.10 获取指定桶中的所有对象](#3.10 获取指定桶中的所有对象)

[4.0 MinIO 工具类](#4.0 MinIO 工具类)


1.0 MinIO 文件服务器概述

MinIO 是一个高性能的对象存储服务器,专门设计用来处理大规模的非结构化数据。它提供

与 Amazon S3(简单存储服务)兼容的 API,使得开发人员和运维团队能够轻松实现数据存储和

管理。以下是 MinIO 的一些关键特点和概述:

1)高性能:MinIO 具有极高的吞吐量,能够支持大规模的并发请求,适用于需要快速处理大

量数据的应用场景,如机器学习和数据分析等。

2)易于部署:MinIO 可以在多种环境中部署,包括本地服务器、虚拟机、容器(如 Docker

和 Kubernetes)以及云环境,以灵活适应不同的使用需求。

3)兼容 S3 API:MinIO 采用与 S3 兼容的 API,这意味着用户可以使用现有的 S3 工具和软

件与 MinIO 进行交互,降低了迁移和集成的门槛。

4)数据保护:MinIO 支持多种数据冗余和保护机制,包括纠删码(Erasure Coding),可以

在发生硬件故障时保护数据的完整性。

5)安全性:MinIO 提供多种安全措施,包括身份验证、访问控制、TLS 加密等,确保数据在

传输和存储过程中的安全。

6)企业级功能:MinIO 具备多租户支持、审计日志、生命周期管理等功能,适合企业和组织

使用。

7)开源:MinIO 是一个开源项目,允许社区参与贡献和改进,同时也提供商业支持选项,适

合不同规模的企业使用。

MinIO 官网:MinIO | S3 Compatible Storage for AI

在以往的项目中,用的比较多的是 OSS 服务有腾讯云、阿里云的存储服务,但是这些云存储

的服务大多数都是要收取一定的费用,一直积累起来也是一笔不小的费用。因此,自己部署一台

MinIO 文件服务器是一种不错的选择。

1.1 MinIO 使用 Docker 部署

1)执行以下命令进行部署:

javascript 复制代码
docker run \
   -p 9000:9000 \
   -p 9001:9001 \
   --name minio \
   -v root\minio\data:/data \
   -e "MINIO_ROOT_USER=xbs12345" \
   -e "MINIO_ROOT_PASSWORD=xbs12345" \
   quay.io/minio/minio server /data --console-address ":9001"

docker run:表示启动运行容器。

-p:表示为容器绑定一个本地的端口。

--name:表示为容器创建一个本地的名字。

-v:表示将文件路径设置为容器使用持久卷位置。将数据保存到本地,使其能够在容器重启时保持持久化。

-e:设置账号秘密。

其中访问控制台的端口为:9001,api 的访问端口为:9000 。

2)服务端部署完毕之后,通过控制台访问服务器:

访问 MinIO 控制台:

http://自己的IP地址:9001


1.2 MinIO 控制台的使用

在对象存储服务里面,所有的文件都是以桶的形式来组织的。简单说,可以将桶看作是目

录,这个目录下有很多的文件或者文件夹,这和其它云存储服务基本一致。

首先需要创建桶:

接着,设置桶名:

桶这就创建好了:

默认创建的存储桶,均为私有桶,无法被公开访问,需要设置成公开:


通常而言,要将数据写入操作进行控制;而读操作,很多不涉及安全问题,希望能被互联网

公开访问,以便加快文件的访问速度。

可以在存储桶里面配置,将数据读取权限设置为公开访问:


测试上传图片:

选择 Upload:

上传成功:

接着通过:http//自己的IP地址:9000/text/R-C (2).jpg 来访问,此时 "/text/R-C (2).jpg" 是桶

名与文件名的拼接。

最后访问到已经上传的图片了:

2.0 使用 Java 操作 MinIO

1)首先引入依赖:

XML 复制代码
        <!-- 操作minio的java客户端-->
        <dependency>
            <groupId>io.minio</groupId>
            <artifactId>minio</artifactId>
            <version>8.5.2</version>
        </dependency>

2)获取 API 访问凭证:

生成密钥之后,需要记住这对密钥,最好保存起来。

3)在 application.yaml 中配置 MinIo:

javascript 复制代码
#minio配置
spring:
  minio:
    access-key: xxxxx
    secret-key: xxxxx
    url: http://xxxxx:9000  #访问地址
    bucket-name: xbs

将之前的密钥配置到该配置文件中,url 是 MinIO 的服务器地址,bucket-name 是表示对具

体某一个桶进行操作。

4)设置配置类:

java 复制代码
import io.minio.MinioClient;
import lombok.Data;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

@Data
@Configuration
@ConfigurationProperties(prefix = "spring.minio")
public class MinioConfig {

    private String accessKey;
    private String secretKey;
    private String url;
    private String bucketName;

    @Bean
    public MinioClient minioClient(){
        return MinioClient.builder()
                .endpoint(url)
                .credentials(accessKey,secretKey)
                .build();
    }
}

通过 @ConfigurationProperties(prefix = "spring.minio") 注解,将配置文件中的参数映射

到当前类中的对应的属性中,通过 @Configuration 注解,将 minioClient 实体对象添加到

Spring IOC容器中。

接下来,就可以使用 minioClient 实体对象中的方法,对文件进行操作,如上传文件到

MinIO服务器中、从 MinIO 服务器中下载文件、删除 MinIO 服务器中的文件等等。

3.0 使用 minioClient 对象的方法

3.1 判断桶是否存在

代码如下:

java 复制代码
    @Autowired
    private MinioClient minioClient;


    /**
     * 判断bucket是否存在,不存在就创建
     * @param bucketName bucket名称
     * @return 成功返回true,否则返回false
     */
    public boolean exitBucket(String bucketName){
        try {
            //判断bucket是否存在
            BucketExistsArgs bucketExistsArgs = BucketExistsArgs.builder().bucket(bucketName).build();
            boolean isExist = minioClient.bucketExists(bucketExistsArgs);
            if (isExist){
                return true;
            }
            //不存在的话,则创建bucket
            MakeBucketArgs makeBucketArgs = MakeBucketArgs.builder().bucket(bucketName).build();
            minioClient.makeBucket(makeBucketArgs);
            return true;
        }catch (Exception e){
            e.printStackTrace();
            log.info("minio 连接失败");
            return false;
        }
    }

根据桶名,来判断该桶是否存在 MinIO 中。

测试:

java 复制代码
    @Test
    public void test() throws Exception {

        BucketExistsArgs build = BucketExistsArgs.builder().bucket("xbs").build();
        boolean b = minioClient.bucketExists(build);
        if (b){
            System.out.println("该桶存在");
        }
    }

执行结果:

3.2 创建桶

代码如下:

java 复制代码
    /**
     * 创建bucket
     * @param bucketName bucket名称
     * @return 成功创建返回true,否则返回false
     */
    public boolean makeBucket(String bucketName){

        try {
            MakeBucketArgs makeBucketArgs = MakeBucketArgs.builder().bucket(bucketName).build();
            minioClient.makeBucket(makeBucketArgs);
        }catch (Exception e){
            e.printStackTrace();
            log.info("桶创建失败");
            return false;
        }
        return true;
    }

参数就只有一个,在 MinIO 服务器中创建 bucketName 的桶。

测试:

java 复制代码
    @Test
    public void makeBucket() throws Exception {
        boolean xbs = minioUtils.makeBucket("hero");
        if (xbs){
            System.out.println("创建成功");
            return;
        }
        System.out.println("创建失败");
    }

执行结果:


3.3 删除桶

代码如下:

java 复制代码
    /**
     * 根据桶名删除
     * @param bucketName 桶名
     * @return 删除成功返回true,否则返回false
     */
    public boolean removeBucket(String bucketName){

        try {
            RemoveBucketArgs removeBucketArgs = RemoveBucketArgs.builder().bucket(bucketName).build();
            minioClient.removeBucket(removeBucketArgs);
        }catch (Exception e){
            e.printStackTrace();
            log.info("桶删除失败");
            return false;
        }
        return true;
    }

直接根据桶名来删除。

测试:

java 复制代码
    @Test
    public void removeBucket() throws Exception {
        boolean hero = minioUtils.removeBucket("hero");
        if (hero){
            System.out.println("删除成功");
            return;
        }
        System.out.println("删除失败");

    }

执行结果:


需要注意的是,当桶不为空,则删除桶失败。

测试:

3.4 删除桶内的对象

代码如下:

java 复制代码
    /**
     * 根据桶名、对象名来删除一个对象
     * @param bucketName 桶名
     * @param objectName 对象名
     * @return 删除成功返回true,否则返回false
     * @throws Exception
     */
    public boolean removeObject(String bucketName, String objectName) throws Exception {

        try {
            RemoveObjectArgs removeObjectArgs = RemoveObjectArgs.builder().bucket(bucketName).object(objectName).build();
            minioClient.removeObject(removeObjectArgs);
            return true;
        }catch (Exception e) {
            e.printStackTrace();
            log.info("删除失败");
            return false;
        }
    }

参数有两个,一个是桶名、另一个是对象名。根据桶名和对象名,可以确定删除的对象。这

里说的对象名,可以理解为文件名。

测试:

java 复制代码
    @Test
    public void removeObject() throws Exception {
        boolean xbs = minioUtils.removeObject("text", "R-C (2).jpg");
        if (xbs){
            System.out.println("删除成功");
            return;
        }
        System.out.println("删除失败");
    }

执行结果:


这就删除成功了。

除了可以一个一个删除,也可以进行批量删除:

代码如下:

java 复制代码
    /**
     * 删除指定桶的多个文件对象,返回删除错误的对象列表,全部删除成功,返回空列表
     *
     * @param bucketName  存储桶名称
     * @param objectNames 含有要删除的多个object名称的迭代器对象
     * @return
     * eg:
     * List<DeleteObject> objects = new LinkedList<>();
     * objects.add(new DeleteObject("my-objectname1"));
     * objects.add(new DeleteObject("my-objectname2"));
     * objects.add(new DeleteObject("my-objectname3"));
    **/
    public List<String> removeObjects(String bucketName, List<DeleteObject> objectNames) throws Exception {
        List<String> deleteErrorNames = new ArrayList<>();
        try {
            RemoveObjectsArgs removeObjectsArgs = RemoveObjectsArgs
                    .builder()
                    .bucket(bucketName)
                    .objects(objectNames)
                    .build();
            Iterable<Result<DeleteError>> results = minioClient.removeObjects(removeObjectsArgs);
            for (Result<DeleteError> result : results) {
                DeleteError deleteError = result.get();
                deleteErrorNames.add(deleteError.objectName());
            }
            return deleteErrorNames;
        }catch (Exception e) {
            e.printStackTrace();
            log.info("删除失败");
            return null;
        }
    }

3.5 获取 url

当上传完照片之后,需要拿到可以访问到该照片的 url:

代码如下:

java 复制代码
    /**
     * 获取url
     * @param bucketName 桶名
     * @param objectName 对象名
     * @param time 限制时间
     * @param unit 时间单位
     * @return 找不到返回null,找到返回对象的url
     */
    public String getUrl(String bucketName, String objectName, int time, TimeUnit unit){
        try {

            GetPresignedObjectUrlArgs getPresignedObjectUrlArgs = GetPresignedObjectUrlArgs
                    .builder()
                    .method(Method.GET)
                    .bucket(bucketName)
                    .object(objectName)
                    .expiry(time, unit)
                    .build();
            return minioClient.getPresignedObjectUrl(getPresignedObjectUrlArgs);
        }catch (Exception e){
            e.printStackTrace();
            log.info("获取url失败");
            return null;
        }
    }

具体的参数有三个,桶名、对象名和设置过期时间。顾名思义,当超过了过期时间后,访问

图片失败。

测试:

java 复制代码
    @Test
    public void getUrl() throws Exception{
        String xbs = minioUtils.getUrl("xbs", "v2-44a694ce65533da4b79b96a003acbbc7_r.jpg", 10, TimeUnit.SECONDS);
        System.out.println(xbs);
    }

执行结果:

得到 url 后,可以直接访问:

当超过 10 秒后,再次访问:

时间过期了,就访问不了。

3.6 上传文件

代码如下:

java 复制代码
    /**
     * 上传文件
     * @param file 需要上传的文件
     * @param fileName 文件在桶中的命名
     * @param bucketName 需要上传的桶名
     * @return 上传成功返回true,否则返回false
     */
    public boolean upload(MultipartFile file,String fileName,String bucketName){

        try {
            InputStream fileInputStream = file.getInputStream();
            PutObjectArgs putObjectArgs = PutObjectArgs
                    .builder()
                    .bucket(bucketName)
                    .object(fileName+file.getName().substring(file.getName().lastIndexOf(".")))
                    .stream(fileInputStream, file.getSize(), -1)
                    .contentType(file.getContentType())
                    .build();

            minioClient.putObject(putObjectArgs);
        }catch (Exception e){
            e.printStackTrace();
            log.info("上传失败");
            return false;
        }
        return true;
    }

解析核心代码:

1)首先,设置目标存储桶的名称为 bucketName。

2)构建对象名称:fileName: 用户自定义的文件名前缀。

file.getName().substring(file.getName().lastIndexOf(".")): 获取原始文件的扩展名(从最后一个

点开始截取)。最终的对象名称是由 fileName 和文件扩展名拼接而成,确保上传后的文件名包含

正确的扩展名。

3)fileInputStream: 文件的输入流,用于读取文件内容并上传到 MinIO。

file.getSize(): 文件的大小(以字节为单位),告诉 MinIO 文件的实际大小。

-1: 表示未知的分段大小(part size),MinIO 会根据文件大小自动处理分段上传。

4)设置文件的内容类型(MIME 类型),例如 image/jpeg、application/pdf 等,这有助于

客户端正确解析下载的文件。

测试:

java 复制代码
    @Test
    public void upload() throws Exception {
        // 创建一个 MockMultipartFile 实例来模拟图片文件
        String fileName = "1111.jpg";
        String contentType = "image/jpg";
        Path path = Paths.get("D:\\照片\\1111.jpg"); // 假设图片文件在目录下
        byte[] content = Files.readAllBytes(path);

        MultipartFile file = new MockMultipartFile(fileName, fileName, contentType, content);

        boolean xbs = minioUtils.upload(file, "4", "xbs");
        if (xbs){
            System.out.println("上传成功");
        }
    }

执行结果:


上传成功了。

除了这种上传方式,还有一种是直接根据文件路径进行上传:

代码如下:

java 复制代码
    /**
     * 上传文件
     * @param bucketName 桶名
     * @param objectName 对象名
     * @param fileName 文件路径
     * @return 上传成功返回true,否则返回false
     * @throws Exception
     */
    public boolean uploadObject(String bucketName, String objectName, String fileName) throws Exception {

        try {
            UploadObjectArgs uploadObjectArgs = UploadObjectArgs.builder().bucket(bucketName).object(objectName).filename(fileName).build();
            minioClient.uploadObject(uploadObjectArgs);
            log.info("上传成功");
            return true;
        }catch (Exception e){
            e.printStackTrace();
            log.info("上传失败");
            return false;
        }
    }

有三个简单的参数,桶名、需要上传文件的路径、上传文件之后在桶中的命名。

3.7 下载文件

代码如下:

java 复制代码
    /**
     * 下载文件
     * @param bucketName 桶名
     * @param objectName 目标下载对象
     * @return 下载成功返回true,否则返回false
     * @throws IOException
     */
    public boolean download(String bucketName,String objectName) throws IOException {
        InputStream inputStream = null;
        OutputStream outputStream = null;
        try {
            GetObjectArgs getObjectArgs = GetObjectArgs.builder()
                    .bucket(bucketName)
                    .object(objectName)
                    .build();
            inputStream = minioClient.getObject(getObjectArgs);

            File file = new File("D:/Download/" + objectName);
            outputStream = new FileOutputStream(file);
            IOUtils.copy(inputStream,outputStream);

        }catch (Exception e){
            e.printStackTrace();
            log.info("下载失败");
            return false;
        }finally {
            try {
                if (inputStream != null) {
                    try {
                        inputStream.close();
                    } catch (IOException e) {
                        e.printStackTrace();
                    }
                }
                if (outputStream != null) {
                    try {
                        outputStream.close();
                    } catch (IOException e) {
                        e.printStackTrace();
                    }
                }
            } catch (Exception e) {
                e.printStackTrace();
            }

        }
        return true;
    }

根据桶名、对象名来选中需要下载的文件,接着通过获取输入流之后拷贝到输出流中。从而

完成文件下载。

测试:

java 复制代码
    @Test
    public void download() throws Exception{
        boolean xbs = minioUtils.download("xbs", "1.jpg");
        if (xbs){
            System.out.println("下载成功");
            return;
        }
        System.out.println("下载失败");
    }

执行结果:


这就下载成功了。

除了这种下载方式,还有另一个下载方式:

代码如下:

java 复制代码
    /**
     * 下载文件
     * @param bucketName 桶名
     * @param objectName 对象名
     * @param fileName 下载到本地路径
     * @return
     * @throws Exception
     */
    public boolean downloadObject(String bucketName, String objectName, String fileName) throws Exception {

        try {
            DownloadObjectArgs downloadObjectArgs = DownloadObjectArgs
                    .builder()
                    .bucket(bucketName)
                    .object(objectName)
                    .filename(fileName)
                    .build();
            minioClient.downloadObject(downloadObjectArgs);
            log.info("下载成功");
            return true;
        }catch (Exception e) {
            e.printStackTrace();
            log.info("下载失败");
            return false;
        }
    }

直接给定三个参数:桶名、对象名、下载路径就可以完成下载文件。

3.8 获取所有桶

代码如下:

java 复制代码
    /**
     * 获取所有桶
     * @return 桶集合
     */
    public List<Bucket> getAllBuckets(){
        List<Bucket> buckets = null;
        try {
            buckets = minioClient.listBuckets();
        }catch (Exception e){
            e.printStackTrace();
            log.info("获取桶失败");
            return null;
        }
        return buckets;
    }

测试:

java 复制代码
    @Test
    public void getBucket(){
        List<Bucket> allBuckets = minioUtils.getAllBuckets();
        for (Bucket bucket : allBuckets) {
            System.out.println("bucket.name() = " + bucket.name());
            System.out.println("bucket.creationDate() = " + bucket.creationDate().format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")));
        }
    }

执行结果:

3.9 获取所有桶名

代码如下:

java 复制代码
    /**
     * 获取所有桶名
     * @return 桶名集合
     */
    public List<String> getAllBucketNames(){
        List<Bucket> allBuckets = getAllBuckets();
        List<String> collect = null;
        if (CollUtil.isNotEmpty(allBuckets)){
            collect = allBuckets.stream().map(Bucket::name).collect(Collectors.toList());
        }
        return collect;
    }

测试:

java 复制代码
    @Test
    public void getAllBucketNames() throws Exception {
        List<String> bucketNames = minioUtils.getAllBucketNames();
        if (CollUtils.isNotEmpty(bucketNames)) {
            System.out.println(bucketNames);
        }
    }

执行结果:

3.10 获取指定桶中的所有对象

代码如下:

java 复制代码
    /**
     * 获取桶内所有对象
     * @param bucketName 桶名
     * @return 返回对象集合
     */
    public Iterable<Result<Item>> listObjects(String bucketName){

        try {
            ListObjectsArgs listObjectsArgs = ListObjectsArgs.builder().bucket(bucketName).build();
            return minioClient.listObjects(listObjectsArgs);
        }catch (Exception e){
            e.printStackTrace();
            log.info("获取桶失败");
            return null;
        }
    }

唯一的参数就是桶名,根据桶名来查询当前桶中的所有对象。

测试:

java 复制代码
    @Test
    public void listObjects() throws Exception {
        Iterable<Result<io.minio.messages.Item>> listObjects = minioUtils.listObjects("xbs");
        for (Result<io.minio.messages.Item> itemResult : listObjects) {
            Item item = itemResult.get();
            System.out.println("item.getSize() = " + item.size());
            System.out.println("item.getObjectName() = " + item.objectName());
        }
    }

执行结果:

4.0 MinIO 工具类

通过以上的方法可以解决绝大部分的场景应用了,可以将这些的方法封装成一个 MinIO 的

工具类。

代码如下:

java 复制代码
import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.io.IoUtil;
import com.hmall.config.MinioConfig;
import io.minio.*;
import io.minio.http.Method;
import io.minio.messages.Bucket;
import io.minio.messages.DeleteError;
import io.minio.messages.DeleteObject;
import io.minio.messages.Item;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.compress.utils.IOUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import org.springframework.web.multipart.MultipartFile;

import java.io.*;
import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.TimeUnit;
import java.util.stream.Collectors;

@Component
@Slf4j
//关于minio的工具
public class MinioUtils {


    @Autowired
    private MinioConfig minioConfig;

    @Autowired
    private MinioClient minioClient;


    /**
     * 判断bucket是否存在,不存在就创建
     * @param bucketName bucket名称
     * @return 成功返回true,否则返回false
     */
    public boolean exitBucket(String bucketName){
        try {
            //判断bucket是否存在
            BucketExistsArgs bucketExistsArgs = BucketExistsArgs.builder().bucket(bucketName).build();
            boolean isExist = minioClient.bucketExists(bucketExistsArgs);
            if (isExist){
                return true;
            }
            //不存在的话,则创建bucket
            MakeBucketArgs makeBucketArgs = MakeBucketArgs.builder().bucket(bucketName).build();
            minioClient.makeBucket(makeBucketArgs);
            return true;
        }catch (Exception e){
            e.printStackTrace();
            log.info("minio 连接失败");
            return false;
        }
    }


    /**
     * 创建bucket
     * @param bucketName bucket名称
     * @return 成功创建返回true,否则返回false
     */
    public boolean makeBucket(String bucketName){

        try {
            MakeBucketArgs makeBucketArgs = MakeBucketArgs.builder().bucket(bucketName).build();
            minioClient.makeBucket(makeBucketArgs);
        }catch (Exception e){
            e.printStackTrace();
            log.info("桶创建失败");
            return false;
        }
        return true;
    }



    /**
     * 根据桶名删除
     * @param bucketName 桶名
     * @return 删除成功返回true,否则返回false
     */
    public boolean removeBucket(String bucketName){

        try {
            RemoveBucketArgs removeBucketArgs = RemoveBucketArgs.builder().bucket(bucketName).build();
            minioClient.removeBucket(removeBucketArgs);
        }catch (Exception e){
            e.printStackTrace();
            log.info("桶删除失败");
            return false;
        }
        return true;
    }


    /**
     * 根据桶名、对象名来删除一个对象
     * @param bucketName 桶名
     * @param objectName 对象名
     * @return 删除成功返回true,否则返回false
     * @throws Exception
     */
    public boolean removeObject(String bucketName, String objectName) throws Exception {

        try {
            RemoveObjectArgs removeObjectArgs = RemoveObjectArgs.builder().bucket(bucketName).object(objectName).build();
            minioClient.removeObject(removeObjectArgs);
            return true;
        }catch (Exception e) {
            e.printStackTrace();
            log.info("删除失败");
            return false;
        }
    }


    /**
     * 删除指定桶的多个文件对象,返回删除错误的对象列表,全部删除成功,返回空列表
     *
     * @param bucketName  存储桶名称
     * @param objectNames 含有要删除的多个object名称的迭代器对象
     * @return
     * eg:
     * List<DeleteObject> objects = new LinkedList<>();
     * objects.add(new DeleteObject("my-objectname1"));
     * objects.add(new DeleteObject("my-objectname2"));
     * objects.add(new DeleteObject("my-objectname3"));
    **/
    public List<String> removeObjects(String bucketName, List<DeleteObject> objectNames) throws Exception {
        List<String> deleteErrorNames = new ArrayList<>();
        try {
            RemoveObjectsArgs removeObjectsArgs = RemoveObjectsArgs
                    .builder()
                    .bucket(bucketName)
                    .objects(objectNames)
                    .build();
            Iterable<Result<DeleteError>> results = minioClient.removeObjects(removeObjectsArgs);
            for (Result<DeleteError> result : results) {
                DeleteError deleteError = result.get();
                deleteErrorNames.add(deleteError.objectName());
            }
            return deleteErrorNames;
        }catch (Exception e) {
            e.printStackTrace();
            log.info("删除失败");
            return null;
        }
    }


    /**
     * 获取url
     * @param bucketName 桶名
     * @param objectName 对象名
     * @param time 限制时间
     * @param unit 时间单位
     * @return 找不到返回null,找到返回对象的url
     */
    public String getUrl(String bucketName, String objectName, int time, TimeUnit unit){
        try {

            GetPresignedObjectUrlArgs getPresignedObjectUrlArgs = GetPresignedObjectUrlArgs
                    .builder()
                    .method(Method.GET)
                    .bucket(bucketName)
                    .object(objectName)
                    .expiry(time, unit)
                    .build();
            return minioClient.getPresignedObjectUrl(getPresignedObjectUrlArgs);
        }catch (Exception e){
            e.printStackTrace();
            log.info("获取url失败");
            return null;
        }
    }


    /**
     * 上传文件
     * @param file 需要上传的文件
     * @param fileName 文件在桶中的命名
     * @param bucketName 需要上传的桶名
     * @return 上传成功返回true,否则返回false
     */
    public boolean upload(MultipartFile file,String fileName,String bucketName){

        try {
            InputStream fileInputStream = file.getInputStream();
            PutObjectArgs putObjectArgs = PutObjectArgs
                    .builder()
                    .bucket(bucketName)
                    .object(fileName+file.getName().substring(file.getName().lastIndexOf(".")))
                    .stream(fileInputStream, file.getSize(), -1)
                    .contentType(file.getContentType())
                    .build();

            minioClient.putObject(putObjectArgs);
        }catch (Exception e){
            e.printStackTrace();
            log.info("上传失败");
            return false;
        }
        return true;
    }


    /**
     * 上传文件
     * @param bucketName 桶名
     * @param objectName 对象名
     * @param fileName 文件路径
     * @return 上传成功返回true,否则返回false
     * @throws Exception
     */
    public boolean uploadObject(String bucketName, String objectName, String fileName) throws Exception {

        try {
            UploadObjectArgs uploadObjectArgs = UploadObjectArgs.builder().bucket(bucketName).object(objectName).filename(fileName).build();
            minioClient.uploadObject(uploadObjectArgs);
            log.info("上传成功");
            return true;
        }catch (Exception e){
            e.printStackTrace();
            log.info("上传失败");
            return false;
        }
    }




    /**
     * 下载文件
     * @param bucketName 桶名
     * @param objectName 目标下载对象
     * @return 下载成功返回true,否则返回false
     * @throws IOException
     */
    public boolean download(String bucketName,String objectName) throws IOException {
        InputStream inputStream = null;
        OutputStream outputStream = null;
        try {
            GetObjectArgs getObjectArgs = GetObjectArgs.builder()
                    .bucket(bucketName)
                    .object(objectName)
                    .build();
            inputStream = minioClient.getObject(getObjectArgs);

            File file = new File("D:/Download/" + objectName);
            outputStream = new FileOutputStream(file);
            IOUtils.copy(inputStream,outputStream);

        }catch (Exception e){
            e.printStackTrace();
            log.info("下载失败");
            return false;
        }finally {
            try {
                if (inputStream != null) {
                    try {
                        inputStream.close();
                    } catch (IOException e) {
                        e.printStackTrace();
                    }
                }
                if (outputStream != null) {
                    try {
                        outputStream.close();
                    } catch (IOException e) {
                        e.printStackTrace();
                    }
                }
            } catch (Exception e) {
                e.printStackTrace();
            }

        }
        return true;
    }


    /**
     * 下载文件
     * @param bucketName 桶名
     * @param objectName 对象名
     * @param fileName 下载到本地路径
     * @return
     * @throws Exception
     */
    public boolean downloadObject(String bucketName, String objectName, String fileName) throws Exception {

        try {
            DownloadObjectArgs downloadObjectArgs = DownloadObjectArgs
                    .builder()
                    .bucket(bucketName)
                    .object(objectName)
                    .filename(fileName)
                    .build();
            minioClient.downloadObject(downloadObjectArgs);
            log.info("下载成功");
            return true;
        }catch (Exception e) {
            e.printStackTrace();
            log.info("下载失败");
            return false;
        }
    }


    /**
     * 获取所有桶
     * @return 桶集合
     */
    public List<Bucket> getAllBuckets(){
        List<Bucket> buckets = null;
        try {
            buckets = minioClient.listBuckets();
        }catch (Exception e){
            e.printStackTrace();
            log.info("获取桶失败");
            return null;
        }
        return buckets;
    }


    /**
     * 获取所有桶名
     * @return 桶名集合
     */
    public List<String> getAllBucketNames(){
        List<Bucket> allBuckets = getAllBuckets();
        List<String> collect = null;
        if (CollUtil.isNotEmpty(allBuckets)){
            collect = allBuckets.stream().map(Bucket::name).collect(Collectors.toList());
        }
        return collect;
    }


    /**
     * 获取桶内所有对象
     * @param bucketName 桶名
     * @return 返回对象集合
     */
    public Iterable<Result<Item>> listObjects(String bucketName){

        try {
            ListObjectsArgs listObjectsArgs = ListObjectsArgs.builder().bucket(bucketName).build();
            return minioClient.listObjects(listObjectsArgs);
        }catch (Exception e){
            e.printStackTrace();
            log.info("获取桶失败");
            return null;
        }
    }
    
}
相关推荐
黑胡子大叔的小屋26 分钟前
基于springboot的海洋知识服务平台的设计与实现
java·spring boot·毕业设计
ThisIsClark28 分钟前
【后端面试总结】深入解析进程和线程的区别
java·jvm·面试
9527华安1 小时前
FPGA多路MIPI转FPD-Link视频缩放拼接显示,基于IMX327+FPD953架构,提供2套工程源码和技术支持
fpga开发·架构·音视频
雷神乐乐1 小时前
Spring学习(一)——Sping-XML
java·学习·spring
小林coding2 小时前
阿里云 Java 后端一面,什么难度?
java·后端·mysql·spring·阿里云
V+zmm101342 小时前
基于小程序宿舍报修系统的设计与实现ssm+论文源码调试讲解
java·小程序·毕业设计·mvc·ssm
文大。2 小时前
2024年广西职工职业技能大赛-Spring
java·spring·网络安全
Anna_Tong2 小时前
云原生大数据计算服务 MaxCompute 是什么?
大数据·阿里云·云原生·maxcompute·odps
一只小小翠2 小时前
EasyExcel 模板+公式填充
java·easyexcel
运维&陈同学3 小时前
【模块一】kubernetes容器编排进阶实战之基于velero及minio实现etcd数据备份与恢复
数据库·后端·云原生·容器·kubernetes·etcd·minio·velero