This is the fourth day of my participation in the August More text Challenge. For details, see:August is more challenging

Basically every project, there will be a need to upload files, pictures, files can be stored in Ali Cloud, Tencent cloud, Qiniuyun such object storage services, but use these can not be paid, this makes people very uncomfortable ah. Then I found this Minio, and I felt very cool. I was in control. Code with a detailed explanation, do not understand can also leave a message or private message, will make a reply in time!

Cover Location: Shunhe Village, Lanshan County, Yongzhou City, Hunan Province

Author: Laugh with your heart *👩

First, preface and environmental preparation

Minio is a high performance object storage product released under the GNU Affero General Public License V3.0.

Minio features:

  • High performance (up to 183 GB/s and 171 GB/s at read/write speeds)
  • Scalability (The scaling starts with a single cluster, which can be federated with other MinIO clusters to create global namespaces, and can span multiple different data centers as needed.)
  • It can store many types of files, such as video, execl files, pictures and so on.
  • Actual combat words 1) file storage 2) database file backup, etc

Everyone has used cloud storage. Minio is similar, but much more convenient.

Don’t look at me write so much code, in fact, the logic is very simple, you install minio, direct CV method can run. 😀 👨 💻

By the way, if you need to find a utility class to determine the type of file, this article also covers it. 🙆 came ️

Environment to prepare

  • ☞ Docker install MInio on Docker server
  • Local download Minio: official Minio website

The project structure

Once the Minio service is set up, project coding is actually quite simple.

Ii. Project initialization

Create a New SpringBoot project

I think we all do that

2.2. Pom. XML file

<parent>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-parent</artifactId>
    <version>2.5.2</version>
    <relativePath/> <! -- lookup parent from repository -->
</parent>

<dependencies>
    <! Minio JAR -->
    <dependency> 
        <groupId>io.minio</groupId>
        <artifactId>minio</artifactId>
        <version>8.2.1</version>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter</artifactId>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
    </dependency>
    <dependency>
        <groupId>org.projectlombok</groupId>
        <artifactId>lombok</artifactId>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-configuration-processor</artifactId>
        <optional>true</optional>
    </dependency>
    <dependency>
        <groupId>org.apache.commons</groupId>
        <artifactId>commons-lang3</artifactId>
    </dependency>
    <dependency>
        <groupId>cn.hutool</groupId>
        <artifactId>hutool-all</artifactId>
        <version>5.6.5</version>
    </dependency>

    <! -- for compatibility I use jdk11-->
    <dependency>
        <groupId>javax.xml.bind</groupId>
        <artifactId>jaxb-api</artifactId>
        <version>2.3.0</version>
    </dependency>
    <dependency>
        <groupId>com.sun.xml.bind</groupId>
        <artifactId>jaxb-impl</artifactId>
        <version>2.3.0</version>
    </dependency>
    <dependency>
        <groupId>com.sun.xml.bind</groupId>
        <artifactId>jaxb-core</artifactId>
        <version>2.3.0</version>
    </dependency>
    <dependency>
        <groupId>javax.activation</groupId>
        <artifactId>activation</artifactId>
        <version>1.1.1</version>
    </dependency>
</dependencies>
Copy the code

2.3 yML files

spring:
  profiles:
    active: prod
Copy the code
server:
  port: 8085
spring:
  application:
    name: springboot-minio
minio:
  endpoint: http://IP address : 9000
  port: 9000
  accessKey: Login account
  secretKey: The login password
  secure: false
  bucket-name: commons This is to give a default bucket name
  image-size: 10485760 # HERE I set the maximum size of the image file
  file-size: 1073741824 The maximum size of the file is set
Copy the code

2.4. Improve the package structure

It’s up to you. (🐕 survival)

Three, knock code (CV method)

3.1, MinioProperties

The main purpose of this class is to bind to configuration files for injection and maintenance.

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;


/ * * *@author crush
 */
@Data
@Configuration
@ConfigurationProperties(prefix = "minio")
public class MinioProperties {

    /** * is a URL, domain name, IPv4 or IPv6 address ") */
    private String endpoint;

    /** */ "TCP/IP port number "*/
    private Integer port;

    /** */ /"accessKey is similar to user ID and is used to uniquely identify your account "*/
    private String accessKey;

    /** */ /"secretKey is your password "*/
    private String secretKey;

    /** */ /" If true, use HTTPS instead of HTTP. The default is true" */
    private boolean secure;

    /** */ /" default bucket "*/
    private String bucketName;

    /** * The maximum size of the image */
    private long imageSize;

    /** * Maximum size of other files */
    private long fileSize;


    /** * this class is the class where the client performs operations */
    @Bean
    public MinioClient minioClient(a) {
        MinioClient minioClient =
                MinioClient.builder()
                        .credentials(accessKey, secretKey)
                        .endpoint(endpoint,port,secure)
                        .build();
        returnminioClient; }}Copy the code

3.2. Tool classes used

  1. FileTypeUtils: Is a utility class that I repackaged with the Hutool toolkit to facilitate the return data of calls.

    I think it is quite practical (👩🚀🤱)

  2. MinioUtil: encapsulates the minioClient operation again.

FileTypeUtils

I’m dividing the files into categories, and then choosing the way to save the files according to the exact file name extension.

import cn.hutool.core.io.FileTypeUtil;
import org.springframework.web.multipart.MultipartFile;

import java.io.IOException;
import java.io.InputStream;

/ * * *@Author: crush
 * @Date: 2021-07-25 22:26
 * version 1.0
 */
public class FileTypeUtils {


    private final static String IMAGE_TYPE = "image/";
    private final static String AUDIO_TYPE = "audio/";
    private final static String VIDEO_TYPE = "video/";
    private final static String APPLICATION_TYPE = "application/";
    private final static String TXT_TYPE = "text/";

    public static String getFileType(MultipartFile multipartFile) {
        InputStream inputStream = null;
        String type = null;
        try {
            inputStream = multipartFile.getInputStream();
            type = FileTypeUtil.getType(inputStream);
            System.out.println(type);
            if (type.equalsIgnoreCase("JPG") || type.equalsIgnoreCase("JPEG")
                    || type.equalsIgnoreCase("GIF") || type.equalsIgnoreCase("PNG")
                    || type.equalsIgnoreCase("BMP") || type.equalsIgnoreCase("PCX")
                    || type.equalsIgnoreCase("TGA") || type.equalsIgnoreCase("PSD")
                    || type.equalsIgnoreCase("TIFF")) {
                return IMAGE_TYPE+type;
            }
            if (type.equalsIgnoreCase("mp3") || type.equalsIgnoreCase("OGG")
                    || type.equalsIgnoreCase("WAV") || type.equalsIgnoreCase("REAL")
                    || type.equalsIgnoreCase("APE") || type.equalsIgnoreCase("MODULE")
                    || type.equalsIgnoreCase("MIDI") || type.equalsIgnoreCase("VQF")
                    || type.equalsIgnoreCase("CD")) {
                return AUDIO_TYPE+type;
            }
            if (type.equalsIgnoreCase("mp4") || type.equalsIgnoreCase("avi")
                    || type.equalsIgnoreCase("MPEG-1") || type.equalsIgnoreCase("RM")
                    || type.equalsIgnoreCase("ASF") || type.equalsIgnoreCase("WMV")
                    || type.equalsIgnoreCase("qlv") || type.equalsIgnoreCase("MPEG-2")
                    || type.equalsIgnoreCase("MPEG4") || type.equalsIgnoreCase("mov")
                    || type.equalsIgnoreCase("3gp")) {
                return VIDEO_TYPE+type;
            }
            if (type.equalsIgnoreCase("doc") || type.equalsIgnoreCase("docx")
                    || type.equalsIgnoreCase("ppt") || type.equalsIgnoreCase("pptx")
                    || type.equalsIgnoreCase("xls") || type.equalsIgnoreCase("xlsx")
                    || type.equalsIgnoreCase("zip")||type.equalsIgnoreCase("jar")) {
                return APPLICATION_TYPE+type;
            }
            if (type.equalsIgnoreCase("txt")) {
                returnTXT_TYPE+type; }}catch (IOException e) {
            e.printStackTrace();
        }
        return null; }}Copy the code

MinioUtil

This one is a bit more, after all, it is a reencapsulation of minioClient. Code is simple, you don’t panic, direct CV finished slowly see 🧜♂️

import java.io.ByteArrayInputStream;
import java.io.InputStream;
import java.nio.charset.StandardCharsets;
import java.util.ArrayList;
import java.util.LinkedList;
import java.util.List;
import java.util.concurrent.TimeUnit;
import javax.servlet.ServletOutputStream;
import javax.servlet.http.HttpServletResponse;

import com.crush.minio.config.MinioProperties;
import io.minio.*;
import io.minio.http.Method;
import io.minio.messages.DeleteObject;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import org.springframework.web.multipart.MultipartFile;
import io.minio.errors.ErrorResponseException;
import io.minio.messages.Bucket;
import io.minio.messages.DeleteError;
import io.minio.messages.Item;
import lombok.SneakyThrows;

/ * * *@Author crush
 * @Date2021/7/25 "* /

@Component
public class MinioUtil {

    private final MinioClient minioClient;

    private final MinioProperties minioProperties;

    public MinioUtil(MinioClient minioClient, MinioProperties minioProperties) {
        this.minioClient = minioClient;
        this.minioProperties = minioProperties;
    }

    /** * Check whether ** exists in the bucket@paramBucketName bucketName *@return* /
    @SneakyThrows
    public boolean bucketExists(String bucketName) {
        boolean found =
                minioClient.bucketExists(BucketExistsArgs.builder().bucket(bucketName).build());
        if (found) {
            System.out.println(bucketName + " exists");
        } else {
            System.out.println(bucketName + " does not exist");
        }
        return found;
    }

    /** * Create buckets **@paramBucketName bucketName */
    @SneakyThrows
    public boolean makeBucket(String bucketName) {
        boolean flag = bucketExists(bucketName);
        if(! flag) { minioClient.makeBucket( MakeBucketArgs.builder() .bucket(bucketName) .build());return true;
        } else {
            return false; }}/** * List all bucket names **@return* /
    @SneakyThrows
    public List<String> listBucketNames(a) {
        List<Bucket> bucketList = listBuckets();
        List<String> bucketListName = new ArrayList<>();
        for (Bucket bucket : bucketList) {
            bucketListName.add(bucket.name());
        }
        return bucketListName;
    }

    /** * List all buckets@return* /
    @SneakyThrows
    public List<Bucket> listBuckets(a) {
        return minioClient.listBuckets();
    }


    /** * Delete bucket **@paramBucketName bucketName *@return* /
    @SneakyThrows
    public boolean removeBucket(String bucketName) {
        boolean flag = bucketExists(bucketName);
        if (flag) {
            Iterable<Result<Item>> myObjects = listObjects(bucketName);
            for (Result<Item> result : myObjects) {
                Item item = result.get();
                // If there are object files, the deletion fails
                if (item.size() > 0) {
                    return false; }}// Delete the bucket. Note that the bucket can be deleted only when it is empty.
            minioClient.removeBucket(RemoveBucketArgs.builder().bucket(bucketName).build());
            flag = bucketExists(bucketName);
            if(! flag) {return true; }}return false;
    }

    /** * List all object names in the bucket **@paramBucketName bucketName *@return* /
    @SneakyThrows
    public List<String> listObjectNames(String bucketName) {
        List<String> listObjectNames = new ArrayList<>();
        boolean flag = bucketExists(bucketName);
        if (flag) {
            Iterable<Result<Item>> myObjects = listObjects(bucketName);
            for(Result<Item> result : myObjects) { Item item = result.get(); listObjectNames.add(item.objectName()); }}else{
            listObjectNames.add("Bucket does not exist");
        }
        return listObjectNames;
    }


    /** * Lists all objects in the bucket@paramBucketName bucketName *@return* /
    @SneakyThrows
    public Iterable<Result<Item>> listObjects(String bucketName) {
        boolean flag = bucketExists(bucketName);
        if (flag) {
            return minioClient.listObjects(
                    ListObjectsArgs.builder().bucket(bucketName).build());
        }
        return null;
    }

    /** * Upload file **@param bucketName
     * @param multipartFile
     */
    @SneakyThrows
    public void putObject(String bucketName, MultipartFile multipartFile, String filename, String fileType) {
        InputStream inputStream = new ByteArrayInputStream(multipartFile.getBytes());
        minioClient.putObject(
                PutObjectArgs.builder().bucket(bucketName).object(filename).stream(
                        inputStream, -1, minioProperties.getFileSize())
                        .contentType(fileType)
                        .build());
    }


    /** * File access path **@paramBucketName bucketName *@paramObjectName Name of the object in the bucket *@return* /
    @SneakyThrows
    public String getObjectUrl(String bucketName, String objectName) {
        boolean flag = bucketExists(bucketName);
        String url = "";
        if (flag) {
            url = minioClient.getPresignedObjectUrl(
                    GetPresignedObjectUrlArgs.builder()
                            .method(Method.GET)
                            .bucket(bucketName)
                            .object(objectName)
                            .expiry(2, TimeUnit.MINUTES)
                            .build());
            System.out.println(url);
        }
        return url;
    }


    /** * Delete an object **@paramBucketName bucketName *@paramObjectName Name of the object in the bucket */
    @SneakyThrows
    public boolean removeObject(String bucketName, String objectName) {
        boolean flag = bucketExists(bucketName);
        if (flag) {
            minioClient.removeObject(
                    RemoveObjectArgs.builder().bucket(bucketName).object(objectName).build());
            return true;
        }
        return false;
    }

    /** * Get a file object as a stream **@paramBucketName bucketName *@paramObjectName Name of the object in the bucket *@return* /
    @SneakyThrows
    public InputStream getObject(String bucketName, String objectName) {
        boolean flag = bucketExists(bucketName);
        if (flag) {
            StatObjectResponse statObject = statObject(bucketName, objectName);
            if(statObject ! =null && statObject.size() > 0) {
                InputStream stream =
                        minioClient.getObject(
                                GetObjectArgs.builder()
                                        .bucket(bucketName)
                                        .object(objectName)
                                        .build());
                returnstream; }}return null;
    }

    /** * Get the metadata for the object **@paramBucketName bucketName *@paramObjectName Name of the object in the bucket *@return* /
    @SneakyThrows
    public StatObjectResponse statObject(String bucketName, String objectName) {
        boolean flag = bucketExists(bucketName);
        if (flag) {
            StatObjectResponse stat =
                    minioClient.statObject(
                            StatObjectArgs.builder().bucket(bucketName).object(objectName).build());
            return stat;
        }
        return null;
    }

    /** * If multiple file objects in a specified bucket are deleted, an error object list is returned. If all file objects are successfully deleted, an empty list is returned@paramBucketName bucketName *@paramObjectNames An iterator object * that contains multiple object names to delete@return* /
    @SneakyThrows
    public boolean removeObject(String bucketName, List<String> objectNames) {
        boolean flag = bucketExists(bucketName);
        if (flag) {
            List<DeleteObject> objects = new LinkedList<>();
            for (int i = 0; i < objectNames.size(); i++) {
                objects.add(new DeleteObject(objectNames.get(i)));
            }
            Iterable<Result<DeleteError>> results =
                    minioClient.removeObjects(
                            RemoveObjectsArgs.builder().bucket(bucketName).objects(objects).build());
            for (Result<DeleteError> result : results) {
                DeleteError error = result.get();
                System.out.println(
                        "Error in deleting object " + error.objectName() + "; " + error.message());
                return false; }}return true;
    }

    /** * Get a file object as a stream (breakpoint download) **@paramBucketName bucketName *@paramObjectName Name of the object in the bucket *@paramOffset The position of the starting byte *@paramLength Length to read (optional, if there is no value, the end of the file is read) *@return* /
    @SneakyThrows
    public InputStream getObject(String bucketName, String objectName, long offset, Long length) {
        boolean flag = bucketExists(bucketName);
        if (flag) {
            StatObjectResponse statObject = statObject(bucketName, objectName);
            if(statObject ! =null && statObject.size() > 0) {
                InputStream stream =
                        minioClient.getObject(
                                GetObjectArgs.builder()
                                        .bucket(bucketName)
                                        .object(objectName)
                                        .offset(offset)
                                        .length(length)
                                        .build());
                returnstream; }}return null;
    }


    /** * Upload objects via InputStream **@paramBucketName bucketName *@paramObjectName Name of the object in the bucket *@paramInputStream Stream to be uploaded *@paramContentType Type of the file to be uploaded MimeTypeUtils.IMAGE_JPEG_VALUE *@return* /
    @SneakyThrows
    public boolean putObject(String bucketName, String objectName, InputStream inputStream,String contentType) {
        boolean flag = bucketExists(bucketName);
        if (flag) {
            minioClient.putObject(
                    PutObjectArgs.builder().bucket(bucketName).object(objectName).stream(
                            inputStream, -1, minioProperties.getFileSize())
                            .contentType(contentType)
                            .build());
            StatObjectResponse statObject = statObject(bucketName, objectName);
            if(statObject ! =null && statObject.size() > 0) {
                return true; }}return false; }}Copy the code

3.3. Writing Service layer

MinioService

import io.minio.messages.Bucket;
import org.springframework.web.multipart.MultipartFile;
import java.io.InputStream;
import java.util.List;

/ * * *@Author crush
 * @Date 2021/7/25 9:58
 * @Description: MinioService
 */
public interface MinioService {

    /** * Check whether ** exists in the bucket@param bucketName
     * @return* /
    boolean bucketExists(String bucketName);

    /** * create bucket **@param bucketName
     */
    void makeBucket(String bucketName);

    /** * List all buckets *@return* /
    List<String> listBucketName(a);

    /** * List all buckets **@return* /
    List<Bucket> listBuckets(a);

    /** * Delete bucket * by bucket name@param bucketName
     */
    boolean removeBucket(String bucketName);

    /** * List all object names * in the bucket@param bucketName
     * @return* /
    List<String> listObjectNames(String bucketName);

    /** * Upload file **@param multipartFile
     * @param bucketName
     */
    String putObject( MultipartFile multipartFile, String bucketName,String fileType);

    /** * File stream download *@param bucketName
     * @param objectName
     * @return* /
    InputStream downloadObject(String bucketName, String objectName);


    /** * Delete file *@param bucketName
     * @param objectName
     */
    boolean removeObject(String bucketName, String objectName);



    /** * Delete files * in batches@param bucketName
     * @param objectNameList
     * @return* /
    boolean removeListObject(String bucketName, List<String> objectNameList);

    /** * Obtain the file path *@param bucketName
     * @param objectName
     * @return* /
    String getObjectUrl(String bucketName,String objectName);
}
Copy the code

MinioServiceImpl

import com.crush.minio.config.MinioProperties;
import com.crush.minio.service.MinioService;
import com.crush.minio.utils.MinioUtil;
import io.minio.MinioClient;
import io.minio.messages.Bucket;
import org.apache.commons.lang3.StringUtils;
import org.springframework.stereotype.Service;
import org.springframework.web.multipart.MultipartFile;


import java.io.InputStream;
import java.util.List;
import java.util.UUID;

/ * * *@Author crush
 * @Date 2021/7/25 9:58
 * @Description: MinioServiceImpl
 */
@Service
public class MinioServiceImpl implements MinioService {

    private final MinioUtil minioUtil;
    private final MinioClient minioClient;
    private final MinioProperties minioProperties;

    public MinioServiceImpl(MinioUtil minioUtil, MinioClient minioClient, MinioProperties minioProperties) {
        this.minioUtil = minioUtil;
        this.minioClient = minioClient;
        this.minioProperties = minioProperties;
    }

    @Override
    public boolean bucketExists(String bucketName) {
        return minioUtil.bucketExists(bucketName);
    }


    @Override
    public void makeBucket(String bucketName) {
        minioUtil.makeBucket(bucketName);
    }

    @Override
    public List<String> listBucketName(a) {
        return minioUtil.listBucketNames();
    }

    @Override
    public List<Bucket> listBuckets(a) {
        return minioUtil.listBuckets();
    }

    @Override
    public boolean removeBucket(String bucketName) {
        return minioUtil.removeBucket(bucketName);
    }


    @Override
    public List<String> listObjectNames(String bucketName) {
        return minioUtil.listObjectNames(bucketName);
    }


    @Override
    public String putObject(MultipartFile file, String bucketName,String fileType) {
        try {
            bucketName = StringUtils.isNotBlank(bucketName) ? bucketName : minioProperties.getBucketName();
            if (!this.bucketExists(bucketName)) {
                this.makeBucket(bucketName);
            }
            String fileName = file.getOriginalFilename();

            String objectName = UUID.randomUUID().toString().replaceAll("-"."")
                    + fileName.substring(fileName.lastIndexOf("."));
            minioUtil.putObject(bucketName, file, objectName,fileType);
            return minioProperties.getEndpoint()+"/"+bucketName+"/"+objectName;
        } catch (Exception e) {
            e.printStackTrace();
            return "Upload failed"; }}@Override
    public InputStream downloadObject(String bucketName, String objectName) {
        return minioUtil.getObject(bucketName,objectName);
    }

    @Override
    public boolean removeObject(String bucketName, String objectName) {
        return minioUtil.removeObject(bucketName, objectName);
    }

    @Override
    public boolean removeListObject(String bucketName, List<String> objectNameList) {
        return minioUtil.removeObject(bucketName,objectNameList);
    }

    @Override
    public String getObjectUrl(String bucketName,String objectName) {
        returnminioUtil.getObjectUrl(bucketName, objectName); }}Copy the code

3.4. Write the Controller layer

import com.crush.minio.service.MinioService;
import com.crush.minio.utils.FileTypeUtils;
import org.apache.tomcat.util.http.fileupload.IOUtils;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;

import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.InputStream;
import java.io.UnsupportedEncodingException;
import java.net.URLEncoder;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/ * * *@author crush
 */
@RequestMapping("/minio")
@RestController
public class MinioController {

    private final MinioService minioService;


    public MinioController(MinioService minioService) {
        this.minioService = minioService;
    }

    @PostMapping("/upload")
    public String uploadFile(MultipartFile file, String bucketName) {
        String fileType = FileTypeUtils.getFileType(file);
        if(fileType ! =null) {
            return minioService.putObject(file, bucketName, fileType);
        }
        return "Unsupported file format. Please confirm the format and upload again!!";
    }

    @PostMapping("/addBucket/{bucketName}")
    public String addBucket(@PathVariable String bucketName) {
        minioService.makeBucket(bucketName);
        return "Create success!!";
    }

    @GetMapping("/show/{bucketName}")
    public List<String> show(@PathVariable String bucketName) {
        return minioService.listObjectNames(bucketName);
    }

    @GetMapping("/showBucketName")
    public List<String> showBucketName(a) {
        return minioService.listBucketName();
    }

    @GetMapping("/showListObjectNameAndDownloadUrl/{bucketName}")
    public Map<String, String> showListObjectNameAndDownloadUrl(@PathVariable String bucketName) {
        Map<String, String> map = new HashMap<>();
        List<String> listObjectNames = minioService.listObjectNames(bucketName);
        String url = "localhost:8085/minio/download/" + bucketName + "/";
        listObjectNames.forEach(System.out::println);
        for (int i = 0; i <listObjectNames.size() ; i++) {
            map.put(listObjectNames.get(i),url+listObjectNames.get(i));
        }
        return map;
    }

    @DeleteMapping("/removeBucket/{bucketName}")
    public String delBucketName(@PathVariable String bucketName) {
        return minioService.removeBucket(bucketName) == true ? "Deletion successful" : "Deletion failed";
    }

    @DeleteMapping("/removeObject/{bucketName}/{objectName}")
    public String delObject(@PathVariable("bucketName") String bucketName, @PathVariable("objectName") String objectName) {
        return minioService.removeObject(bucketName, objectName) == true ? "Deletion successful" : "Deletion failed";
    }

    @DeleteMapping("/removeListObject/{bucketName}")
    public String delListObject(@PathVariable("bucketName") String bucketName, @RequestBody List<String> objectNameList) {
        return minioService.removeListObject(bucketName, objectNameList) == true ? "Deletion successful" : "Deletion failed";
    }


    @RequestMapping("/download/{bucketName}/{objectName}")
    public void download(HttpServletResponse response, @PathVariable("bucketName") String bucketName, @PathVariable("objectName") String objectName) {
        InputStream in = null;
        try {
            in = minioService.downloadObject(bucketName, objectName);
            response.setHeader("Content-Disposition"."attachment; filename="
                    + URLEncoder.encode(objectName, "UTF-8"));
            response.setCharacterEncoding("UTF-8");
            // Copy bytes from InputStream to OutputStream.
            IOUtils.copy(in, response.getOutputStream());
        } catch (UnsupportedEncodingException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            if(in ! =null) {
                try {
                    in.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
        }

    }
}
Copy the code

There’s nothing to change with the main start, just run to okla

Don’t panic. I took you to do it. I must have taken you to see the test results.

👇

Four, the actual combat test

I currently contain the bucket of Minio

4.1 File upload

You can also see that it has been uploaded successfully on the visualization platform.

4.2 File download

This is the file download interface.

4.3, other

The others are not tested individually, but the method names should give you a clue.

5. Talk to yourself

If you encounter any errors or doubts, please leave a message or a private message and we will respond promptly.

Java this road ah, is really more and more rolling forward ah. 🛌