apollo-configservice/src/main/java/com/ctrip/framework/apollo/configservice/controller/ConfigFileController.java/ConfigFileController/ConfigFileController
class ConfigFileController:  public ConfigFileController(
      final ConfigController configController,
      final NamespaceUtil namespaceUtil,
      final WatchKeysUtil watchKeysUtil,
      final GrayReleaseRulesHolder grayReleaseRulesHolder) {
    localCache = CacheBuilder.newBuilder()
        .expireAfterWrite(EXPIRE_AFTER_WRITE, TimeUnit.MINUTES)
        .weigher((Weigher<String, String>) (key, value) -> value == null ? 0 : value.length())
        .maximumWeight(MAX_CACHE_SIZE)
        .removalListener(notification -> {
          String cacheKey = notification.getKey();
          logger.debug("removing cache key: {}", cacheKey);
          if (!cacheKey2WatchedKeys.containsKey(cacheKey)) {
            return;
          }
          //create a new list to avoid ConcurrentModificationException
          List<String> watchedKeys = new ArrayList<>(cacheKey2WatchedKeys.get(cacheKey));
          for (String watchedKey : watchedKeys) {
            watchedKeys2CacheKey.remove(watchedKey, cacheKey);
          }
          cacheKey2WatchedKeys.removeAll(cacheKey);
          logger.debug("removed cache key: {}", cacheKey);
        })
        .build();
    propertiesResponseHeaders = new HttpHeaders();
    propertiesResponseHeaders.add("Content-Type", "text/plain;charset=UTF-8");
    jsonResponseHeaders = new HttpHeaders();
    jsonResponseHeaders.add("Content-Type", "application/json;charset=UTF-8");
    NOT_FOUND_RESPONSE = new ResponseEntity<>(HttpStatus.NOT_FOUND);
    this.configController = configController;
    this.namespaceUtil = namespaceUtil;
    this.watchKeysUtil = watchKeysUtil;
    this.grayReleaseRulesHolder = grayReleaseRulesHolder;
  }