【新手必看】SpringBoot集成Minio实现文件上传、下载和删除

一,前言

       安装教程可看我以前的文章,Linux和Windows安装教程都有。安装好minio后今天学习minio的使用。

二,集成Minio

1,导入依赖,版本可自己选择

<!-- https://mvnrepository.com/artifact/io.minio/minio -->
<dependency><groupId>io.minio</groupId><artifactId>minio</artifactId><version>8.5.7</version>
</dependency>

2,application.yml中配置minio信息

minio:endpoint: http://localhost:9000 # minio地址access-key: admin # 账号secret-key: admin123 # 密码bucket-name: my-bucket # 存储桶名称

如果不想用账号密码也可以使用生成的秘钥

3,编写 MinioConfig.class 配置类

@Data
@Configuration
@ConfigurationProperties(prefix = "minio")
public class MinioConfig {/*** 扫描配置文件,获取minio的相关配置信息*/private String endpoint;private String accessKey;private String secretKey;private String bucketName;/*** 构建 minioClient 客户端*/@Beanpublic MinioClient minioClient() {return MinioClient.builder().endpoint(endpoint).credentials(accessKey, secretKey).build();}
}

4,编写 MinioUtils.class 工具类

@Component
@Slf4j
public class MinioUtils {/*** 构造器注入 minioClient、minioConfig*/private final MinioClient minioClient;private final MinioConfig minioConfig;public MinioUtils(MinioClient minioClient,MinioConfig minioConfig) {this.minioClient = minioClient;this.minioConfig = minioConfig;}/*** 上传文件到minio** @param file 文件* @return 文件存储的路径*/public String uploadFile(MultipartFile file) {String originalFilename = file.getOriginalFilename();if (StringUtils.isBlank(originalFilename)) {throw new RuntimeException();}// 重新命名文件,文件名为 uuid 生成String fileName = UuidUtils.getUuid() + originalFilename.substring(originalFilename.lastIndexOf("."));// 设置存储目录,设置 年-月和日两级目录String objectName = DateUtils.format(new Date(), "yyyy-MM/dd") + "/" + fileName;try {PutObjectArgs objectArgs = PutObjectArgs.builder().bucket(minioConfig.getBucketName()).object(objectName).stream(file.getInputStream(), file.getSize(), -1).contentType(file.getContentType()).build();// 文件名称相同会覆盖minioClient.putObject(objectArgs);} catch (Exception e) {// 异常处理return null;}// 拼接minio的端点和存储桶的名称return getPrefix() + objectName;}/*** 根据文件名称删除文件** @param file 文件路径*/public void deleteFile(String file) {// 获取文件的名称String fileName = removeMinioEndpoint(file);try {minioClient.removeObject(RemoveObjectArgs.builder().bucket(minioConfig.getBucketName()).object(fileName).build());} catch (Exception e) {// 异常处理e.printStackTrace();}}/*** 下载文件** @param file 文件路径*/public void downloadFile(String file, HttpServletResponse response) {// 获取文件的名称String fileName = removeMinioEndpoint(file);try {InputStream fileIo = minioClient.getObject(GetObjectArgs.builder().bucket(minioConfig.getBucketName()).object(fileName).build());// 设置响应类型response.setContentType("application/octet-stream");// 设置附件名称response.setHeader("Content-Disposition", "attachment; filename=\"" + fileName + "\"");IOUtils.copy(fileIo, response.getOutputStream());response.flushBuffer();} catch (Exception e) {// 异常处理e.printStackTrace();}}/*** 移除文件路径的前缀,获取文件的名称** @param file 文件路径*/public String removeMinioEndpoint(String file) {return file.substring(getPrefix().length()-1);}/*** 获取文件前缀*/public String getPrefix() {return minioConfig.getEndpoint() + "/" + minioConfig.getBucketName() + "/";}}

5,编写测试接口

import static com.cms.pojo.CommonResult.success;@RestController
@RequestMapping("/system/file")
public class FileController {@ResourceMinioUtils minioUtil;/*** 上传文件* @param file 文件*/@PostMapping("/upload")public CommonResult<String> uploadFile(@RequestParam("file") MultipartFile file) {String objectName = minioUtil.uploadFile(file);return success(objectName);}/*** 删除文件* @param file 文件*/@DeleteMapping("/delete")public CommonResult<String> deleteFile(String file) {minioUtil.deleteFile(file);return success("success");}/*** 下载文件* @param file 文件*/@GetMapping("/download")public void downloadFile(String file, HttpServletResponse response) {minioUtil.downloadFile(file,response);}
}

6,上传文件

直接访问地址可查看图片

注意存储权限要改为public

7,下载文件,参数为上传文件返回的地址

8,删除文件

文件已删除

大功告成!!!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.xdnf.cn/news/144351.html

如若内容造成侵权/违法违规/事实不符,请联系一条长河网进行投诉反馈,一经查实,立即删除!

相关文章

LeetCode力扣——并查集:947. 移除最多的同行或同列石头,1971. 寻找图中是否存在路径,2424. 最长上传前缀

947. 移除最多的同行或同列石头 题目描述 947. 移除最多的同行或同列石头 n 块石头放置在二维平面中的一些整数坐标点上。每个坐标点上最多只能有一块石头。 如果一块石头的 同行或者同列 上有其他石头存在&#xff0c;那么就可以移除这块石头。 给你一个长度为 n 的数组 …

[Golang] Select

[Golang] Select 文章目录 [Golang] Select什么是selectselect用法基本用法空select没有default且case永久无法执行单个case和default多个case和default IO多路复用 什么是select select是Golang中一个控制结构&#xff0c;可以用来处理多个channel的发送和接收操作。select会…

Echats 实现CPK (过程能力)研究报告

背景: 实现: Echarts Option 代码示例 option {title: {text: 折线图示例 - X轴为数值},xAxis: {type: value, // X 轴改为数值型min: 0, // 最小值max: 10, // 最大值},yAxis: {type: value},series: [{type: line,data: [[0, 150], [2, 230], [4, 224], [6…

Photoshop 2021安装教程

软件介绍 Adobe Photoshop&#xff0c;简称“PS”&#xff0c;是美国Adobe公司旗下最为出名的图像处理软件系列之一。ps 2021新增一键换天空&#xff0c;AI只能滤镜&#xff0c;新增内置的画笔工具极为丰富&#xff0c;成千上万的精致像素、动态和矢量画笔可以满足你的各种绘图…

论文阅读--Planning-oriented Autonomous Driving(二)

自动驾驶框架的各种设计比较。 ( a )大多数工业解决方案针对不同的任务部署不同的模型。 ( b )多任务学习方案共享一个具有分割任务头的主干。 ( c )端到端范式将感知和预测模块统一起来。以往的尝试要么采用( c.1 )中对规划的直接优化&#xff0c;要么采用( c.2 )中的部分元…

【结构型】树形结构的应用王者,组合模式

目录 一、组合模式1、组合模式是什么&#xff1f;2、组合模式的主要参与者&#xff1a; 二、优化案例&#xff1a;文件系统1、不使用组合模式2、通过组合模式优化上面代码优化点&#xff1a; 三、使用组合模式有哪些优势1、统一接口&#xff0c;简化客户端代码2、递归结构处理方…

选址模型 | 基于混沌模拟退火粒子群优化算法的电动汽车充电站选址与定容(Matlab)

目录 效果一览基本介绍程序设计参考资料 效果一览 基本介绍 基于混沌模拟退火粒子群优化算法的电动汽车充电站选址与定容&#xff08;Matlab&#xff09; 问题建模&#xff1a;首先&#xff0c;需要将电动汽车充电站选址与定容问题进行数学建模&#xff0c;确定目标函数和约束…

Redis面试真题总结(一)

文章收录在网站&#xff1a;http://hardyfish.top/ 文章收录在网站&#xff1a;http://hardyfish.top/ 文章收录在网站&#xff1a;http://hardyfish.top/ 文章收录在网站&#xff1a;http://hardyfish.top/ 什么是Redis? Redis是一个高性能的开源内存数据库系统&#xff0…

Java从入门到精通学习框架(三)

这一阶段的学习目标是将 Java 的知识从基础提升到实战开发的应用层面&#xff0c;通过对常见的 Java 企业级开发框架的学习和实践&#xff0c;掌握设计模式、分布式系统开发、性能优化等核心技能。在此基础上&#xff0c;学习并应用 Java 的高级特性和最佳实践&#xff0c;使自…

C#和数据库高级:抽象类和抽象方法

文章目录 一、为什么使用抽象类和抽象方法&#xff1f;1.1、父类与子类的相互转换 二、抽象类和抽象方法2.1、抽象类的定义和方法声明规范2.2、使用继承多态的机制解决问题 三、抽象类的概念和使用特点总结 一、为什么使用抽象类和抽象方法&#xff1f; 1.1、父类与子类的相互…

代码随想录_刷题笔记_第二次

链表 — 环形链表 题目链接&#xff1a;142. 环形链表 II - 力扣&#xff08;LeetCode&#xff09; 题目要求&#xff1a; 给定一个链表的头节点 head &#xff0c;返回链表开始入环的第一个节点。 如果链表无环&#xff0c;则返回 null。 如果链表中有某个节点&#xff0c…

计算机专业的就业方向

计算机专业的就业方向 亲爱的新生们&#xff0c;欢迎你们踏上计算机科学的旅程&#xff01;作为一名计算机专业的学生&#xff0c;你们即将进入一个充满无限可能的领域。今天&#xff0c;我将为大家介绍计算机专业的一些主要就业方向&#xff0c;帮助你们了解未来的职业选择。…

(黑马点评)二、短信登录功能实现

2.1 基于传统Session实现的短信登录及其校验 2.1.1 基于Session登录校验的流程设计 2.1.2 实现短信验证码发送功能 请求接口/user/code请求类型post请求参数phone返回值无 /*** 发送手机验证码*/PostMapping("/code")public Result sendCode(RequestParam("ph…

Ubunutu 的 Bash 没有颜色

终端没有颜色&#xff1a; 取消注释 force_color_promptyes &#xff1a; 这时候就有颜色了&#xff1a;

three.js shader 实现天空中白云

three.js shader 实现天空中白云 预览&#xff1a; https://threehub.cn/#/codeMirror?navigationThreeJS&classifyshader&idwhiteCloud 更多案例 可见 预览&#xff1a; https://threehub.cn import * as THREE from "three"; import { OrbitControls …

按摩上门预约小程序源码系统 在线评价+即时服务 带完整的安装代码包以及搭建部署教程

系统概述 按摩上门预约小程序源码系统是一款专为按摩行业量身定制的移动端应用解决方案。它利用先进的互联网技术&#xff0c;将传统按摩服务与线上平台相结合&#xff0c;实现了用户与服务商之间的无缝对接。该系统不仅简化了预约流程&#xff0c;提高了服务效率&#xff0c;…

【Python】探索 PluginBase:Python 插件系统的灵活构建

我承认这道菜有赌的成分&#xff0c;果然还是赌输了。 在现代软件开发中&#xff0c;插件系统为应用程序提供了极大的灵活性和扩展性。Python&#xff0c;作为一种流行的编程语言&#xff0c;拥有丰富的库和框架来支持插件的开发。今天&#xff0c;我们将深入探讨一个名为Plug…

23.面试题02.07链表相交

public class Solution {public ListNode getIntersectionNode(ListNode headA, ListNode headB) {ListNode apheadA;ListNode bpheadB;int lenA0,lenB0;//求两个链表长度while(ap!null){apap.next;lenA;}while(bp!null){bpbp.next;lenB;}apheadA;bpheadB;int len0;//用来计算让…

BAS模型论文阅读

论文全名&#xff1a;Background Activation Suppression for Weakly Supervised Object Localization and Semantic Segmentation 论文pdf下载地址&#xff1a;2309.12943 (arxiv.org) 论文会议版全名&#xff1a;Background Activation Suppression for Weakly Supervised O…

AI产品经理面试20个问题汇总(含面试解题技巧、注意事项)

这题我会&#xff01;这是一个包含AI产品经理问题的备考文章&#xff0c;本文主要讲解AI产品经理的备考注意事项、真题展示、解题技巧及高效刷题方法&#xff0c;相信大家看完就一定能掌握技巧并且顺利通关&#xff01; 一、AI产品经理面试问题展示(20道) 1. 请描述一下你过…