Apollo源码解析——ConfigService配置读取接口(客户端定时拉取接口)

本文解析了Apollo配置服务中ConfigService接口的实现细节,包括客户端配置读取流程、配置更新检查及缓存机制。


一、概述

上文讲了客户端定时轮询的接口,这里我们看下Config Service配置读取的接口的实现。

二、代码流程

1. ConfigController#queryConfig方法

代码很长,但是大体流程就是根据客户端的参数从服务端查询出来最新的配置,然后根据clientSideReleaseKey和服务端的ReleaseKey进行比较,判断配置有没有更新,这里重点看下loadConfig方法,怎么加载最新的配置

  @GetMapping(value = "/{appId}/{clusterName}/{namespace:.+}")
  public ApolloConfig queryConfig(@PathVariable String appId, @PathVariable String clusterName,
                                  @PathVariable String namespace,
                                  @RequestParam(value = "dataCenter", required = false) String dataCenter,
                                  @RequestParam(value = "releaseKey", defaultValue = "-1") String clientSideReleaseKey,
                                  @RequestParam(value = "ip", required = false) String clientIp,
                                  @RequestParam(value = "messages", required = false) String messagesAsString,
                                  HttpServletRequest request, HttpServletResponse response) throws IOException {
   
   
    String originalNamespace = namespace;
    //strip out .properties suffix
    // 若 Namespace 名以 .properties 结尾, 移除该结尾,并设置到 ApolloConfigNotification中
    namespace = namespaceUtil.filterNamespaceName(namespace);
    //fix the character case issue, such as FX.apollo <-> fx.apollo
    // 获得归一化的 Namespace 名字。因为,客户端 Namespace 会填错大消息
    namespace = namespaceUtil.normalizeNamespace(appId, namespace);

    // 若 clientIp 未提交,从 Request 中获取
    if (Strings.isNullOrEmpty(clientIp)) {
   
   
      clientIp = tryToGetClientIp(request);
    }

    // 解析 messageAsString 参数,创建 ApolloNotificationMessages 对象
    ApolloNotificationMessages clientMessages = transformMessages(messagesAsString);

    // 获取 Release 数组
    List<Release> releases = Lists.newLinkedList();

    // 获得 Namespace 对应的 Release 对象
    String appClusterNameLoaded = clusterName;
    if (!ConfigConsts.NO_APPID_PLACEHOLDER.equalsIgnoreCase(appId)) {
   
   
      // 获取 release 对象
      Release currentAppRelease = configService.loadConfig(appId, clientIp, appId, clusterName, namespace,
          dataCenter, clientMessages);

      if (currentAppRelease != null) {
   
   
        // 添加到 Release 数组中
        releases.add(currentAppRelease);
        //we have cluster search process, so the cluster name might be overridden
        // 获得 Release 对应的Cluster 名字
        appClusterNameLoaded = currentAppRelease.getClusterName();
      }
    }

    //if namespace does not belong to this appId, should check if there is a public configuration
    // 若 Namespace 未关联类型,则获取关联的 namespace 的 Release 对象
    if (!namespaceBelongsToAppId(appId, namespace)) {
   
   
      // 获得 Release 对象
      Release publicRelease = this.findPublicConfig(appId, clientIp, clusterName, namespace,
              dataCenter, clientMessages);
      // 添加到 Release 数组中
      if (Objects.nonNull(publicRelease)) {
   
   
        releases.add(publicRelease);
      }
    }

    // 若获得不到 Release , 返回状态码为 404 的响应
    if (releases.isEmpty()) {
   
   
      response.sendError(HttpServletResponse.SC_NOT_FOUND,
          String.format(
              
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值