一、Operator是什么,解决了什么问题

1.1、为什么需要Operator

1.1.1、无状态和有状态

K8s作为容器编框架,可以减轻配置、部署、管理和监控大规模容器应用的负担,早期的k8s非常善于管理无状态的应用程序,比如k8s提供的Deployment控制器,他认为所有的Pod都是完全一样的,Pod间没有顺序和依赖,扩容的时候,就根据模板创建一个一模一样的新的应用,也可以任意删除Pod。
但对于向DB这样的有状态的应用程序,添加删除实例可能需要不同的节点做不同的配置,与已有的集群进行通信写上等,这些操作通常需要我们人工来干预,这就会增加运维的负担,并增加出错的可能性,最重要的是他消除了k8s的一个主要的卖点:自动化。

这是一个大问题,那么如果在k8s中管理有状态的应用程序呢?

1.1.2、StatefulSet的价值和不足

k8s 1.5版本开始,出现了StatefulSet, StatefulSet提供了一系列资源来处理有状态的容器,比如: volume, 稳定的网络标识,从0到N的顺序索引等。通过为Pod编号,再使用k8s里面的两个标准功能:headless service和PV/PVC,实现了对Pod的拓扑状态和存储状态的维护,从而让用户可以在k8s上运行有状态的应用。

然后StatefulSet只能提供受限的管理,通过StatefulSet我们还是需要编写复杂的脚步,通过判断节点编号来区别节点的关系和拓扑,需要关心具体的部署工作,并且一旦你的应用没法通过上述方式进行状态的管理,那就代表了StatefuleSet已经不能解决他的部署问题了。

既然StatefulSet不能完美的圣人管理有状态应用的工作,那么还有什么优雅的解决方案呢?答案是Operator。
Operator在2016年由CoreOS提出,用来扩充K8s管理有状态应用的能力。

二、Operator的核心原理

解释operator不得不提k8s中两个最具价值的理念:“声明式API”和“控制器模式”。

“声明式API”的核心原理,就是当用户向k8s提交了一个API对象描述之后,k8s会负责为你保证整个集群里各项资源的状态,都与你的API对象描述的需求相一致。k8s通过启动一种叫做“控制器模式”的无限循环,watch这些API对象的变化,不断检查,然后调谐,最后确保整个集群的状态与这个API对象的描述一致。

比如k8s自带的控制器:Deployment,如果我们想在k8s中部署双副本的Nginx服务,那么我们就定义一个repicas为2的Deployment对象,Deployment控制器watch到我们的对象后,通过控制循环,最终会帮我们在k8s启动两个Pod。

Operator是同样的道理,以我们的Redis Operator为例,为了实现Operator,我们首先需要将自定义对象的说明,注册到k8s中,这个对象的说明就叫做CRD(Custom Resource Definition),用于描述我们Operator控制的应用:Redis集群实例,这样当用户告诉K8s我想要一个redis集群实例后,Redis Operator就能通过控制循环执行调谐逻辑达到用户定义状态。


所以Operator本质上是一个个特殊应用的控制器,其提供了一种在k8s API之上构建应用程序并在k8s上部署程序的方法,他允许开发中扩展k8s API,增加新功能,像管理k8s原生组件一样管理自定义的资源。如果你想运行一个Redis哨兵模式的主从集群,或者TiDB集群,那么你只需要提交一个声明就可以了,而不需要关心部署这些分布式的应用需要的相关领域的知识,Operator本身就可以做到创建应用、监控应用状态、扩缩容、升级、故障恢复、及资源清理等,从而将分布式应用的使用门槛降到最低。

2.1、Operator核心价值

  • Operator扩展了k8s的能力
  • Operator将人工的运维知识系统化为代码
  • Operator以可扩展、可重复、标准化的方式实现目标
  • Operator减轻了开发人员的负担

2.2、Operator服务化目标

用户想在k8s中快速的运行一些分布式有状态的应用,但他们本身不关心部署、运维,既然Operator可以灵活和优雅的管理有状态应用,我们可以做个Operator平台,基于Operator将K8s管理有状态应用的能力方便的暴露给用户。

核心的目标主要有两方面:
1、针对Operator平台

  • 提供一个简单易用的控制台供用户使用,用户只需要点点鼠标,就能快速拉起有状态应用,并且能在控制台上实时看到应用部署的进度和事件,查看资源,更新资源等。
  • 通用化,将应用名称等通用配置和应用参数(如:redis的maxclients, timeout等参数)解耦。这样带来的好处就是不同的Operator可以共用创建页面,而不需要为每种Operator定制创建页面,同时Operator暴露出更多的应用配置参数时,前端开发也不需关心,由后端通过API返回给前端参数,前端渲染参数,用户修改参数后,通过API传递到后端,后端将参数与模板渲染成最终的实例声明,提交到k8s中,节省了前端开发时间。
  • 可以管理通过公共的Operator和Namespace私有的Operator创建的实例。用户可以用我们提供的公用的Operator,也可以把operator部署到自己的namespace,给自己的项目提供服务,但这两种operator创建的应用实例都可以通过operator控制台管理。
  • 可以无限添加Operator

2、针对Operator控制器

  • 拉起分布式集群,自动运行配置、运维
  • 可以动态更改所控制应用参数
  • 控制器本身需要无状态,不能依赖外部数据库等
  • 实时更新状态,维护状态,推送事件
  • 可以运行在集群范围,也能运行在单namespace, 并且可以共存,不能冲突;

针对上述目标,最终我们实现了operator控制台:

同时为Operator控制台定义了第一个Operator:Redis Operator,未来可推出更多的operator。

三、Redis Operator

3.1、Redis集群模式选型

我们知道Redis集群模式主要有主从模式、哨兵模式、Redis官方CLuster模式及社区的代理分区模式。

分析以上几种模式,主从模式的Redis集群不具备自动容错和恢复功能,主节点和从节点的宕机,都会导致读写请求失败,需要等待节点恢复才能恢复正常;
而Redis官方cluster模式及社区的代理分区模式,只有在数据量及并发数大的业务中才有使用需求。哨兵模式基于主从模式,但因为增加了哨兵节点,使得redis集群拥有了主从切换,故障转移的能力,系统可用性更好,而客户端也只需要通过哨兵节点拿到master和slave地址就能直接使用。因此我们决定为operator平台提供一个快速创建哨兵模式的redis集群的redis operator。

3.2、开源Operator的不足

目前已有一些开源的Redis Operator,通过对这些Operator分析,我们发现都不能满足我们的需求,这些开源的Operator:

  • 不能设置redis密码
  • 不能动态响应更改参数
  • 没有维护状态,推送事件
  • 不能在开启了istio自动注入的namespace中启动实例
  • 只能运行在集群或但namespace模式

3.3、改进工作

我们定制开发了Redis Operator在Github上开源:https://github.com/ucloud/redis-operator,提供:

  • 动态响应更改Redis配置参数
  • 实时监控集群状态,并且推送事件,更新状态
  • 误删除节点故障恢复
  • 设置密码
  • 打开关闭持久化快捷配置
  • 暴露Prometheus metrics

使用Redis Operator我们可以很方便的起一个哨兵模式的集群,集群只有一个Master节点,多个slave节点,假如指定Redis集群的size为3,那么Redis Operator就会帮我们启动一个master节点,2个slave节点,同时启动是3个sentinel节点来管理Redis集群:

Redis Operator通过StatefulSet管理Redis节点,通过Deployment来管理Sentinel节点,这比管理裸Pod要容易,节省实现成本。同时创建一个Service指向所有的哨兵节点,通过Service对客户端提供查询Master,slave节点的服务。最终,Redis Operator控制循环会调谐集群的状态,设置集群的拓扑,让所有的Sentinel监控同一个Master节点,监控相同的Slave节点。Redis operator除了会watch实例的创建、更新、删除事件外,还会定时检测已有的集群的监控状态,实时把集群的状态记录到spec.status.conditions中:

status:conditions:- lastTransitionTime: "2019-09-06T11:10:15Z"lastUpdateTime: "2019-09-09T10:50:36Z"message: Cluster okreason: Cluster availablestatus: "True"type: Healthy- lastTransitionTime: "2019-09-06T11:12:15Z"lastUpdateTime: "2019-09-06T11:12:15Z"message: redis server or sentinel server be removed by user, restartreason: Creatingstatus: "True"type: Creating

为了让用户通过kubectl快速查看redis集群的状态,我们在CRD中定义了如下的additionalPrinterConlums:additionalPrinterColumns:

- JSONPath: .spec.sizedescription: The number of Redis node in the ensemblename: Sizetype: integer- JSONPath: .status.conditions[].typedescription: The status of Redis Clustername: Statustype: string- JSONPath: .metadata.creationTimestampname: Agetype: date

由于CRD的addtionalPrinterColumns对数组类型支持不完善,只能显示数组的第一个元数据,所以需要将spec.status.conditions中的状态按时间倒序,最新的状态显示在上方,方便用户查看最新的状态。通过使用也可以通过kubectl命令直接查看集群的监控状况:

3.4、快速持久化

我们还了解到,用户使用Redis时,有一些使用场景是直接将Redis当数据库用,需要持久化配置,而有些只是当做缓存,允许数据丢失。

为此,我们特意在Redis集群的CRD中添加了快速持久化配置的开关,默认为启用,这会为用户自动开启和配置RDB和AOF持久化,同时结合PVC(Persistent Volume Claim)可以将用户的数据持久化起来。但节点故障,被误删除时数据也不会丢失,并且PVC默认不会跟随Redis集群的删除而删除,当用户在相同namespace下启动同名的Redis集群时,又可以使用上次的PVC,从而恢复数据。

podAntiAffinity:preferredDuringSchedulingIgnoredDuringExecution:- podAffinityTerm:labelSelector:matchLabels:app.kubernetes.io/component: redisapp.kubernetes.io/managed-by: redis-operatorapp.kubernetes.io/name: testapp.kubernetes.io/part-of: redis-clusterredis.kun/v1beta1: prj-shu_testtopologyKey: kubernetes.io/hostnameweight: 100

为了让Redis拥有更高的可用性,我们为Redis节点提供了设置node affinity, pod anti affinity的能力(可避免某些Pod部署在同一个Node上),可以灵活的控制redis数据节点泡在不同Node或者不同数据中心,做到跨机房容灾。如上所示,redis operator缺省情况下,会为每个Pod注入podAntiAffinity,让每个redis服务尽量不会运行在同一个Node节点。

3.5、监控

Operator中还内置了Prometheus Exporter,不仅将operator自身的一些metrics暴露出来,还会将operator创建的每一个redis集群实例的状态通过metrics暴露出来。

这还不够,我们还为每个redis节点提供了单独暴露metrics的能力,用户可以在启动redis集群的时候,为每个redis节点注入单独的exporter,这样每个集群的每个redis暑假节点都能被我们单独的监控起来,结合Prometheus和AlterManager可以很方便的将Operator及Operator创建的实例监控起来。

结合Operator的运维、StatefulSet的能力,加上Sentinel的能力,等于说为Redis集群加了三重保险,可以确保集群的高可用。

参考链接:https://www.infoq.cn/article/pPP3LRqf8BApcg3azNL3

Redis Operator学习笔记相关推荐

  1. Redis 进阶学习笔记

    Redis进阶学习笔记 阅读Redis.conf配置文件 # 61, 绑定的 IP , 一般注释掉该命令,这个吗,命令表示仅接受本机的(IP为本机)客户端连接, bind 127.0.0.1 # 80 ...

  2. redis安全学习笔记

    redis安全学习笔记 [toc] 文章部分内容首发于xray社区公众号 基础 https://www.runoob.com/redis/redis-tutorial.html 环境 : ubuntu ...

  3. 尚硅谷Redis 7学习笔记

    尚硅谷Redis 7学习笔记 视频链接 新手入门篇 1.安装及数据类型 2.持久化 3.Redis 7 事务.管道.发布订阅.主从.哨兵.集群 4.springboot整合redis 高级篇(更新中- ...

  4. memcache/redis 缓存学习笔记

    0.redis和memcache的区别 a.redis可以存储除了string之外的对象,如list,hash等 b.服务器宕机以后,redis会把内存的数据持久化到磁盘上,而memcache则不会 ...

  5. NoSQL Redis的学习笔记

    我下载在:/var/www/html/   (redis.conf在此目录下) 启动Redis:/var/www/html/src下  ./redis-server     然后另一个客户端/src下 ...

  6. Redis个人学习笔记 参考B站视频以及CSDN文档 2万多字 非常全面

    参考内容: B站尚硅谷Redis视频教程 <Redis 6 入门到精通 超详细 教程> B张黑马程序员Redis视频教程 <黑马程序员Redis入门到实战教程,全面透析redis底层 ...

  7. 【转载】Redis个人学习笔记 参考B站视频以及CSDN文档 2万多字 非常全面

    参考内容: B站尚硅谷Redis视频教程 <Redis 6 入门到精通 超详细 教程> B张黑马程序员Redis视频教程 <黑马程序员Redis入门到实战教程,全面透析redis底层 ...

  8. redis geohash 学习笔记

    附近的人: 地图元素的位置数据使用二维的经纬度表示,经度范围 (-180, 180],纬度范围 (-90, 90],纬度正负以赤道为界,北正南负,经度正负以本初子午线 (英国格林尼治天文台) 为界,东 ...

  9. rxjs operator学习笔记

    Pipeable Operators are the kind that can be piped to Observables using the syntax observableInstance ...

  10. Redis数据库学习笔记

    一.NoSql(非关系型数据库) NoSQL:NoSQL = Not Only SQL 非关系型数据库 ​ NoSQL,泛指非关系型的数据库.随着互联网web2.0网站的兴起,传统的关系数据库在应付w ...

最新文章

  1. unity3d Update()和FixedUpdate()的区别
  2. Basic的Json与Xml
  3. Java飞行记录器(JFR)
  4. python try else_python try/except/else与递归
  5. 【C++】C++读取文本中的特定一列
  6. 太极图正确画法_太极图的三种画法你知道吗?
  7. burp基本的用法总结
  8. (七)对Jmeter进行参数化的俩种方式
  9. C语言实现数字串转数字
  10. SpringBoot + Vue 学生管理系统源码(包含数据库文件)
  11. C#反编译工具ilspy下载地址
  12. 使用Android Studio生成APP图标
  13. 【报告分享】2021年中国商业物联网行业研究报告-艾瑞咨询(附下载)
  14. 【Unity3D插件】Alembic插件分享《abc动画文件导入Unity》
  15. word如何去掉标题前面的黑点
  16. HashMap 容量为2次幂的原因
  17. 创新、创业,风险投资介绍。附:2019年热门风险投资人 ( VCPE )
  18. 史上最简单笔记本选购攻略(给对笔记本配置完全不懂的小白,建议收藏)
  19. 微软雅黑html中怎么写,css样式怎么设置字体为微软雅黑?
  20. VMD读取trr轨迹的方法

热门文章

  1. 煮酒探西游 吴闲云全面解读西游记
  2. css的sprites什么意思,CSS Sprites是什么
  3. 计算机网络管理工程师证书考试试题,(信息化知识)国家信息化人才考试计算机网络工程师模拟试题.pdf...
  4. Black Hat USA 2011: Alexander Polyakov - CTO - ERPScan
  5. 教学小结:我这样帮助学生提出疑问
  6. python数字类型中包含了哪三种类型_Python数字类型中包含了________、________和_________三种类型。...
  7. 从360、QQ之争看腾讯的无耻
  8. 第三代USRP 产品对比
  9. vulnhub 网站靶机 DC-1 打靶记录
  10. nodejs和前端基于websocket实现微信群聊与私聊