bboyjing's blog

Zookeeper学习笔记九【Zookeeper典型使用场景之配置中心】

假设一个开发场景,用到三套环境dev、test和prod,把配置信息存放到Zookeeper,各个机器通过自身的hostname来获取对应的信息。下面就按照这个思路一步步来实现这样一个简单的配置中心。

将数据写入zookeeper

直接通过zkcli简单地写入几条数据,数据的分布如下:

  • configuration
    • dev
      • spring.datasource.url=jdbc:mysql://dev.didadu.cn:3306:test
      • spring.datasource.name=dev
      • spring.datasource.password=devPwd
    • test
      • spring.datasource.url=jdbc:mysql://test.didadu.cn:3306:test
      • spring.datasource.name=test
      • spring.datasource.password=testPwd
    • prod
      • spring.datasource.url=jdbc:mysql://prod.didadu.cn:3306:test
      • spring.datasource.name=teprodst
      • spring.datasource.password=prodPwd
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
cd /opt/zookeeper-3.4.9
zookeeper-3.4.9 server1/bin/zkCli.sh
create /configuration ""
create /configuration/dev ""
create /configuration/test ""
create /configuration/prod ""
create /configuration/dev/spring.datasource.url jdbc:mysql://dev.didadu.cn:3306:test
create /configuration/dev/spring.datasource.name dev
create /configuration/dev/spring.datasource.password devPwd
create /configuration/test/spring.datasource.url jdbc:mysql://test.didadu.cn:3306:test
create /configuration/test/spring.datasource.name test
create /configuration/test/spring.datasource.password testPwd
create /configuration/prod/spring.datasource.url jdbc:mysql://prod.didadu.cn:3306:test
create /configuration/prod/spring.datasource.name prod
create /configuration/prod/spring.datasource.password prodPwd

新建测试模块

zookeeper-sample项目中新建模块configuration,没有使用SpringBoot提供的Config Server,只是简单的实现了下,核心代码如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
@Configuration
public class Configurer{
@Bean
public String zookeeperLoader() throws Exception {
String hostname = InetAddress.getLocalHost().getHostName().split("\\.")[0];
CuratorFramework zkClient = CuratorFrameworkFactory.builder()
.connectString("localhost:2181,localhost:2182,localhost:2183")
.sessionTimeoutMs(5000)
.retryPolicy(new ExponentialBackoffRetry(1000, 3)).build();
zkClient.start();
StringBuilder basePath = new StringBuilder("/configuration/").append(hostname).append("/");
StringBuilder urlPath = new StringBuilder(basePath).append("spring.datasource.url");
System.out.println(new String(zkClient.getData().forPath(urlPath.toString())));
StringBuilder namePath = new StringBuilder(basePath).append("spring.datasource.name");
System.out.println(new String(zkClient.getData().forPath(namePath.toString())));
StringBuilder pwdPath = new StringBuilder(basePath).append("spring.datasource.password");
System.out.println(new String(zkClient.getData().forPath(pwdPath.toString())));
zkClient.close();
return "ok";
}
}

修改hostname并测试

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
#修改/etc/hosts,添加如下内容:
127.0.0.1 dev.didadu.cn
127.0.0.1 test.didadu.cn
127.0.0.1 prod.didadu.cn
#临时修改hostname
sudo hostname dev.didadu.cn
输出:
jdbc:mysql://dev.didadu.cn:3306:test
dev
devPwd
#再次修改hostname
sudo hostname prod.didadu.cn
输出:
jdbc:mysql://prod.didadu.cn:3306:test
prod
prodPwd

结果证明实现了当初假设的场景,这个只是简单示例,实际项目还得按需优化。