前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >nacos源码-怎么更新配置

nacos源码-怎么更新配置

原创
作者头像
伍六七AI编程
修改2020-12-28 18:04:47
9740
修改2020-12-28 18:04:47
举报
文章被收录于专栏:preparedprepared

界面操作更新nacos配置,然后使用charles抓包工具,抓到请求

代码语言:txt
复制
http://ip:port/nacos/v1/cs/configs?accessToken=eyJhbGciOiJIUzI1NiJ9.eyJzdWIiOiJuYWNvcyIsImV4cCI6MTYwNTE2Nzc5N30.NNcnIivPaMxj3me9FfKY2VHaWnJNVA6GganyWenR6NU
nacos-1.png
nacos-1.png

下载源码

代码语言:txt
复制
https://github.com/alibaba/nacos

找到请求:nacos/v1/cs/configs

Constants.java类中找到

代码语言:txt
复制
public static final String BASE_PATH = "/v1/cs";
public static final String CONFIG_CONTROLLER_PATH = BASE_PATH + "/configs";

找到使用CONFIG_CONTROLLER_PATH的controller请求

代码语言:txt
复制
/**
 * Special controller for soft load client to publish data.
 *
 * @author leiwen
 */
@RestController
@RequestMapping(Constants.CONFIG_CONTROLLER_PATH)
public class ConfigController {

根据请求地址以及参数,定位到请求的方法为publishConfig

代码语言:javascript
复制
/**
 * Adds or updates non-aggregated data.
 *
 * @throws NacosException NacosException.
 */
@PostMapping
@Secured(action = ActionTypes.WRITE, parser = ConfigResourceParser.class)
public Boolean publishConfig(HttpServletRequest request, HttpServletResponse response,
        @RequestParam(value = "dataId") String dataId, @RequestParam(value = "group") String group,
        @RequestParam(value = "tenant", required = false, defaultValue = StringUtils.EMPTY) String tenant,
        @RequestParam(value = "content") String content, @RequestParam(value = "tag", required = false) String tag,
        @RequestParam(value = "appName", required = false) String appName,
        @RequestParam(value = "src_user", required = false) String srcUser,
        @RequestParam(value = "config_tags", required = false) String configTags,
        @RequestParam(value = "desc", required = false) String desc,
        @RequestParam(value = "use", required = false) String use,
        @RequestParam(value = "effect", required = false) String effect,
        @RequestParam(value = "type", required = false) String type,
        @RequestParam(value = "schema", required = false) String schema) throws NacosException {
    
    final String srcIp = RequestUtil.getRemoteIp(request);
    final String requestIpApp = RequestUtil.getAppName(request);
    srcUser = RequestUtil.getSrcUserName(request);
    //check type
    if (!ConfigType.isValidType(type)) {
        type = ConfigType.getDefaultType().getType();
    }
    // check tenant
    // 校验参数的代码
    
    if (AggrWhitelist.isAggrDataId(dataId)) {
        LOGGER.warn("[aggr-conflict] {} attemp to publish single data, {}, {}", RequestUtil.getRemoteIp(request),
                dataId, group);
        throw new NacosException(NacosException.NO_RIGHT, "dataId:" + dataId + " is aggr");
    }
    
    final Timestamp time = TimeUtils.getCurrentTime();
    String betaIps = request.getHeader("betaIps");
    ConfigInfo configInfo = new ConfigInfo(dataId, group, tenant, appName, content);
    configInfo.setType(type);
    if (StringUtils.isBlank(betaIps)) {
        if (StringUtils.isBlank(tag)) {
            persistService.insertOrUpdate(srcIp, srcUser, configInfo, time, configAdvanceInfo, true);
            ConfigChangePublisher
                    .notifyConfigChange(new ConfigDataChangeEvent(false, dataId, group, tenant, time.getTime()));
        } else {
            persistService.insertOrUpdateTag(configInfo, tag, srcIp, srcUser, time, true);
            ConfigChangePublisher.notifyConfigChange(
                    new ConfigDataChangeEvent(false, dataId, group, tenant, tag, time.getTime()));
        }
    } else {
        // beta publish
        persistService.insertOrUpdateBeta(configInfo, betaIps, srcIp, srcUser, time, true);
        ConfigChangePublisher
                .notifyConfigChange(new ConfigDataChangeEvent(true, dataId, group, tenant, time.getTime()));
    }
    ConfigTraceService
            .logPersistenceEvent(dataId, group, tenant, requestIpApp, time.getTime(), InetUtils.getSelfIP(),
                    ConfigTraceService.PERSISTENCE_EVENT_PUB, content);
    return true;
}

逻辑并不复杂,就是判断是新增配置还是修改配置,然后修改或者新增数据库响应信息。

之后通过消息队列通知其他服务,其他服务接收到通知之后,更新配置。

nacos-2.png
nacos-2.png

2 源码值得学习的地方

2.1 构造器注入service

不建议直接使用@Autowired注入,建议使用构造器注入或者getter/setter方法注入。

代码语言:javascript
复制
private final ConfigServletInner inner;

private final PersistService persistService;

private final ConfigSubService configSubService;

@Autowired
public ConfigController(ConfigServletInner configServletInner, PersistService persistService,
        ConfigSubService configSubService) {
    this.inner = configServletInner;
    this.persistService = persistService;
    this.configSubService = configSubService;
}

2.2 判断对向是否为空

可以使用 rt.jar 中的Objects对象的 isNull() 方法。

代码语言:txt
复制
    @Override
    public void insertOrUpdate(String srcIp, String srcUser, ConfigInfo configInfo, Timestamp time,
            Map<String, Object> configAdvanceInfo, boolean notify) {
        if (Objects.isNull(findConfigInfo(configInfo.getDataId(), configInfo.getGroup(), configInfo.getTenant()))) {
            addConfigInfo(srcIp, srcUser, configInfo, time, configAdvanceInfo, notify);
        } else {
            updateConfigInfo(configInfo, srcIp, srcUser, time, configAdvanceInfo, notify);
        }
    }

2.3 插入数据,主键使用雪花算法生成

代码语言:txt
复制
 private void addConfigInfo(final String srcIp, final String srcUser, final ConfigInfo configInfo,
            final Timestamp time, final Map<String, Object> configAdvanceInfo, final boolean notify,
            BiConsumer<Boolean, Throwable> consumer) {
        
        try {
            final String tenantTmp =
                    StringUtils.isBlank(configInfo.getTenant()) ? StringUtils.EMPTY : configInfo.getTenant();
            configInfo.setTenant(tenantTmp);
            
            long configId = idGeneratorManager.nextId(RESOURCE_CONFIG_INFO_ID);
            long hisId = idGeneratorManager.nextId(RESOURCE_CONFIG_HISTORY_ID);
            
            addConfigInfoAtomic(configId, srcIp, srcUser, configInfo, time, configAdvanceInfo);
            String configTags = configAdvanceInfo == null ? null : (String) configAdvanceInfo.get("config_tags");
            
            addConfigTagsRelation(configId, configTags, configInfo.getDataId(), configInfo.getGroup(),
                    configInfo.getTenant());
            insertConfigHistoryAtomic(hisId, configInfo, srcIp, srcUser, time, "I");
            EmbeddedStorageContextUtils.onModifyConfigInfo(configInfo, srcIp, time);
            databaseOperate.blockUpdate(consumer);
        } finally {
            EmbeddedStorageContextUtils.cleanAllContext();
        }
    }

雪花算法实现类SnowFlowerIdGenerator.java

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 2 源码值得学习的地方
    • 2.1 构造器注入service
      • 2.2 判断对向是否为空
        • 2.3 插入数据,主键使用雪花算法生成
        相关产品与服务
        领券
        问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档