文章目录
- 0. 前言
- 1. ETCD的概念和设计
- 2.ETCD的命令示例
- 查看ETCD的版本信息
- 列出ETCD集群中的成员
- 检查ETCD集群的健康状态
- 获取指定key的值
- 设置指定key的值
- 删除指定key及其对应的值
- 监控指定key的变化
- 将ETCD的数据备份到指定文件中
- 3. ETCD的使用场景
- 4. ETCD的优缺点
- 5. 配置文件示例
- 6. Etcd对比Redis核心有点
- 其他维度对比
- 6. Spring boot 集成etcd实例
- 6.1. 添加Maven依赖
- 6.2. 配置Etcd连接信息
- 6.3. 注入EtcdClient
- 6.4. 使用Etcd进行配置管理
- 6.5. 启用配置刷新
- 7.参考资料
0. 前言
Etcd是一个开源的、高可用的、分布式的键值存储系统,可以用于存储关键的配置数据、服务发现、服务注册等。它使用Raft一致性算法来保证数据的一致性,并使用分布式锁机制来实现并发控制。Etcd支持HTTP API和gRPC API,提供了多种客户端库,可以方便地与各种编程语言进行集成。在云原生应用和微服务架构中,Etcd被广泛应用于服务发现、配置管理、分布式锁等场景。本文将介绍Etcd的原理、应用场景和使用方法,帮助读者更好地理解和应用Etcd。
1. ETCD的概念和设计
ETCD是一个分布式键值存储系统,类似于一个分层的键值对,其中键和值都是字符串类型。ETCD将所有数据都存储为键值对,支持将键值对组织成层次结构,目录是一种特殊的键,可以包含其他键值对或子目录。
ETCD的核心概念包括:
- 键值对:ETCD中的数据都以键值对的形式进行存储,其中键和值都是字符串类型。
- 目录:ETCD支持将键值对组织成层次结构,目录是一种特殊的键,可以包含其他键值对或子目录。
- 事务:ETCD支持原子性的事务操作,可以一次性执行多个读写操作,保证数据的一致性。
- 触发器:ETCD支持对键值对的修改进行监控,并在发生变化时触发相应的操作。
ETCD使用Raft算法来保证数据一致性和高可用性,Raft是一种分布式共识算法,可以保证多个节点之间的数据一致性。ETCD还使用gRPC协议进行通信,提供了高效的数据传输和处理能力。
2.ETCD的命令示例
以下是一些常用的ETCD命令的详细解释:
查看ETCD的版本信息
命令:
etcdctl version
执行结果:
etcdctl version: 3.5.0
API version: 3.5
列出ETCD集群中的成员
命令:
etcdctl member list
执行结果:
c7a5d5c9f3a7d6f4, started, etcd1, https://192.168.1.101:2380, https://192.168.1.101:2379, false
d9f0a9b8c7b6a5f4, started, etcd2, https://192.168.1.102:2380, https://192.168.1.102:2379, false
e8f9b8a7d6c5b4a3, started, etcd3, https://192.168.1.103:2380, https://192.168.1.103:2379, false
检查ETCD集群的健康状态
命令:
etcdctl cluster-health
执行结果:
member c7a5d5c9f3a7d6f4 is healthy: got healthy result from https://192.168.1.101:2379
member d9f0a9b8c7b6a5f4 is healthy: got healthy result from https://192.168.1.102:2379
member e8f9b8a7d6c5b4a3 is healthy: got healthy result from https://192.168.1.103:2379
cluster is healthy
获取指定key的值
命令:
etcdctl get key
执行结果:
value
设置指定key的值
命令:
etcdctl put key value
执行结果:
OK
删除指定key及其对应的值
命令:
etcdctl del key
执行结果:
1
监控指定key的变化
命令:
etcdctl watch key
执行结果:
watching key for changes...
将ETCD的数据备份到指定文件中
命令:
etcdctl backup file
执行结果:
{"header":{"cluster_id":1234567890123456789,"member_id":1234567890123456789,"revision":1234567890,"raft_term":1234}}
{"key":"L3Zhci93d3cva...."}
注意:上述命令的结果中,$符号表示命令行提示符,不属于命令的一部分。
3. ETCD的使用场景
ETCD作为一个分布式键值存储系统,不仅可以存储和管理数据,还可以帮助开发人员实现各种分布式应用场景,包括服务发现、配置管理、分布式锁和选举算法等。这些功能可以大大简化分布式系统的开发和维护工作,提高系统的可用性和稳定性。
-
服务发现
ETCD可以帮助开发人员轻松发现各种服务,并提供相应的负载均衡策略,以确保服务的高可用性和稳定性。通过将服务注册到ETCD中,其他服务或客户端可以通过查询ETCD获取服务的地址和端口信息,以便进行调用。此外,ETCD还支持基于服务标签的服务发现,可以根据不同的标签对服务进行分类和过滤,以便更好地管理和使用服务。
-
配置管理
ETCD可以帮助开发人员集中管理和维护各种配置信息,包括数据库连接信息、服务端口等。通过将配置信息存储在ETCD中,可以实现统一的配置管理和版本控制,以便更好地维护和更新配置信息。此外,ETCD还支持配置变更通知功能,可以在配置信息发生变更时自动通知相关服务或客户端,以便及时更新配置信息。
-
分布式锁
ETCD可以帮助开发人员实现分布式锁,以确保多个节点之间的数据一致性和互斥性。通过使用ETCD提供的分布式锁机制,可以在分布式环境中实现数据的原子性操作,避免多个节点之间的竞争和冲突。此外,ETCD还支持租约机制,可以设置锁的过期时间和自动续约等功能,以便更好地管理和使用分布式锁。
-
选举算法
ETCD可以帮助开发人员实现分布式选举算法,以确保各个节点之间的数据一致性。通过使用ETCD提供的选举算法,可以在分布式环境中实现主从节点的切换和数据同步,以便更好地管理和维护分布式系统。此外,ETCD还支持基于租约的选举机制,可以在节点失效或网络分区发生时自动进行主从切换,以保证数据的可用性和一致性。
4. ETCD的优缺点
ETCD作为一个分布式键值存储系统,具有许多优点和缺点。在使用ETCD时需要考虑实际需求和限制,以便更好地利用其优势和避免其缺点。
优点 | 缺点 |
---|---|
高可用性:ETCD使用Raft算法来保证数据的一致性和高可用性。 | 对于小规模应用来说,ETCD可能会带来额外的复杂性和开销。 |
分布式事务:ETCD支持原子性的事务操作,可以一次性执行多个读写操作,保证数据的一致性。 | ETCD需要部署在集群中的多个节点上,如果节点之间的网络连接不稳定,可能会影响数据的一致性和可用性。 |
快速响应:ETCD使用gRPC协议进行通信,提供了高效的数据传输和处理能力。 | ETCD的存储能力和性能受到硬件和网络环境的限制。在处理大量数据或高并发请求时,可能需要增加节点数量或升级硬件设备。 |
简单易用:ETCD提供了简单易用的命令行工具和API,可以方便地管理和维护数据。 |
5. 配置文件示例
ETCD的配置项很多
# etcd 配置文件示例
# 集群名称
name = "etcd-cluster"
# 监听客户端请求的地址,可以指定多个地址
listen-client-urls = "http://0.0.0.0:2379,http://0.0.0.0:4001"
# 监听同伴节点请求的地址,可以指定多个地址
listen-peer-urls = "http://0.0.0.0:2380,http://0.0.0.0:7001"
# 数据目录
data-dir = "/var/lib/etcd"
# 初始集群节点配置,可以指定多个节点
initial-cluster = "etcd-1=http://10.0.0.1:2380,etcd-2=http://10.0.0.2:2380,etcd-3=http://10.0.0.3:2380"
# 初始集群状态
initial-cluster-state = "new"
# 自动压缩模式
auto-compaction-mode = "periodic"
# 自动压缩的保留时间
auto-compaction-retention = "1h"
# 自动压缩的大小
auto-compaction-size = "100MB"
# 启用TLS证书认证
client-transport-security = {
cert-file = "/path/to/client/cert.pem",
key-file = "/path/to/client/key.pem",
trusted-ca-file = "/path/to/ca.pem",
client-cert-auth = true,
}
# 启用同伴节点TLS证书认证
peer-transport-security = {
cert-file = "/path/to/peer/cert.pem",
key-file = "/path/to/peer/key.pem",
trusted-ca-file = "/path/to/ca.pem",
client-cert-auth = true,
}
# 是否启用TLS客户端身份验证
client-cert-auth = true
# 证书和密钥文件路径
cert-file = "/path/to/server/cert.pem"
key-file = "/path/to/server/key.pem"
# 证书颁发机构CA证书路径
trusted-ca-file = "/path/to/ca.pem"
# 证书吊销列表路径
crl-file = "/path/to/crl.pem"
# 客户端证书过期时间
client-cert-allowed-cn = ["example.com", "example.org"]
client-cert-max-epoch = 100
client-cert-min-epoch = 10
# 启用安全客户端端口
client-security = {
ca-file = "/path/to/ca.pem",
cert-file = "/path/to/client/cert.pem",
key-file = "/path/to/client/key.pem",
client-cert-auth = true,
}
# 启用安全同伴节点端口
peer-security = {
ca-file = "/path/to/ca.pem",
cert-file = "/path/to/peer/cert.pem",
key-file = "/path/to/peer/key.pem",
client-cert-auth = true,
}
# 集群内部通信安全策略
peer-client-cert-auth = true
peer-trusted-ca-file = "/path/to/ca.pem"
peer-cert-file = "/path/to/etcd-peer.pem"
peer-key-file = "/path/to/etcd-peer-key.pem"
peer-cert-allowed-cn = ["etcd-1", "etcd-2", "etcd-3"]
peer-cert-max-epoch = 100
peer-cert-min-epoch = 10
# 启用TLS客户端身份验证
client-cert-auth = true
# 集群内部通信安全策略(v3.4.0+)
peer-cert-allowed-san = ["etcd-1", "etcd-2", "etcd-3"]
# 集群内部通信安全策略(v3.5.0+)
peer-cert-allowed-dns-names = ["etcd-1", "etcd-2", "etcd-3"]
# 集群内部通信安全策略(v3.6.0+)
peer-cert-allowed-email-addresses = ["etcd-1@example.com", "etcd-2@example.com", "etcd-3@example.com"]
# TLSv1.0协议启用状态
tls-min-version = "TLSv1.0"
# TLSv1.2协议启用状态
tls-max-version = "TLSv1.2"
# HTTP/2协议启用状态
http2 = true
# HTTP/2流最大并发数
http2-max-concurrent-streams = 1000
# HTTP/2流最大队列大小
http2-max-requests = 1000
# HTTP/2连接最大并发数
http2-max-sessions = 1000
# 代理协议启用状态
proxy-protocol = true
# 健康检查端口
healthcheck-port = 2381
# 健康检查时的超时时间
healthcheck-timeout = "5s"
# 健康检查时的间隔时间
healthcheck-interval = "10s"
# 健康检查时的容忍失败次数
healthcheck-fails = 3
# 是否启用raft协议
enable-v2 = true
# 是否启用v3版本API
enable-v3 = true
# 是否启用v3版本自动同步
auto-sync = true
# 是否启用v3版本自动压缩
auto-compaction-retention = "1h"
auto-compaction-size = "100MB"
# 是否开启v3版本后台压缩
backend-batch-limit = 1000
backend-batch-interval = "5s"
# 是否启用v3版本的限流措施
quota-backend-bytes = "10GB"
# 是否启用v3版本的统计信息
enable-v3-stats = true
# 是否启用v3版本的流量控制
enable-v3-flow-control = true
# 是否启用v3版本的预写日志
wal-dir = "/var/lib/etcd/wal"
wal-enable-sync = true
wal-flush-interval = "5s"
# 是否启用v3版本的备份和恢复
backup-dir = "/var/lib/etcd/backup"
# 是否启用v3版本的故障转移
enable-v3-failover = true
# 是否启用v3版本的自动选举
auto-election = true
# 是否启用v3版本的快照
snapshot-count = 10000
snapshot-interval = "30m"
# 是否启用v3版本的预选
pre-vote = true
# 是否启用v3版本的后选
post-vote = true
# 是否启用v3版本的存储
storage-backend = "v3io"
# 是否启用v3版本的存储区域
storage-region = "us-west-2"
# 是否启用v3版本的存储桶
storage-bucket = "etcd-backup"
# 是否启用v3版本的存储密钥
storage-access-key = "XXXXXXXXXXXXXXXXXXXX"
# 是否启用v3版本的存储密码
storage-secret-key = "XXXXXXXXXXXXXXXXXXXX"
# 是否启用v3版本的存储加密
storage-encryption = true
# 是否启用v3版本的存储压缩
storage-compression = true
# 是否启用v3版本的存储版本控制
storage-versioning = true
# 是否启用v3版本的存储访问控制
storage-acl = "private"
# 是否启用v3版本的存储缓存
storage-cache = "memcached"
# 是否启用v3版本的存储缓存地址
storage-cache-addresses = ["127.0.0.1:11211"]
# 是否启用v3版本的存储缓存超时时间
storage-cache-timeout = "5s"
# 是否启用v3版本的存储缓存大小
storage-cache-size = "100MB"
# 是否启用v3版本的存储缓存压缩
storage-cache-compression = true
# 是否启用v3版本的存储缓存最大值
storage-cache-max-value-size = "1MB"
# 是否启用v3版本的存储缓存清理间隔
storage-cache-eviction-interval = "10s"
# 是否启用v3版本的存储缓存清理最大值
storage-cache-eviction-max-items = 1000
# 是否启用v3版本的存储缓存清理策略
storage-cache-eviction-policy = "LRU"
# 是否启用v3版本的存储缓存清理大小
storage-cache-eviction-size = "100MB"
6. Etcd对比Redis核心有点
- 支持ACID事务,可以保证数据的一致性和完整性。
- 支持服务发现、配置管理、分布式锁、选举算法等分布式应用场景。
- 支持TLS加密和访问控制,可以保证数据的安全性和隐私性。
- 支持多种API和语言,例如gRPC、RESTful API、Go、Java等。
- 支持水平扩展和垂直扩展,可以根据实际需求灵活扩展。
其他维度对比
维度 | ETCD | Redis |
---|---|---|
数据模型 | 键值存储 | 键值存储 |
数据类型 | 支持字符串、列表、集合、字典等数据类型 | 支持字符串、列表、集合、有序集合等数据类型 |
数据一致性 | 采用Raft算法保证数据的一致性和高可用性,可应用于分布式场景 | 采用主从同步和哨兵机制保证数据的一致性和高可用性,可应用于缓存场景 |
数据持久化 | 支持持久化和快照机制,可以将数据保存到磁盘中,数据可靠性高 | 支持持久化和快照机制,可以将数据保存到磁盘中,数据可靠性高 |
分布式支持 | 支持集群模式,可以部署在多个节点上,支持数据分片和复制等特性 | 支持主从复制和哨兵机制,可以部署在多个节点上,支持数据分片和复制等特性 |
性能 | 支持高并发和大规模数据处理,适合于分布式场景 | 支持高并发和大规模数据处理,适合于缓存场景 |
功能 | 支持服务发现、配置管理、分布式锁、选举算法等分布式应用场景 | 支持缓存、消息队列、计数器、发布/订阅等缓存应用场景 |
API和语言支持 | 支持多种API和语言,例如gRPC、RESTful API、Go、Java等 | 支持多种API和语言,例如Redis协议、Java、Python等 |
数据库支持 | 支持嵌入式数据库和外部数据库,例如SQLite、MySQL等 | 不支持外部数据库,但支持AOF和RDB持久化机制 |
事务 | 支持ACID事务,可以保证数据的一致性和完整性 | 不支持ACID事务,但支持MULTI/EXEC、WATCH等机制 |
安全 | 支持TLS加密和访问控制,可以保证数据的安全性和隐私性 | 支持密码认证和网络隔离等机制,可以保证数据的安全性和隐私性 |
可扩展性 | 支持水平扩展和垂直扩展,可以根据实际需求灵活扩展 | 支持水平扩展和垂直扩展,可以根据实际需求灵活扩展 |
社区活跃度 | 开源社区活跃度高,更新迭代频繁,支持多种开源项目和组件 | 开源社区活跃度高,更新迭代频繁,支持多种开源项目和组件 |
6. Spring boot 集成etcd实例
6.1. 添加Maven依赖
在pom.xml文件中添加以下依赖:
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-etcd</artifactId>
<version>3.0.3</version>
</dependency>
6.2. 配置Etcd连接信息
在application.properties文件中添加Etcd连接信息:
spring.cloud.etcd.enabled=true
spring.cloud.etcd.uris=http://localhost:2379
6.3. 注入EtcdClient
在需要使用Etcd的地方,注入EtcdClient:
import org.springframework.cloud.etcd.config.EtcdClient;
import org.springframework.stereotype.Component;
@Component
public class MyComponent {
@Autowired
private EtcdClient etcdClient;
public void doSomething() {
// 使用etcdClient进行操作
}
}
6.4. 使用Etcd进行配置管理
在Etcd中创建一个key-value对:
$ etcdctl put /config/myapp/foo bar
在Spring Boot中使用该key:
import org.springframework.beans.factory.annotation.Value;
import org.springframework.cloud.context.config.annotation.RefreshScope;
import org.springframework.stereotype.Component;
@Component
@RefreshScope
public class MyComponent {
@Value("${foo}")
private String foo;
public void doSomething() {
// 使用foo进行操作
}
}
6.5. 启用配置刷新
如果需要在Etcd中更新配置后自动刷新Spring Boot中的配置,需要在application.properties文件中添加以下配置:
spring.cloud.etcd.config.refresh.enabled=true
spring.cloud.etcd.config.refresh.interval=5
其中,refresh.interval配置项指定了配置刷新的时间间隔(单位为秒)。
7.参考资料
- 官方文档 https://etcd.io/docs/v3.5/quickstart/
- GitHub仓库:https://github.com/etcd-io/etcd
- 官方论坛:https://discuss.etcd.io/
- 分布式键值存储系统—Etcd