kubernetes学习笔记26:存储etcd
etcd是一个分布式,可靠的key-value存储系统,etcd集群通常有3个或5个节点组成,之间通过raft一致性算法进行协同,算法会选举主节点作为leader,由leader负责数据的同步和数据分发,当leader出现故障会选举另一个节点作为leader,并重新完成数据同步呢分发。
在整个架构中有一个概念quorum=(n+1)/2,只要有这个数量的节点存活,etcd就可以继续提供服务,允许有部分节点故障。
etcd给客户提供简单接口访问,用户通过客户端访问,或者http方式(类似curl命令)访问,它的存储理解为有序的map,以key-value形式存储。etcd为方便客户订阅资料数据,支持watch机制,我们通过watch实时拿到etcd中数据增量更新,保持与etcd数据同步。etcd接口分类:put/delete,get(支持单个key查询,也支持范围查询,左闭右开,也支持带前缀的查询),watch(支持单个key,也支持带前缀的key),transactions(if/then/else ops).commit,leases(grant,revoke,keepalive)。
etcd数据版本号叫term,当leader节点发生故障时或者重启时或者网络问题term加1,第二个版本号叫revision,代表全局版本号,当数据发生变更,包括创建,删除,修改,revision就好加1,这样实现了数据支持mvcc功能和watch功能。
第三个版本号create_revision,就是key-value创建时的版本号,mod_revision就是数据被操作时的版本号,version就是计数器,表示被修改了多少次。
etcd中所有数据存储在b+tree中,b+tree保存在磁盘中,维护着revision到value关系,并通过mmap方式映射到内存用来查询,客户端通过版本号revision查询数据的时候,可以用b+tree直接返回数据,通过watch订阅数据的时候,通过版本号revision,遍历这个b+tree拿到所有数据更新,当然etcd还维护一个b+tree,它管理着key到revision映射关系,当需要通过key查询数据的时候,通过另一个b+tree,把key翻译成revision,这个revision是最新的版本号,再通过之前的b+tree获取到value,这样就满足不同的查询需求。
当然为了应对磁盘数据增长,etcd周期性运行一个compaction来清理历史数据。
mini-transactions可以理解为一段if-else程序,在etcd内部会保证事务一致性,也就是说if操作的所有比较条件,其看到的视图一定是一致的,同时它能确保在争执条件中,多个操作的原子性不会出现etcd仅执行一半的情况。
k8s正是通过etcd事务机制保证多个k8sapi server对同样一个数据修改的一致性。
lease是分布式系统常见概念叫租约,etcd的key也有租约,到期了之后在某一个时间点就会被etcd自动清理掉,如果希望永不过期,调用keepalive方法,与etcd保持不断的续约。
etcd支持多个key绑定到同一个lease租约上。etcd使用场景:k8s状态数据元数据存储,service discovery(名字服务,资源注册,存活性检查。使得API网关能够通过etcd及时感知后端进程地址,这样后端地址发生变更时,会重新注册到etcd中,API网关及时感知新的集群地址,同时etcd提供lease租约操作,及时感知进程状态变化,进程死掉,网关及时感知,从而将流量自动切换到其他进程,而且网关也是无状态的,它可以水平扩展服务更多客户。同时支持上万个后端进程节点),leader election(master-slave模式,首先选主,然后把主节点注册IP地址),并发控制(相当于Java中的concurrency的实现方式executorservice,支持分布式信号量,自动踢出故障节点,存储进程的执行状态)。