zoukankan      html  css  js  c++  java
  • Apollo实现@ConfigurationProperties配置刷新的另一种方式

    背景

    目前apollo官方实现@ConfigurationProperties需要配合使用EnvironmentChangeEvent或RefreshScope(需要引入springCloud-context),考虑一种简单的实现方式如下:

    思路

    监听apollo配置刷新事件,然后通过spring的工具类获取当前配置类的bean实例对象(单例),通过反射将对应改变的配置项注入配置类bean实例。

    代码实现

    @Data
    @Slf4j
    @Configuration
    @ConfigurationProperties
    @EnableApolloConfig
    public class AppConfig {
    
        private Map<String, String> xxConfigMap;
    
        @ApolloConfigChangeListener
        public void onChange(ConfigChangeEvent changeEvent) {
            //this.applicationContext.publishEvent(new EnvironmentChangeEvent(changeEvent.changedKeys()));
       changeEvent.changedKeys().stream().map(changeEvent::getChange).forEach(change -> {
                log.info("Found change - key: {}, oldValue: {}, newValue: {}, changeType: {}", change.getPropertyName(), change.getOldValue(), change.getNewValue(), change.getChangeType());
                String vKey = change.getPropertyName();
                String newValue = change.getNewValue();
                if (vKey.contains(".")) {
                    //取出对应的field 反射重新赋值
                    AppConfig appConfig = SpringContext.getBean(AppConfig.class);
                    try {
                        PropertyDescriptor propertyDescriptor = new PropertyDescriptor(vKey.substring(0, vKey.indexOf(".")), appConfig.getClass());
                        Map<String, String> map = (Map<String, String>) propertyDescriptor.getReadMethod().invoke(appConfig);
                        map.put(vKey.substring(vKey.indexOf(".")+1,vKey.length()), newValue);
                        propertyDescriptor.getWriteMethod().invoke(appConfig, map);
                    } catch (Exception e) {
                        log.error("replace field {} error", vKey);
                    }
                }
            });
        }
    
    
        //测试是否生效
        @PostConstruct
        void test() {
            Executors.newSingleThreadExecutor().submit(() -> {
                while (true) {
                    log.info(xxConfigMap.toString());
                    Thread.sleep(2000);
                }
            });
        }
    }
    

    Reference

    apollo wiki spring-boot集成方式

    =====原文作者博客园----dustyhope,转载请注明出处,谢谢
  • 相关阅读:
    使用eclipse从github导入maven项目
    J2SE 8的Lambda --- Comparator
    J2SE 8的Lambda --- functions
    J2SE 8的Lambda --- 语法
    J2SE 8的流库 --- 收集处理结果
    J2SE 8的流库 --- 转换流, 得到的还是流
    J2SE 8的流库 --- 基本类型流的使用
    J2SE 8的流库 --- 生成流
    Hadoop 3.0 安装
    程序员到底要不要读研,过来人给你几点建议!
  • 原文地址:https://www.cnblogs.com/liwanping/p/11147143.html
Copyright © 2011-2022 走看看