什么是分布式文件系统
分布式文件系统(Distributed File System,DFS)是指文件系统管理的物理存储资源不一定直接连接在本地节点上,而是通过计算机网络与节点(可简单的理解为一台计算机)相连;或是若干不同的逻辑磁盘分区或卷标组合在一起而形成的完整的有层次的文件系统。DFS为分布在网络上任意位置的资源提供一个逻辑上的树形文件系统结构,从而使用户访问分布在网络上的共享文件更加简便。单独的DFS共享文件夹的作用是相对于通过网络上的其他共享文件夹的访问点.
通过概念可以简单理解为:一个计算机无法存储海量的文件,通过网络将若干计算机组织起来共同去存储海量的文件,去接收海量用户的请求,这些组织起来的计算机通过网络进行通信
好处:
- 一台计算机的文件系统处理能力扩充到多台计算机同时处理。
- 一台计算机挂了还有另外副本计算机提供数据。
- 每台计算机可以放在不同的地域,这样用户就可以就近访问,提高访问速度。
Minio
介绍
本项目采用MinlO构建分布式文件系统,MinlO是一个非常轻量的服务,可以很简单的和其他应用的结合使用,它兼容亚马逊S3云存储服务接口,非常适合于存储大容量非结构化的数据,例如图片、视频、日志文件、备份数据和容器/虚拟机镜像等。
它一大特点就是轻量,使用简单,功能强大,支持各种平台,单个文件最大5TB,兼容Amazon S3接口,提供了Java、Python、GO等多版本SDK支持。
官网: https:l/min.io
中文: https://www.minio.org.cnl ,http://docs.minio.org.cn/docs/
MinlO集群采用去中心化(任何一个都可以当主节点)共享架构,每个结点是对等关系,通过Nginx可对MinlO进行负载均衡访问。
去中心化有什么好处?
在大数据领域,通常的设计理念都是无中心和分布式。Minio分布式模式可以帮助你搭建一个高可用的对象存储服务,你可以使用这些存储设备,而不用考虑其真实物理位置。
它将分布在不同服务器上的多块硬盘组成一个对象存储服务。由于硬盘分布在不同的节点上,分布式Minio避免了单点故障。
Minio使用纠删码技术来保护数据,它是一种恢复丢失和损坏数据的数学算法,它将数据分块冗余的分散存储在各各节点的磁盘上,所有的可用磁盘组成一个集合,上图由8块硬盘组成一个集合,当上传一个文件时会通过纠删码算法计算对文件进行分块存储,除了将文件本身分成4个数据块,还会生成4个校验块,数据块和校验块会分散的存储在这8块硬盘上。
使用纠删码的好处是即便丢失一半数量(N/2)的硬盘,仍然可以恢复数据。比如上边集合中有4个以内的硬盘损害仍可保证数据恢复,不影响上传和下载,如果多于一半的硬盘坏了则无法恢复。
数据恢复演示 (windows)
下边在本机演示MinlO恢复数据的过程。在本地创建4个目录表示4个硬盘(代表四台虚拟机)。
下载minio,下载地址在https://dl.min.io/server/minio/release/,CMD进入有minio.exe的目录,运行下边的命令:
minio.exe server D:\MinioData\data1 D:\MinioData\data2 D:\MinioData\data3 D:\MinioData\data4
进入创建一个桶
测试Docker环境
开发阶段和生产阶段统一使用Docker下的MINIO。
在下发的虚拟机中已安装了MinlO的镜像和容器,执行sh /datalsoft /restart.sh启动Docker下的MinlO启动完成登录MinIO查看是否正常。
访问http://192.168.101.65:9000
docker上安装步骤
-
docker pull minio/minio(拉取下载最新版Minio镜像 )
docker pull minio/minio:RELEASE.2022-06-20T23-13-45Z.fips(下载指定版本的Minio镜像 (xxx指具体版本号))
-
创建目录
一个用来存放配置,一个用来存储上传文件的目录启动前需要先创建Minio外部挂载的配置文件( /home/minio/config),和存储上传文件的目录( /home/minio/data)
mkdir -p /home/minio/config
mkdir -p /home/minio/data
-
创建Minio容器并运行
多行模式docker run -p 9000:9000 -p 9090:9090 \ --net=host \ --name minio \ -d --restart=always \ -e "MINIO_ACCESS_KEY=minioadmin" \ -e "MINIO_SECRET_KEY=minioadmin" \ -v /home/minio/data:/data \ -v /home/minio/config:/root/.minio \ minio/minio server \ /data --console-address ":9090" -address ":9000"
9090端口指的是minio的客户端端口
MINIO_ACCESS_KEY :账号
MINIO_SECRET_KEY :密码(账号长度必须大于等于5,密码长度必须大于等于8位)
- 访问:http://虚拟机ip:9090/login 用户名:密码 minioadmin:minioadmin
文件内容如下,保存文件,SDK操作文件的API需要用到
{"url":"http://192.168.93.129:9090/api/v1/service-account-credentials","accessKey":"EQSaIXkhWSmAeNk36ieI","secretKey":"PGXu2WDM3GjmrPvezEm7nGIIwCoD6eAaxPa5PyXn","api":"s3v4","path":"auto"}
SDK操作
- minio涉及依赖
<dependency>
<groupId>io.minio</groupId>
<artifactId>minio</artifactId>
<version>8.4.3</version>
</dependency>
<dependency>
<groupId>com.squareup.okhttp3</groupId>
<artifactId>okhttp</artifactId>
<version>4.8.1</version>
</dependency>
- 工具类的依赖
<!--使用起DigestUtils.md5Hex将字节流转为md5-->
<dependency>
<groupId>commons-codec</groupId>
<artifactId>commons-codec</artifactId>
</dependency>
<!--根据扩展名取得mimetype-->
<dependency>
<groupId>com.j256.simplemagic</groupId>
<artifactId>simplemagic</artifactId>
<version>1.17</version>
</dependency>
代码测试(上传文件)
public class FileUploader {
public static void main(String[] args) throws IOException, NoSuchAlgorithmException, InvalidKeyException {
try {
// Create a minioClient with the MinIO server playground, its access key and secret key.
MinioClient minioClient =
MinioClient.builder()
//虚拟机地址
.endpoint("http://192.168.93.129:9000")
//可以使用 用户名minioadmin 密码minioadmin
.credentials("EQSaIXkhWSmAeNk36ieI", "PGXu2WDM3GjmrPvezEm7nGIIwCoD6eAaxPa5PyXn")
.build();
// Make 'public' bucket if not exist.
//判断桶是否存在,若是不存在就创建
boolean found = minioClient.bucketExists(BucketExistsArgs.builder().bucket("public").build());
if (!found) {
// Make a new bucket called 'public'.
minioClient.makeBucket(MakeBucketArgs.builder().bucket("public").build());
} else {
System.out.println("Bucket 'public' already exists.");
}
// Upload '/home/user/Photos/public.zip' as object name 'public-2015.zip' to bucket
// 'public'.
//上传文件
minioClient.uploadObject(
UploadObjectArgs.builder()
.bucket("public")
.object("credentials.json")
//文件地址
.filename("E:/softwerzonghe/credentials.json")
.build());
System.out.println("'E:/softwerzonghe/credentials.json' is successfully uploaded as " + "object 'credentials.json' to bucket 'public'.");
} catch (MinioException e) {
System.out.println("Error occurred: " + e);
System.out.println("HTTP trace: " + e.httpTrace());
}
}
}
代码测试(上传文件II)
MinioClient minioClient =
MinioClient.builder()
//虚拟机地址
.endpoint("http://192.168.93.129:9000")
//可以使用 用户名minioadmin 密码minioadmin
.credentials("EQSaIXkhWSmAeNk36ieI", "PGXu2WDM3GjmrPvezEm7nGIIwCoD6eAaxPa5PyXn")
.build();
@Test
public void test_upload() throws Exception {
//通过扩展名得到媒体资源类型 mimeType
//根据扩展名取出mimeType
ContentInfo extensionMatch = ContentInfoUtil.findExtensionMatch(".json");
String mimeType = MediaType.APPLICATION_OCTET_STREAM_VALUE;//通用mimeType,字节流
if(extensionMatch!=null){
mimeType = extensionMatch.getMimeType();
}
//上传文件的参数信息
UploadObjectArgs uploadObjectArgs =
UploadObjectArgs.builder()
.bucket("public")//桶名
.filename("E:/softwerzonghe/credentials.json")//本地文件地址
// .object("credentials.json")//对象名在桶下存储该文件
.object("test/01/credentials.json")//对象名放在桶的子目录下
.contentType(mimeType)//设置媒体文件类型(尽量配置上)
.build();
minioClient.uploadObject(uploadObjectArgs);
}
代码测试(删除文件)
//删除文件
@Test
public void test_delete() throws Exception {
//RemoveObjectArgs
RemoveObjectArgs removeObjectArgs =
RemoveObjectArgs.builder()
.bucket("public")
.object("credentials.json")
.build();
//删除文件
minioClient.removeObject(removeObjectArgs);
}
代码测试(下载文件)
//查询文件 从minio中下载
@Test
public void test_getFile() throws Exception {
GetObjectArgs getObjectArgs = GetObjectArgs.builder().bucket("public").object("test/01/credentials.json").build();
//查询远程服务获取到一个流对象 网络流拿到的数据可能不完整
FilterInputStream inputStream = minioClient.getObject(getObjectArgs);
//指定输出流
FileOutputStream outputStream = new FileOutputStream(new File("E:/softwerzonghe/credentials123.json"));
IOUtils.copy(inputStream, outputStream);
}
校验文件的完整性
对文件计算出md5值,比较原始文件的md5和目标文件的md5值,一致则说明完整
//校验文件的完整性对文件的内容进行md5
FileInputStream fileInputStream1 = new FileInputStream(new File("E:/softwerzonghe/credentials.json"));
String source_md5 = DigestUtils.md5Hex(fileInputStream1);
FileInputStream fileInputStream = new FileInputStream(new File("E:/softwerzonghe/credentials123.json"));
String local_md5 = DigestUtils.md5Hex(fileInputStream);
if (source_md5.equals(local_md5)) {
System.out.println("下载成功");
}
标签:文件,Minio,---,json,credentials,分布式文件系统,public,minio
From: https://www.cnblogs.com/uuuuZhang/p/18006170