写点什么

【分布式技术专题】「OSS 中间件系列」Minio 的文件服务的存储模型及整合 SpringBoot 客户端访问的实战指南

作者:洛神灬殇
  • 2023-05-06
    江苏
  • 本文字数:3669 字

    阅读完需:约 12 分钟

【分布式技术专题】「OSS中间件系列」Minio的文件服务的存储模型及整合SpringBoot客户端访问的实战指南

Maven 依赖的配置

首先增加对应的配置依赖,添加 MINIO 的客户端依赖,目前比较稳定的。客户端组件是 com.jvm123 的客户端 starter, 我们会基于他进行二次封装,形成可插拔化且集成化更高的的 OSS 客户端。


具体配置可见如下依赖:


<dependency>   <groupId>com.jvm123</groupId>   <artifactId>minio-spring-boot-starter</artifactId>   <version>1.2.1</version></dependency>
复制代码


在这里,我们选择的版本是 1.2.1 的这个版本,具体也有更高的版本,但是我们本次的一个演示主要以此版本为主。

定义 OSS 数据模型

接下来呢,我们需要定一下我 OSS 的传输、操作等相关的数据模型。


我们定义其名称为:OssProcessDTO 类。


@Data@SuppressWarnings("serial")public class OssProcessDTO implements Serializable {    private String filePath;    private String bucketName;    private String fileName;}
复制代码


从上面我们可以看到我们主要的属性,只有三个部分:


  • filePath: 数据文件的目录其他都有了访问地址, 主要用于传输本地的文件的目录信息以及存储在 OS X 部分的目录信息,作为他的主要作用。

  • bucketName: 主要作为协议的 Bucket 名称,大家可以理解为命名空间进行隔离的边界。

  • fileName: 主要作为存储文件的名称,方便后续进行名称的一个替换,以及原始名称的存储。

定义模型类

定一下模型类,如下所示:


@Data@SuppressWarnings("serial")public class OssProcessDTO implements Serializable {    private String filePath;    private String bucketName;    private String fileName;}
复制代码

定义数据传输模型

定义一个 RPC 请求数据模型


@NoArgsConstructor@Data@Accessors(chain = true)public class RpcRequest<T> implements Serializable {
private String id;
private T enity;
public RpcRequest(T enity) { this.enity = enity; }
public RpcRequest(String id, T enity) { this.id = id; this.enity = enity; }
public RpcRequest(String id) { this.id = id; }}
复制代码

核心功能接口定义

接下来呢我们要定义对应的依赖关系和定义我们的逻辑接口,命名为:RpcOssOperateRpcApi。


public interface RpcOssOperateRpcApi {
/** * bucket * @param rpcRequest:内部存储对应的BucketName * @return */ RpcResponse create(RpcRequest<String> rpcRequest); /** * 存储文件 * @param rpcRequest filePath和bucketName * @return */ RpcResponse upload(RpcRequest<OssProcessDTO> rpcRequest); /** * 删除文件 * @param rpcRequest bucketName 和 fileName * @return */ RpcResponse remove(RpcRequest<OssProcessDTO> rpcRequest);
/** * 下载文件 * @param rpcRequest bucketName 和 fileName * @return */ RpcResponse download(RpcRequest<OssProcessDTO> rpcRequest);
}
复制代码


实际上还有很多,我们暂时定一个基础的接口就可以了。

内部创建对应的 BucketName 的 Bucket 对象

rpcRequest:内部存储对应的 BucketName


RpcResponse create(RpcRequest<String> rpcRequest);
复制代码

上传且存储文件

    /**     * 存储文件     * @param rpcRequest filePath和bucketName     * @return     */    RpcResponse upload(RpcRequest<OssProcessDTO> rpcRequest);
复制代码

删除 OSS 文件

  /**     * 删除文件     * @param rpcRequest bucketName 和 fileName     * @return     */    RpcResponse remove(RpcRequest<OssProcessDTO> rpcRequest);
复制代码

下载 OSS 文件


/** * 下载文件 * @param rpcRequest bucketName 和 fileName * @return */ RpcResponse download(RpcRequest<OssProcessDTO> rpcRequest);
复制代码

实现对应 OSS 功能

接下来我们要去实现上面定义的 RpcOssOperateRpcApi 接口。


我们建立一个新的实现类:MinioRpcOssService,并且进行实现对应的接口 RpcOssOperateRpcApi。


对此我们需要依赖注入一个 MINIO 核心 SDK 的业务操作类:MinioFileService


@AutowiredMinioFileService fileStoreService;
复制代码

实现 create 方法

主要调用了他创建 bucket 的实现类方法。如下面代码所示。



/** * 创建的操作处理控制 * @param rpcRequest:内部存储对应的BucketName * @return */ @Override public RpcResponse create(RpcRequest<String> rpcRequest) { return fileStoreService.createBucket(rpcRequest.getEnity())? RpcResponse.success(): RpcResponse.failure("创建oss bucket失败!"); }
复制代码

实现 upload 方法

主要调用它保存文件的 save 方法,在这里我们主要是将上传过来的文件进行转换为数据流。并且指定对应的 bucket 的名字以及原始的文件名。


    /**     * 上传服务文件处理     * @param rpcRequest filePath和bucketName     * @return     */    @Override    public RpcResponse upload(RpcRequest<OssProcessDTO> rpcRequest) {        try(        InputStream inputStream =                            IoUtil.toStream(new File(rpcRequest.getEnity().getFilePath()));) {            fileStoreService.save(rpcRequest.getEnity().getBucketName(), inputStream, rpcRequest.getEnity().getFileName());        }catch (Exception e) {            log.error("upload the file is error",e);            return RpcResponse.failure("upload the file is error");        }        return RpcResponse.success();    }
复制代码

实现 remove 方法

主要是用于删除 OSS 服务器上的对应的文件。主要用于删除对应的 bucket 的下面对应的文件。那么我们要指定他的原始文件名称。


 /**     * 删除文件地下     * @param rpcRequest bucketName 和 fileName     * @return     */    @Override    public RpcResponse remove(RpcRequest<OssProcessDTO> rpcRequest) {        return fileStoreService.delete(rpcRequest.getEnity().getBucketName(),                rpcRequest.getEnity().getFileName())?                RpcResponse.success(): RpcResponse.failure("删除oss bucket文件失败!");    }
复制代码

实现 download 方法

下载文件处理控制,主要用于传输我们的 bucket 的名称以及文件的把我们的文件的名称,就可以完成下载对应的文件数据。


 /**     * 下载文件处理控制     * @param rpcRequest     * @return     */    @Override    public RpcResponse download(RpcRequest<OssProcessDTO> rpcRequest) {        try(                OutputStream outputStream =                         new FileOutputStream(rpcRequest.getEnity().getFilePath());        ) {            fileStoreService.writeTo(rpcRequest.getEnity().getBucketName(), rpcRequest.getEnity().getFileName(), outputStream);        } catch (IOException e) {            log.error("download file is failure!",e);            return RpcResponse.failure("下载oss bucket文件失败!");        }        return RpcResponse.success(rpcRequest.getEnity().getFilePath());    }`
复制代码

封装为 SpringBoot 的 starter

建立 Configuration 主要扫描我们的组件

我们建立一个 configuration 类。主要用于扫描我们的所对应的 MINIO 的客户端组件,主要就可以去扫描我们刚才定义的这个实现类。当然你也可以使用 @Bean 的方式进行注入:


@ComponentScan("com.hyts.assemble.minio")@Configurationpublic class MinoConfiguration {}
复制代码

定义我们的注解类

主要用于定义和引入 Spring 的配置信息类作为注解的方式进行启动,例如,我们下面的 EnableMinioClient。


@Documented@Retention(RetentionPolicy.RUNTIME)@Target({ElementType.TYPE,ElementType.FIELD})@SpringBootConfiguration@Import(MinoConfiguration.class)public @interface EnableMinioClient {}
复制代码

使用启动我们的 MINIO 客户端

@Slf4j@SpringBootApplication@EnableMinioClientpublic class OssClientApplication {    public static void main(String[] args) {        try {            ApplicationContext applicationContext = SpringApplication.run(OssClientApplication.class,args);            log.info("请访问MINIO控制台:{}",applicationContext.getBean(MinioProperties.class).getEndpoint());            ServerProperties serverProperties = applicationContext.getBean(ServerProperties.class);            log.info("请访问swagger访问页面:{}", "http://"+NetUtil.localIpv4s().stream().findFirst().get()+":"+                    serverProperties.getPort()+"/doc.html");        } catch (Exception e) {            log.error("启动我失败!",e);        }    }
复制代码


至此,所有的代码实现全部完成!

发布于: 刚刚阅读数: 4
用户头像

洛神灬殇

关注

🏆 InfoQ写作平台-签约作者 🏆 2020-03-25 加入

【个人简介】酷爱计算机科学、醉心编程技术、喜爱健身运动、热衷悬疑推理的“极客达人” 【技术格言】任何足够先进的技术都与魔法无异 【技术范畴】Java领域、Spring生态、MySQL专项、微服务/分布式体系和算法设计等

评论

发布
暂无评论
【分布式技术专题】「OSS中间件系列」Minio的文件服务的存储模型及整合SpringBoot客户端访问的实战指南_分布式_洛神灬殇_InfoQ写作社区