2018年3月29日 11:02:33 关于docker分享之分布式存储 glusterfs
经典语录:
实际实验搭建:
前提 是要保证 一个 /data目录不和根分区在同一个磁盘!
1、centos7安装glusterfs
参考链接:https://wiki.centos.org/SpecialInterestGroup/Storage/gluster-Quickstart
#To Use the RPMs from Storage SIG, you need to install the centos-release-gluster RPM as it will provide the required YUM repository files. This RPM is available from CentOS Extras.
yum install centos-release-gluster -y
yum --enablerepo=centos-gluster*-test install glusterfs-server -y
systemctl enable glusterd
systemctl start glusterd
systemctl status glusterd
2、组建集群(配置信任存储池):
#从glusterfs官网跳转过来的
[[email protected] ~]# ping docker2 #确保hostname可以通讯
PING dubbo2 (192.168.0.78) 56(84) bytes of data.
64 bytes from dubbo2 (192.168.0.78): icmp_seq=1 ttl=64 time=0.200 ms
64 bytes from dubbo2 (192.168.0.78): icmp_seq=2 ttl=64 time=0.167 ms
64 bytes from dubbo2 (192.168.0.78): icmp_seq=3 ttl=64 time=0.191 ms
^C
--- dubbo2 ping statistics ---
3 packets transmitted, 3 received, 0% packet loss, time 2000ms
rtt min/avg/max/mdev = 0.167/0.186/0.200/0.013 ms
[[email protected] ~]# gluster peer probe docker2
peer probe: success. #建立集群成功!
#验证检查 docker2和docker1建立集群成功!
[[email protected] ~]# gluster peer status
Number of Peers: 1
Hostname: docker2
Uuid: e675b971-b503-4342-82ff-182858656282
State: Peer in Cluster (Connected)
[[email protected] ~]# gluster peer status
Number of Peers: 1
Hostname: docker1
Uuid: 283ff245-7adf-4359-98c7-873cfcaa4a13
State: Peer in Cluster (Connected)
3、建立 GlusterFS volume
On both docker1 and docker2:
[[email protected] ~]# mkdir -p /data/brick1/gv0
[[email protected] ~]# mkdir -p /data/brick1/gv0
From any single server:
[[email protected] ~]# gluster volume create gv0 replica 2 docker1:/data/brick1/gv0
Replica 2 volumes are prone to split-brain. Use Arbiter or Replica 3 to avoid this. See: http://docs.gluster.org/en/latest/Administrator%20Guide/Split%20brain%20and%20ways%20to%20deal%20with%20it/.
Do you still want to continue? #上述提示是2台集群有脑裂的风险,建议3台建群,有自动选举决策能力
(y/n) y
volume create: gv0: success: please start the volume to access data
[[email protected] ~]# gluster volume start gv0
volume start: gv0: success
#查看一下
[[email protected] ~]# gluster volume info
Volume Name: gv0
Type: Replicate
Volume ID: 47a40786-eb5e-4845-b324-6feb4557d428
Status: Started
Snapshot Count: 0
Number of Bricks: 1 x 2 = 2
Transport-type: tcp
Bricks:
Brick1: docker1:/data/brick1/gv0
Brick2: docker2:/data/brick1/gv0
Options Reconfigured:
transport.address-family: inet
nfs.disable: on
performance.client-io-threads: off
4、客户端使用
yum install centos-release-gluster -y
yum -y install glusterfs-fuse #glusterfs-client和glusterfs-fuse等价,其实都是安装的glusterfs-fuse!
#如果客户端不安装gluster-fuse,其实还可以以nfs协议传输,也就是把glusterfs当作nfs来用!(这里埋个伏笔,马上后面有讲到)
原理等:
拓展研究的网址:
http://gluster.readthedocs.io/en/latest/Quick-Start-Guide/Architecture/ #英文讲解,最正宗!(其实网页翻译后一样 0.0)
https://www.ibm.com/developerworks/cn/opensource/os-cn-glusterfs-docker-volume/index.html #中文版可能好看些
前面是基础部分了,相信群里大家都会安装的了,很简单的分布式存储,其实比起nfs来说可能还要更加的简单!
为了填充下篇幅,特盗取上述网址的图片来讲讲glusterfs的原理和我的理解(其实还参考了老男孩架构班glusterfs的讲解):
企业级的容器应用常常需要将重要的数据持久化,方便在不同容器间共享。为了能够持久化数据以及共享容器间的数据,Docker 提出了 Volume 的概念。单机环境的数据卷难以满足 Docker 集群化的要求,因此需要引入分布式文件系统。目前开源的分布式文件系统有许多,例如 GFS,Ceph,HDFS,FastDFS,GlusterFS 等。GlusterFS 因其部署简单、扩展性强、高可用等特点,在分布式存储领域被广泛使用。本文主要介绍了如何利用 GlusterFS 为 Docker 集群提供可靠的分布式文件存储。
GlusterFS 概述
GlusterFS (Gluster File System) 是一个开源的分布式文件系统。
GlusterFS 总体架构与组成部分如图1所示,它主要由存储服务器(Brick Server)、客户端以及 NFS/Samba 存储网关组成。
不难发现,GlusterFS 架构中没有元数据服务器组件(这个是对比fastdfs来说的,其实我对那个也了解不深,姑且认为会一个就得了把,其实可以理解这段是废话,你就认为它性能好就行了!),这是其最大的设计这点,对于提升整个系统的性能、可靠性和稳定性都有着决定性的意义。
- GlusterFS 支持 TCP/IP 和 InfiniBand RDMA 高速网络互联。
- 客户端可通过原生 GlusterFS 协议访问数据,其他没有运行 GlusterFS 客户端的终端可通过 NFS/CIFS 标准协议通过存储网关访问数据(存储网关提供弹性卷管理和访问代理功能)。
- 存储服务器主要提供基本的数据存储功能,客户端弥补了没有元数据服务器的问题,承担了更多的功能,包括数据卷管理、I/O 调度、文件定位、数据缓存等功能,利用 FUSE(File system in User Space)模块(所以客户端使用需要安装glusterfs-fuse)将 GlusterFS 挂载到本地文件系统之上,实现 POSIX 兼容的方式来访问系统数据。
重点来了,
GlusterFS卷类型
为了满足不同应用对高性能、高可用的需求,GlusterFS 支持 7 种卷,即 distribute 卷、stripe 卷、replica 卷、distribute stripe 卷、distribute replica 卷、stripe Replica 卷、distribute stripe replica 卷。其实不难看出,GlusterFS 卷类型实际上可以分为 3 种基本卷和 4 种复合卷,每种类型的卷都有其自身的特点和适用场景。(怎么说呢,我的理解就是raid磁盘系列,每种都有自己的优缺点,你根据需求是性能还是扩容,随便选用即可! 只要关注前面的三种基本卷就行了,后面的反正也是前面的组合混搭,至少我觉得后面几种卷用的应该不太多把。。。)
###For example to create a distributed volume with four storage servers using TCP.
gluster volume create test-volume server1:/exp1 server2:/exp2 server3:/exp3 server4:/exp4 Creation of test-volume has been successful Please start the volume to access data
别人的小结:基于 Hash 算法将文件分布到所有 brick server,只是扩大了磁盘空间,不具备容错能力。由于distribute volume 使用本地文件系统,因此存取效率并没有提高,相反会因为网络通信的原因使用效率有所降低,另外本地存储设备的容量有限制,因此支持超大型文件会有一定难度。
###For example, to create a replicated volume with two storage servers:
gluster volume create test-volume replica 2 transport tcp server1:/exp1 server2:/exp2
Creation of test-volume has been successful
Please start the volume to access data
别人的小结:文件同步复制到多个 brick 上,文件级 RAID1,具有容错能力,写性能下降,读性能提升。Replicated 模式,也称作 AFR(Auto File Replication),相当于 RAID1,即同一文件在多个镜像存储节点上保存多份,每个 replicated 子节点有着相同的目录结构和文件,replica volume 也是在容器存储中较为推崇的一种。
这个用法需要注意的地方就是 中间指定卷类型如果为n个副本,则后面必须接对应n个 节点地址;
假如你前面指定4个副本,后面接的2个pv地址,那么就是raid0+1了,即后面所谓的复合卷 distribute stripe volume.
假如你前面指定2个副本,后面接的4个节点地址,即下面所谓的基础卷 Distributed Replicated Glusterfs Volume.
###For example, four node distributed (replicated) volume with a two-way mirror:
gluster volume create test-volume replica 2 transport tcp server1:/exp1 server2:/exp2 server3:/exp3 server4:/exp4
Creation of test-volume has been successful Please start the volume to access data
别人的小结:Brick server 数量是条带数的倍数,兼具 distribute 和 stripe 卷的特点。分布式的条带卷,volume 中 brick 所包含的存储服务器数必须是 stripe 的倍数(>=2倍),兼顾分布式和条带式的功能。每个文件分布在四台共享服务器上,通常用于大文件访问处理,最少需要 4 台服务器才能创建分布条带卷。
###For example, to create a striped volume across two storage servers:
gluster volume create test-volume stripe 2 transport tcp server1:/exp1 server2:/exp2
Creation of test-volume has been successful
Please start the volume to access data
别人的小结:类似 RAID0,文件分成数据块以 Round Robin 方式分布到 brick server 上,并发粒度是数据块,支持超大文件,大文件的读写性能高。
GlusterFS 客户端常用命令: (创建信任集群后,在任意一个节点执行下面命令,集群全部配置生效,这句话或许说的不够准确呢!)
命令 功能
gluster peer probe 添加节点
gluster peer detach 移除节点
gluster volume create 创建卷
gluster volume start 启动卷
gluster volume stop 停止卷
gluster volume delete 删除卷
其实上面说了这么多,也就是打个基础和铺垫,对于今天的标题来说,这才是重点!!!
基于docker的持久化,如果要使用到glusterfs必须安装别人写的第三方插件,(我觉得主要是docker懒,没有出系统化的持久化方案,或许未来更新迭代应该也不会有了,因为有k8s了,哈哈哈!)
摘抄如下:接下来,我们再来看GlusterFS如何作为Docker的存储。Docker Volume是一种可以将容器以及容器生产的数据分享开来的数据格式,我们可以使用宿主机的本地存储作为Volume的提供方,也可以使用Volume Plugin接入许多第三方的存储。 GitHub就有一个Docker GlusterFS Volume Plugin,方便我们将GlusterFS挂载到容器中。
原文:https://www.ibm.com/developerworks/cn/opensource/os-cn-glusterfs-docker-volume/index.html (也就是上面的中文拓展网址)
基于k8s编排工具的持久化,k8s是原生就支持glusterfs的存储驱动的,当然k8s还支持别的很多种存储驱动,今天就讲讲它算了。
安装好k8s后,直接部署下面几个文件即可!
[[email protected] glusterfs]# cat glusterfs-pvc.yaml #先创建pv,再创建pvc。比如创建个100G的大磁盘,里面分个50G的分区出来!用的是分区名字。
apiVersion: v1
kind: PersistentVolume
metadata:
name: gluster-pv
spec:
capacity:
storage: 5Gi
accessModes:
- ReadWriteMany
glusterfs:
endpoints: "glusterfs-cluster"
path: "gv0"
readOnly: false
---
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
name: glusterfs-pvc
spec:
accessModes:
- ReadWriteMany
resources:
requests:
storage: 5Gi
[[email protected] glusterfs]# cat glusterfs-endpoints.json #ep的意思其实就是指定glusterfs集群的节点ip地址
{
"kind": "Endpoints",
"apiVersion": "v1",
"metadata": {
"name": "glusterfs-cluster"
},
"subsets": [
{
"addresses": [
{
"ip": "192.168.0.78"
}
],
"ports": [
{
"port": 1
}
]
},
{
"addresses": [
{
"ip": "192.168.0.101"
}
],
"ports": [
{
"port": 1
}
]
}
]
}
[[email protected] glusterfs]# cat glusterfs-service.json #svc主要就是把容器和应用给发布出去,比如通过cluster(集群)的port(端口) 1就能访问到了
{
"kind": "Service",
"apiVersion": "v1",
"metadata": {
"name": "glusterfs-cluster"
},
"spec": {
"ports": [
{"port": 1}
]
}
}
[[email protected] glusterfs]# cat nginx-deployment.yaml #dep主要的作用就是部署任务了。
apiVersion: extensions/v1beta1
kind: Deployment #部署一个nginx到k8s集群
metadata:
name: nginx-deployment
spec:
replicas: 3 #副本为3
template:
metadata:
labels:
app: nginx #标签是app:nginx
spec:
containers:
- name: nginx
image: nginx #镜像是nginx:laster,拉取最新的nginx镜像
volumeMounts:
- name: glusterfsvol
mountPath: /usr/share/nginx/html #挂载到容器的位置
ports:
- containerPort: 80
volumes:
- name: glusterfsvol
glusterfs:
endpoints: glusterfs-cluster #这里就和上面第三步创建的的ep的name必须对应,不然就报错!
path: gv0 #这是glusterfs的pvc名称,也就是第一步创建的那个
readOnly: false #并不是只读
---
apiVersion: v1
kind: Service #发布服务svc,让外界能访问到容器
metadata:
name: nginx-service
spec:
selector:
app: nginx #这个标签就是匹配上面发布nginx的那个标签!
ports:
- name: http
port: 80 #外界访问cluster集群的 端口是80
protocol: TCP
targetPort: 80 #外界访问pod的端口是 80
type: NodePort #其实这里还有个nodeport,也就是访问node节点的端口,既然没有指定端口的话,部署就应该是随机指定一个,特点好像是5位数的端口。(后面验证了一下,Kubernetes 会从 30000-32767 中分配一个可用的端口??? 我也不懂为啥我的实验不一致呢?或者说前面这个说法是错的。埋坑!!!)
填坑:
我自己自定义了端口范围。。。
总的来说,port和nodePort都是service的端口,前者暴露给集群内客户访问服务,后者暴露给集群外客户访问服务。从这两个端口到来的数据都需要经过反向代理kube-proxy流入后端pod的targetPod,从而到达pod上的容器内。
实验结果:
[[email protected] PV]# kubectl get all -o wide
NAME DESIRED CURRENT UP-TO-DATE AVAILABLE AGE CONTAINERS IMAGES SELECTOR
deploy/nginx-deployment 3 3 3 3 22m nginx nginx app=nginx
NAME DESIRED CURRENT READY AGE CONTAINERS IMAGES SELECTOR
rs/nginx-deployment-5b87cb9b85 3 3 3 22m nginx nginx app=nginx,pod-template-hash=1643765641
NAME DESIRED CURRENT UP-TO-DATE AVAILABLE AGE CONTAINERS IMAGES SELECTOR
deploy/nginx-deployment 3 3 3 3 22m nginx nginx app=nginx
NAME DESIRED CURRENT READY AGE CONTAINERS IMAGES SELECTOR
rs/nginx-deployment-5b87cb9b85 3 3 3 22m nginx nginx app=nginx,pod-template-hash=1643765641
NAME READY STATUS RESTARTS AGE IP NODE
po/nginx-deployment-5b87cb9b85-49lmx 1/1 Running 0 22m 172.17.23.7 192.168.0.101
po/nginx-deployment-5b87cb9b85-8php8 1/1 Running 0 22m 172.17.23.2 192.168.0.101
po/nginx-deployment-5b87cb9b85-phl87 1/1 Running 0 22m 172.17.35.3 192.168.0.78
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE SELECTOR
svc/glusterfs-cluster ClusterIP 10.10.10.246 <none> 1/TCP 8d <none>
svc/kubernetes ClusterIP 10.10.10.1 <none> 443/TCP 12d <none>
svc/nginx-service NodePort 10.10.10.149 <none> 80:36914/TCP 22m app=nginx
That‘s ALL!
Thankyou!
原文地址:http://blog.51cto.com/20has/2104838