【编者的话】
自从我第一次尝试在Docker中运行Ceph已经过去快两年了。时光飞逝,直到最近我才有时间重新开始这项工作。在过去的几个月中,我把业余时间都用在Docker中部署Ceph上了。在我们开始之前,我想说明一下如果不是Seán C. McCord的帮助,这项工作根本不可能。事实上,目前github上的ceph-docker项目就是基于Seán的早期工作。让我们来看看怎么把它跑起来吧!
原理
在Docker中运行Ceph是存在一些争议的,很多人可能认为完全没必要这样做。虽然将Monitors, Metadata Server和Rados Gateway容器化没什么问题,但当涉及到OSD时,事情就变得棘手。Ceph的OSD与它运行的主机紧密相关,与底层硬件的强烈关系和寻常的软件不同。如果OSD依赖的硬盘损坏,OSD也无法工作,这也是容器化场景中的问题所在。
坦白的说,我经常这样想:
我也不知道我为什么做这个。我只知道人们需要(是的,他们也不知道为什么)。我只是觉得这样很有必要,所以就让我们试试看吧。
我知道这听起来一点都不乐观,但在某种程度上就是真相。我的观点后来也有所变化,所以让我来解释一下为什么值得这样做。希望这也能改变你的看法。是的我的解释不仅仅是:Docker很酷,所以让我们Dockerize一切。
人们已经投入了很多努力,在自己的平台上运行容器化的软件。因此,他们在使用各种工具来构建和编排他们的环境。而且看到Kubernetes成为这类的编排工具,我一点都不吃惊。有些人还喜欢在生产环境尝试最新的技术,不然会觉得自己的工作很无聊(Seán,对吗?)。所以,在containerize一切的道路上,他们看到自己喜欢的开源存储解决方案也容器化了会非常高兴:)。
凡是与yum
或者apt-get
相关的,都不容易回滚,这与容器不同。容器使得升级和回滚都变得非常容易,因为你可以很容易地用docker stop
和docker run
来运行程序的新版本。你也可以在一台机器上运行多个相互隔离的集群。这也是开发模式的最理想状态。
项目
如前所述,一切都源于Seán C. McCord的工作,我们都是在他的基础上进行完善的。现在,如果你使用ceph-docker,你可以在Ubuntu或者CentOS上运行单个的Ceph守护进程。
在Docker Hub上我们有很多可用的镜像。我们使用Ceph的命名空间,所以我们镜像的前缀是ceph/<daemon>
。我们使用了自动构建,因此每次合并一个新补丁就会触发构建,并生成一个新版本的容器镜像。由于我们目前正处于重构过程中,你会看到大量可用的镜像。历史的原因,每个守护进程都有一个镜像(在合并这个补丁前,我们会一直这样做 )。因此monitor,OSD,MDS和radosgw各有一个容器镜像。这不是最理想的而且也没必要这样。这也是我们为什么开始daemon
镜像工作的原因。这个镜像包含了Ceph所有的守护程序和调用docker run
命令时你想使用的参数。也就是说,如果你准备开始,我建议直接使用ceph/daemon
镜像。在下一节我举例说明如何运行。
容器化CEPH
MONITORS
由于monitors不能在NAT过的网络进行通信,我们需要使用--net=host
暴露Docker主机网络:
$ sudo docker run -d --net=host \ |
可用选项列表:
MON_IP
是你运行Docker的主机IP地址MON_NAME
是你的monitor名称(默认:$(hostname))CEPH_PUBLIC_NETWORK
是你运行Docker的主机CIDR,应该与MON_IP
是相同的网络CEPH_CLUSTER_NETWORK
是你运行Docker的主机的第二块网卡CIDR,用于OSD复制流量
OBJECT STORAGE DAEMON
按照微服务的理念,我们不应该在容器中运行多个服务,当前的实现允许你在每个容器运行一个OSD进程。在我们的例子中,一个容器中运行多个OSD进程打破了这种理念,是不可取的行为。也增加了方案安装和维护的复杂性。
在这个配置中,--privileged=true
是必须的,因为我们需要完全访问/dev/
和其他内核功能。不过在简单的开放OSD目录基础上支持另外的配置,其中operators会对设备做适当的准备工作。然后只要简单的开放OSD目录并由entrypoint来完成OSD(ceph-osd mkfs
)配置。现在我介绍的配置方法比较简单,因为你只需要指定一个块设备,然后entrypoint会完成剩下的所有工作。
对于那些不希望使用--privileged=true
的,请退回到第二个例子。
$ sudo docker run -d --net=host \ |
如果你不希望使用--privileged=true
,你也可以使用你选择的配置管理工具手动配置OSD。
没有特权模式的例子,在这个例子中假设你已经分区和配置了文件系统并挂载了OSD分区。要创建OSD,只需运行下面的命令:
$ sudo docker exec <mon-container-id> ceph osd create. |
然后运行您的容器,如下所示:
docker run -v /osds/1:/var/lib/ceph/osd/ceph-1 -v /osds/2:/var/lib/ceph/osd/ceph-2 |
可用选项列表:
OSD_DEVICE
是OSD设备,如:/dev/sdbOSD_JOURNAL
是将用于存储OSD日志的设备,如:/dev/sdzHOSTNAME
是运行OSD容器主机的主机名(默认:$(hostname))OSD_FORCE_ZAP
将强制指定设备内容zapping(默认值:0,1是开启)OSD_JOURNAL_SIZE
是OSD日志大小(默认值:100)
METADATA SERVER
这个是非常直观和容易实现的。目前唯一要注意的是Docker中需要Ceph管理员密钥。这个密钥将被用来创建CephFS池和文件系统。如果你运行旧版本的Ceph(0.87之前的版本)你不用这个。但是最好运行最新版本,所以你还是需要!
$ sudo docker run -d --net=host \ |
可用选项列表:
MDS_NAME
是元数据服务的名称(默认:mds-$(hostname))CEPHFS_CREATE
会为元数据服务创建一个文件系统(默认值:0,1是启用)CEPHFS_NAME
是元数据文件系统的名称(默认:cephfs)CEPHFS_DATA_POOL
是元数据服务的数据池名称(默认:cephfs_data)CEPHFS_DATA_POOL_PG
是数据池placement groups的数量(默认值:8)CEPHFS_DATA_POOL
是元数据服务的元数据池名称(默认:cephfs_metadata)CEPHFS_METADATA_POOL_PG
是元数据池placement groups的数量(默认值:8)
RADOS GATEWAY
对于Rados Gateway,我们部署时会默认开启civetweb
。也可以通过简单地指定远程地址和端口以使用不同的CGI前端。
$ sudo docker run -d --net=host \ |
可用选项列表:
RGW_REMOTE_CGI
指定是否使用Rados Gateway嵌入的Web服务(默认值:0,1是不使用)RGW_REMOTE_CGI_HOST
指定运行CGI进程的远程主机RGW_REMOTE_CGI_PORT
运行CGI进程的远程主机端口RGW_CIVETWEB_PORT
是civetweb的监听端口(默认:80)RGW_NAME
是Rados Gateway实例名称(默认:$(hostname))
后续工作
配置存储后端
缺省情况下,在初始化monitor启动时,会生成ceph.conf
和所有的CEPH密钥。此过程假设你会将集群扩展到多个节点,你必须分发这些配置到所有节点。这一点都不灵活,我们希望改善这一点。我马上提出的一个方案是使用Ansible生成配置/密钥并分发他们到所有机器。另外,我们也希望能够在不同的后端KV存储上存储所有配置文件,例如etcd和consul。
编排部署
最简单的方法是使用ceph-ansible,其中主要的逻辑已经完成了。我只需要再提交一些修改,大部分的工作已经完成。Kubernetes也发布了可用的运行monitors的预览版。
Rocket等其他容器技术延伸
你可以简单地将你的Docker镜像放到Rocket容器环境中并启动他们(这里一语双关,你懂了没?)。
福利视频
这里有一个视频demo:
我想借此机会再次感谢Seán C. McCord,是他让这一切成为可能。Seán是一个很好的工作伙伴,我期待着与他一起为ceph-docker贡献!
原文链接:BOOTSTRAP YOUR CEPH CLUSTER IN DOCKER (翻译:朱高校)