1. Namespace
1.1. 什么是 Namespace
Namespace 是配置项的集合, 类似于一个配置文件的概念.
Apollo 在创建项目的时候, 都会默认创建一个 "application" 的 Namespace. 顾名思义,"application" 是给应用自身使用的, 熟悉 Spring Boot 的同学都知道, Spring Boot 项目都有一个默认配置文件 application.YAML. 在这里 application.properties 就等同于 "application" 的 Namespace. 对于 90% 的应用来说,"application" 的 Namespace 已经满足日常配置使用场景了.
1.2. 客户端如何获取 Namespace
2. 重新构建
Git clone https://github.com/ctripcorp/apollo.git
修改完代码后调用 ${YOUR-WORKSPACE}/apollo/script/build.sh
执行完 bulid.sh 以后会再各个项目的 target 目录下生产 zip 包
于是, 我们就可以得到以下三个包
- apollo-adminservice-1.5.0-SNAPSHOT-GitHub.zip
- apollo-configservice-1.5.0-SNAPSHOT-GitHub.zip
- apollo-portal-1.5.0-SNAPSHOT-GitHub.zip
解压后修改数据库连接地址后, 启动
3. 增加可用的环境
前面我们通过执行初始化脚本来初始化数据库, 在脚本的最后插入了几条初始化数据
因此, 可以通过修改 apollo.portal.envs 字段的值来添加激活的 (可用的) 环境. 直接修改初始化脚本, 或者脚本执行完以后再执行 update. 例如:
- UPDATE ApolloPortalDB.ServerConfig SET value = 'local,dev,test,prod' WHERE id = 1;
- UPDATE ApolloPortalDB.ServerConfig SET value = '[{"orgId":"TEC","orgName":" 技术部 "}]' WHERE id = 2;
访问 http://localhost:8070/ (apollo/admin)
本例中, 增加了 TEST 环境, 还增加了一个 Namespace
4. API 使用方式
API 方式是最简单, 高效使用 Apollo 配置的方式, 不依赖 Spring 框架即可使用.
4.1. 获取默认 namespace 的配置
- // config instance is singleton for each namespace and is never null
- Config config = ConfigService.getAppConfig();
- String someKey = "someKeyFromDefaultNamespace";
- String someDefaultValue = "someDefaultValueForTheKey";
- String value = config.getProperty(someKey, someDefaultValue);
通过上述的 config.getProperty 可以获取到 someKey 对应的实时最新的配置值.
另外, 配置值从内存中获取, 所以不需要应用自己做缓存.
4.2. 监听配置变化事件
监听配置变化事件只在应用真的关心配置变化, 需要在配置变化时得到通知时使用, 比如: 数据库连接串变化后需要重建连接等.
如果只是希望每次都取到最新的配置的话, 只需要按照上面的例子, 调用 config.getProperty 即可.
- // config instance is singleton for each namespace and is never null
- Config config = ConfigService.getAppConfig();
- config.addChangeListener(new ConfigChangeListener() {
- @Override
- public void onChange(ConfigChangeEvent changeEvent) {
- System.out.println("Changes for namespace" + changeEvent.getNamespace());
- for (String key : changeEvent.changedKeys()) {
- ConfigChange change = changeEvent.getChange(key);
- System.out.println(String.format("Found change - key: %s, oldValue: %s, newValue: %s, changeType: %s", change.getPropertyName(), change.getOldValue(), change.getNewValue(), change.getChangeType()));
- }
- }
- });
4.3. 获取公共 Namespace 的配置
- String somePublicNamespace = "CAT";
- Config config = ConfigService.getConfig(somePublicNamespace);
- String someKey = "someKeyFromPublicNamespace";
- String someDefaultValue = "someDefaultValueForTheKey";
- String value = config.getProperty(someKey, someDefaultValue);
4.4. 获取非 properties 格式 namespace 的配置
apollo-client 1.3.0 版本开始对 YAML/YAML 做了更好的支持, 使用起来和 properties 格式一致.
- Config config = ConfigService.getConfig("application.yml");
- String someKey = "someKeyFromYmlNamespace";
- String someDefaultValue = "someDefaultValueForTheKey";
- String value = config.getProperty(someKey, someDefaultValue);
5. 实时动态调整日志级别
这个功能很实用
引入依赖
- <groupId>com.ctrip.framework.apollo</groupId>
- <artifactId>apollo-client</artifactId>
- <version>1.4.0</version>
- </dependency>
日志级别配置
- package com.cjs.example.config;
- import com.ctrip.framework.apollo.Config;
- import com.ctrip.framework.apollo.model.ConfigChange;
- import com.ctrip.framework.apollo.model.ConfigChangeEvent;
- import com.ctrip.framework.apollo.spring.annotation.ApolloConfig;
- import com.ctrip.framework.apollo.spring.annotation.ApolloConfigChangeListener;
- import lombok.extern.slf4j.Slf4j;
- import org.springframework.beans.factory.annotation.Autowired;
- import org.springframework.boot.logging.LogLevel;
- import org.springframework.boot.logging.LoggingSystem;
- import org.springframework.context.annotation.Configuration;
- import org.springframework.util.StringUtils;
- import java.util.Set;
- /**
- * @author ChengJianSheng
- * @date 2019-05-31
- */
- @Slf4j
- @Configuration
- public class LoggerConfig {
- private static final String LOGGER_TAG = "logging.level.";
- /**
- * 注入默认的命名空间配置
- */
- @ApolloConfig
- private Config config;
- @Autowired
- private LoggingSystem loggingSystem;
- @ApolloConfigChangeListener
- private void onChange(ConfigChangeEvent configChangeEvent) {
- System.out.println("配置发生变化");
- System.out.println("Changes for namespace" + configChangeEvent.getNamespace());
- for (String key : configChangeEvent.changedKeys()) {
- ConfigChange change = configChangeEvent.getChange(key);
- System.out.println(String.format("Found change - key: %s, oldValue: %s, newValue: %s, changeType: %s", change.getPropertyName(), change.getOldValue(), change.getNewValue(), change.getChangeType()));
- }
- Set<String> keyNames = config.getPropertyNames();
- for (String key : keyNames) {
- if (StringUtils.isEmpty(key)) {
- continue;
- }
- if (!key.startsWith(LOGGER_TAG)) {
- continue;
- }
- String loggerName = key.replace(LOGGER_TAG, "");
- String strLevel = config.getProperty(key, "info");
- LogLevel level = LogLevel.valueOf(strLevel.toUpperCase());
- loggingSystem.setLogLevel(loggerName, level);
- log.info("{}:{}", key, strLevel);
- }
- }
- }
- application.properties
- server.port=9000
- App.id=1001
- env=LOCAL
- apollo.meta=http://localhost:8080
- apollo.cacheDir=/Users/chengjiansheng/data
- apollo.Bootstrap.enabled=true
修改配置
5. 工程结构
https://github.com/chengjiansheng/apollo-demo
6. 文档
Apollo 核心概念之 "Namespace"
分布式部署指南
Apollo 配置中心的各种使用场景和示例代码
Java 客户端使用指南
部署 & 开发遇到的常见问题
Apollo 使用指南
来源: https://www.cnblogs.com/cjsblog/p/10956364.html