Oprtator模式
Operator模式包含以下是三个重要的机制(属性)
自定义资源
• 定义组件属性:包含期望值 + 状态值
• 需要具备扩展性
Informer事件机制
• 资源监听:监听自定义资源、以及相关的资源
• 资源过滤:根据ownerReferences等过滤非相关的资源
循环控制
• 主要为让期望值(spec)和状态(status)达到一致
• 各种自动化运维的操作以代码的方式沉淀
Operator/Controller流程简述
以下是Operator/Controller的大体流程(可以参考官方的sample-controller项目),在SyncHandler(kubebuilder或者operator-sdk 的reconcile)流程中通常需要实现这么几层逻辑。
AddEventHandler
自定义资源关联的资源
SyncHandler(Reonciler)
1. 资源管理层:自定义资源与内部资源映射维护
2. 组件管理层:通过SDK/API对组件进行配置、运维操作等
3. 状态管理层:状态值的检查和记录
云原生MYSQL架****构
KUBERNETES:集群层,提供容器运行环境
MYSQL-OPERATOR:负责MYSQL集群的运维工作
MYSQL集群:MYSQL运行实例
中间件管理平台:平台层,负责界面化的中间件管理
MYSQL资源结构设计
以下是我们针对MYSQL集群设置的自定义资源结构。
元数据:包含k8s所需要的元数据和自定义的label或者annoations
期望值:用户的期望值属性。包含集群的相关属性和MYSQL的相关属性
状态值:MYSQL的运行状态。包括节点信息、整体运行情况
具体定义如下(仅仅作为参考)
自动化部署
1. 部署OPERATOR:通过deployment部署MYSQL-Operator实例和自定义资源
2. 部署MYSQL:
MYSQL配置
reset slave;
change master to master_host='%s', master_user='%s', master_password='%s',MASTER_PORT=%d,master_auto_position=1 for channel 'replication_applier'
start slave;
检查复制状态
show slave status;
故障自愈能力
1. MYSQL进程异常(可能是由于主机、进程奔溃、阻塞等其他原因)
2. 监控检查探针识别到该MYSQL异常
3. Operator开始触发转移操作
4. 如果故障的是主库,则做数据的延迟检查、将打开备库的流量通道,并配置只读配置。读写都在旧的从库上
5. 如果故障的备库,则直接将备库写的流量切换到主库;
扩容技术
通过数据扩容的横向扩容可以提高读数据的能力
1. 修改MysqlCluster资源中的replicas属性,由2修改为3
2. Operator发现该值被修改,新建一个Pod
3. 待Pod Runnig以后,Operator访问新建的Mysql Pod, 配置复制策略
4. Operator 执行show slave status命令,检查所有Mysql
5. 最后更新MysqlCluster.status属性
LVM存储
CSI-Provisioner: 监听PVC并且创建PV
CSI-Resizer: 监听PVC存储的情况,进行扩缩容
LVM-CSI-plugin: 实现LVM数据卷的创建和卸载管理。
云原生监控支持
常见的Prometheus + Grafana + Alermanager架构
实时容灾能力
实现了跨机房的MYSQL容灾。
数据备份与恢复
数据备份
• 定时备份资源MysqlBackupSchedule通过corn表达式创建备份资源MysqlBakcup
• 备份资源资源MysqlBakcup创建job,调度pod与Master在相同节点,内置xtrabackup工具备份MYSQL数据,备份完毕后通过MINIO客户端mc上传备份文件到MINIO中
数据恢复
由于xtrabackup的特性,需要基于新的MYSQL进行创建,则需要创建一个新的MysqlCluster资源,并且导入备份数据进而恢复。
通用备份
基于LVM的通用备份工具
采用csi-plugin实现通用的lvm快照备份,并且上传到MINIO。
提供备份的pre-hook以及post-hook,可以用于MYSQL的备份锁、数据刷盘等策略。其他组件也可以采用类似的方式进行管理。
内核能力扩展
线程池
默认的Mysql连接方式是, one-thread-per-connection,也就是每一个连接请求采用一个线程进行处理。这种模式在大量的线程请求下效率会非常差。
为了提升高并发的问题,以插件的形式支持MYSQL以线程池的方式应对大连接。
MYSQL默认连接方式
每个线程除以一个客户端的socket,并且堵塞接收client消息。
MySQL Thread-pool 连接方式
1. 单个监听线程通过IO多路复用(EPOLL),接收线程池里面一个组的所有IO请求,并且转发给工作线程
2. 工作线程循环处理请求,如果没有则进入休眠
采用sysbench对线程池进行压力测试
随着压测线程的上升的确有了很大的性能提升。
数据回收站
MYSQL不具备数据删除回收的功能,当发生数据误删除则只能通过备份数据进行恢复,可能导致数据的部分丢失。为了解决这个问题,目前以插件的方式提供数据回收的能力。
mysql复制插件包含以下扩展结构
• Trans_observer:扩展事务执行
• Server_state_observer:扩展服务状态
• Binlog_storage_observer:binlog存储
• Binlog_transmit_observer:binlog dump
• Binlog_relay_IO_observer:扩展中继日志我们针对Binlog_relay_IO_observer接口进行了扩展,实现了数据回收的能力。
针对从库中继日志落盘的回调方法中执行相应的操作逻辑,发现如果是删除表/库操作,则针对具体操作的表对象进行rename操作,将表移动到回收站,超过一定期限才会删除。
typedef struct Binlog_relay_IO_observer {
...
// 将事件包写入中继日志后调用此回调
int (*after_queue_event)(Binlog_relay_IO_param *param,
const char *event_buf, unsigned long event_len,
uint32 flags);
...
} Binlog_relay_IO_observer;
未来工作
MYSQL代理接入
1. 采用MYSQL 代理的方式接入MYSQL集群本身,以兼容单体MYSQL的方式进行连接
2. MYSQL-PROXY本身具备故障检查的功能,可以主动剔除异常的MYSQL实例。
Operator分层
减少Operator本身的臃肿,将组件的运维功能独立,使用接口调用。