Spring Boot 读取 ZooKeeper (ZK) 属性的总结指南,涵盖配置定义、绑定、初始化和使用:
1. 在配置文件中定义 ZK 属性
在 application.properties
或 application.yml
中添加 ZK 相关配置:
application.properties
# 单源配置示例
zookeeper.source.default.rootnode=/democonfig
zookeeper.source.default.servers=192.168.124.1:2181,192.168.124.2:2181
zookeeper.source.default.acls=root:iiot!@#zk$
# 多源配置示例(可选)
zookeeper.source.backup.rootnode=/backup-config
zookeeper.source.backup.servers=192.168.124.3:2181
application.yml
zookeeper:
source:
default:
rootnode: /democonfig
servers: 192.168.124.1:2181,192.168.124.2:2181
acls: root:iiot!@#zk$
backup:
rootnode: /backup-config
servers: 192.168.124.3:2181
2. 创建配置类绑定属性
使用 @ConfigurationProperties
绑定 ZK 配置:
import lombok.Getter;
import lombok.Setter;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.stereotype.Component;
import java.util.Map;
@Component
@ConfigurationProperties(prefix = "zookeeper")
@Getter
@Setter
public class ZookeeperConfig {
private Map<String, SourceProperties> source = new HashMap<>();
@Getter
@Setter
public static class SourceProperties {
private String rootnode;
private String servers;
private String acls;
}
}
3. 初始化 ZK 客户端
在 Spring 容器中初始化 ZK 客户端,确保配置已注入:
import org.apache.zookeeper.ZooKeeper;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import java.io.IOException;
@Component
public class ZookeeperClient {
private static final int SESSION_TIMEOUT = 5000;
private final ZooKeeper zooKeeper;
@Autowired
public ZookeeperClient(ZookeeperConfig zookeeperConfig) {
try {
// 获取默认源配置
ZookeeperConfig.SourceProperties source = zookeeperConfig.getSource().get("default");
if (source == null) {
throw new IllegalArgumentException("ZooKeeper source 'default' not configured");
}
this.zooKeeper = new ZooKeeper(
source.getServers(),
SESSION_TIMEOUT,
null
);
} catch (IOException e) {
throw new RuntimeException("Failed to connect to ZooKeeper", e);
}
}
public ZooKeeper getZooKeeper() {
return zooKeeper;
}
}
4. 使用配置属性
在任意 Spring Bean 中注入 ZookeeperConfig
或 ZookeeperClient
,并读取属性:
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
@Service
public class MyService {
@Autowired
private ZookeeperConfig zookeeperConfig;
@Autowired
private ZookeeperClient zookeeperClient;
public void printZkConfig() {
// 直接读取配置
ZookeeperConfig.SourceProperties source = zookeeperConfig.getSource().get("default");
System.out.println("ZK Root Node: " + source.getRootnode());
System.out.println("ZK Servers: " + source.getServers());
// 通过客户端使用 ZK 连接
ZooKeeper zk = zookeeperClient.getZooKeeper();
System.out.println("ZK Session ID: " + zk.getSessionId());
}
}
5. 多源配置支持
如果需要切换不同的 ZK 源(如 default
和 backup
),可扩展 ZookeeperClient
:
@Component
public class ZookeeperClient {
private final Map<String, ZooKeeper> clients = new HashMap<>();
@Autowired
public ZookeeperClient(ZookeeperConfig zookeeperConfig) {
zookeeperConfig.getSource().forEach((name, config) -> {
try {
clients.put(name, new ZooKeeper(
config.getServers(),
SESSION_TIMEOUT,
null
));
} catch (IOException e) {
throw new RuntimeException("Failed to connect to ZooKeeper source: " + name, e);
}
});
}
public ZooKeeper getClient(String sourceName) {
return clients.getOrDefault(sourceName, clients.get("default"));
}
}
6. 注意事项
- 配置文件路径:确保
application.properties
或application.yml
在类路径下(src/main/resources
)。 - 属性键命名规则:
- 使用
kebab-case
(如zookeeper.source.default.servers
)。 - 绑定到
@ConfigurationProperties
时,自动转换为驼峰命名(如source.default.servers
→source.get("default").getServers()
)。
- 使用
- 优先级:
- 系统属性(
-D
参数) > 配置文件 > 代码默认值。
- 系统属性(
- 异常处理:在 ZK 客户端初始化时捕获
IOException
,并提供友好的错误提示。 - 单例与依赖注入:避免在 Spring 容器初始化前手动创建
ZookeeperClient
(如在main
方法中),应通过@Autowired
注入。
对比:传统属性读取 vs Spring Boot 原生方式
方式 | 优点 | 缺点 |
---|---|---|
传统 PropertyConfig |
简单直接,无需 Spring 依赖 | 不支持自动刷新、类型安全、配置校验 |
Spring Boot @ConfigurationProperties |
类型安全、支持校验、自动刷新(需配置) | 需要定义配置类,学习成本略高 |
通过以上步骤,你可以在 Spring Boot 中优雅地读取和管理 ZooKeeper 的配置属性。