Mesos Introduction
Table of Contents
基本概念
基本架构
Mesos用于管理分布式集群,简单来讲就是隐藏底层硬件设施细节,让开发人员能够将一个集群当成一台高性能计算机。 Mesos将所有资源汇集到一个资源池来避免静态划分以提高资源利用率。
Mesos架构分为如下几个部分:master、slave、框架、通信、附属服务。
- master负责给不同框架分配资源并管理任务的生命周期,资源以offer为单位,每个offer属于一个slave,一个slave可以提供多个offer。
- slave负责执行框架下发的任务,以及对任务的隔离。还需要保证不多不少的给予承诺的资源。
slave资源是指master管理的资源,即运行任务会消耗的元素;
slave属性是指slave的相关信息,它们不会被任务消耗,如操作系统、软件版本等。
--resources
和--attributes
分别用于表示资源和属性。 - 框架运行在Mesos之上,因此需要向Mesos注册。框架用于发起任务请求,任务会消耗资源并最终在slave上执行。框架由两部分组成,调度器负责协调任务执行,执行器启动任务。
- Mesos利用libprocess来异步通信,下列API用到了通信机制:
- 调度器API,调度器和master通信
- 执行器API,执行器和slave通信
- 内部API,master和slave通信
- 运维API,同步通信,主要为运维人员准备
- 附属服务包括:
- 共享文件系统:通过共享文件系统实现统一资源视图,如HDFS、NFS等
- 一致性服务:故障恢复依赖于一致性服务,如ZooKeeper、etcd等
- 服务编排(service fabric):包括多框架上的服务相互发现和连接,框架和用户相互连接等
- 运维服务:Mesos部署、升级、监控、报警、日志和安全等
安装部署
编译安装-Ubuntu
编译安装不是很环保,建议直接用二进制安装。
安装依赖:
sudo apt-get install tar wget git
sudo apt-get install openjdk-7-jdk
sudo apt-get install autoconf libtool
sudo apt-get install build-essential python-dev libcurl4-nss-dev \
libsasl2-dev libsasl2-modules maven libapr1-dev libsvn-dev
配置JAVA_HOME
:
# file: /etc/evironment or .profile export JAVA_HOME=/usr/lib/jvm/default-java PATH="$JAVA_HOME/bin:$PATH"
下载mesos:http://mesos.apache.org/downloads/
wget http://mirror.bit.edu.cn/apache/mesos/1.0.0/mesos-1.0.0.tar.gz ./bootstrap # Only required if from git repository mkdir build cd build ../configure make make check # Run test suite make install
构建完成后在build/bin
目录下有一系列命令可用,直接以root权限运行mesos-local.sh
即可启动本地集群,然后通过 http://127.0.1.1:5050/ 就能访问集群服务。
启动master:
sudo mkdir /var/lib/mesos
sudo chown `whoami` /var/lib/mesos/
mesos-master --work_dir=/var/lib/mesos
启动slave
mesos-slave --work_dir=/var/lib/mesos --master=127.0.1.1:5050
测试框架在build/src
下有三个版本,可以分别尝试如下命令运行:
./test-framework --master=127.0.1.1:5050 # C++ framework, build/src ./test-framework 127.0.1.1:5050 # build/src/java, build/src/python
二进制安装-CentOS
yum install mesos-1.0.0-2.0.89.centos65.x86_64.rpm
注意mesos-1.0需要在CentOS6.5以上的版本运行,否则会出现如下错误提示:
warning: mesos-1.0.0-2.0.89.centos65.x86_64.rpm: Header V4 RSA/SHA1 Signature, key ID e56151bf: NOKEY error: Failed dependencies: subversion is needed by mesos-1.0.0-2.0.89.centos65.x86_64 cyrus-sasl-md5 is needed by mesos-1.0.0-2.0.89.centos65.x86_64 libevent2-devel is needed by mesos-1.0.0-2.0.89.centos65.x86_64
这种情况可以从网上下载安装如下文件来解决依赖问题。
serf-1.3.7-1.x86_64.rpm subversion-1.8.16-3.x86_64.rpm libevent2-2.0.21-2.el6.x86_64.rpm libevent2-devel-2.0.21-2.el6.x86_64.rpm
如果安装过程遇到如下错误提示,可以直接删除提示的文件或目录再重试:
error: unpacking of archive failed on file xxx: cpio: rename
多节点部署
以下操作都在master所在主机上执行:
ssh-keygen -f ~/.ssh/mesos -P ""
ssh-copy-id -i ~/.ssh/mesos.pub USER@SLAVE1
ssh-copy-id -i ~/.ssh/mesos.pub USER@SLAVE2
scp -R build slave1:PREFIX
scp -R build slave2:PREFIX
edit PREFIX/var/mesos/deploy/masters
edit PREFIX/var/mesos/deploy/slaves
mesos-start-cluster.sh
常见问题
Failed to create directory '/sys/fs/cgroup/freezer'
# mesos-slave --work_dir=/var/lib/mesos --master=10.23.10.20:5050 WARNING: Logging before InitGoogleLogging() is written to STDERR I0812 13:30:33.992420 2107 main.cpp:243] Build: 2016-07-27 20:33:59 by root I0812 13:30:33.992513 2107 main.cpp:244] Version: 1.0.0 I0812 13:30:33.992521 2107 main.cpp:247] Git tag: 1.0.0 I0812 13:30:33.992527 2107 main.cpp:251] Git SHA: c9b70582e9fccab8f6863b0bd3a812b5969a8c24 I0812 13:30:33.997602 2107 containerizer.cpp:196] Using isolation: posix/cpu,posix/mem,filesystem/posix,network/cni Failed to create a containerizer: Could not create MesosContainerizer: Failed to create launcher: Failed to create Linux launcher: Failed to mount cgroups hierarchy at '/sys/fs/cgroup/freezer': Failed to create directory '/sys/fs/cgroup/freezer': No such file or directory
在CentOS6.5上遇到此问题,解决办法:
yum install libcgroup /etc/init.d/cgconfig status # show Stopped /etc/init.d/cgconfig start
Failed to obtain the IP address for 'xxx'
# mesos-slave --work_dir=/var/lib/mesos --master=masterip:5050 WARNING: Logging before InitGoogleLogging() is written to STDERR I0812 14:42:33.579213 8441 main.cpp:243] Build: 2016-07-27 20:33:59 by root I0812 14:42:33.579406 8441 main.cpp:244] Version: 1.0.0 I0812 14:42:33.579406 8441 main.cpp:247] Git tag: 1.0.0 I0812 14:42:33.579406 8441 main.cpp:251] Git SHA: c9b70582e9fccab8f6863b0bd3a812b5969a8c24 Failed to obtain the IP address for 'xxx'; the DNS service may not be able to resolve it: Temporary failure in name resolution
在CentOS6.5上遇到此问题,解决办法:添加hostname即可,无需重启网络,立即生效。
# edit /etc/hosts x.x.x.x a-hostname
内部机制
通信机制
Mesos四个组件master、slave、scheduler和executor采用actor model通信,协议用protobuf,基于libprocess
库实现。每个模块都是一个服务,监听其他模块的消息。计算框架想接入Mesos只需要写Scheduler和Executor即可。
线路1:master分配资源,提供给framework scheduler,scheduler将资源分配给任务,返回任务给master、master转发给slave。
线路2:scheduler可以将任务直接发送给slave。
线路3:slave负责管理framework executor并分配资源
注册所有消息处理函数的文件分别在:master.cpp、slave.cpp、sched.cpp、exec.cpp。通过如下命令就能找出所有注册函数。
git grep install\<.*\>
资源分配
Mesos在各个框架之间进行粗粒度资源分配,框架内部需要实现细粒度任务调度。 Mesos这种调度模式称为双层调度,调度器并不知道全局资源利用率,因此难以实现最优资源分配。
Mesos框架事件典型流程:
- 框架调度器在master注册
- master从slave获取offer,分配模块决定给哪个框架
- 框架调度器从master接收资源
- 框架调度器接受资源,向master返回执行器列表;框架也可以拒绝资源
- slave分配资源并运行执行器
- 框架调度器接收任务运行状态
- 框架调度器从master注销,该操作对于持久服务是不必要的
资源预留
静态预留通过--resources
指定,要改变静态预留需要删除slave的所有检查点,并重启slave。
动态预留能够将offer预留下来,以后只能分配给同一框架。框架在接受资源时发送Offer::Operations::Reserve
和Offer::Operations::Unreserve
来管理预留资源。
资源隔离
资源隔离简单来讲是通过接口分层来实现的,隔离机制都是在slave上实现。 slave进程调用容器机API,容器机调用隔离器API,隔离器就是容器,容器运行在slave操作系统之上,操作系统之下即为硬件资源。
容器机API目的用于支持多种容器机,因此可以提供自己的容器机和隔离器。
docker容器机
DockerContainerizer用于将任务或执行器启动销毁翻译成docker CLI,使用docker容器机典型步骤:
- 执行器将CommandInfo中指定文件放入沙箱
- 执行docker pull获取镜像
- 利用DockerExecutor运行docker镜像,将沙箱目录映射到容器并设置MESOS.SANDBOX为目录映射
- 将docker运行日志输出到沙箱stdout/stderr文件
- 在容器机退出时,停止并删除所有docker容器
准备工作:
- 在slave上安装docker CLI
--containerizers
指定dockercontainerInfo.DockerInfo.image
指定镜像.dockercfg
文件包含登录私有仓库信息
容错机制
slave宕机或升级,master会向框架发送slave宕机事件,当slave修复时,会重新向master注册。
master宕机会由选主来保证master高可用性,选主后slave和框架会重新注册。 Mesos只支持ZooKeeper选主服务。
配置文件zoo.cfg
基本配置项:
tickTime=2000 # ZK之间或ZK和客户端心跳间隔 dataDir=/tmp/zookeeper # 数据目录,如日志 clientPort=2181 # 客户端连接ZK的端口 initLimit=5 # slave初始化上限心跳数 syncLimit=2 # master和slave应答上限心跳数 # A 服务器编号 # B 服务器IP # C 服务器与master通信端口 # D 选举端口 server.A=B:C:D