From f5811068efdea26a7d82720cd6003da27dbb710e Mon Sep 17 00:00:00 2001 From: shedfreewu <49236872+shedfreewu@users.noreply.github.com> Date: Tue, 11 Nov 2025 21:41:08 +0800 Subject: [PATCH] fix: fix multiple bugs in tsf. (#1746) --- .../polaris/config/ConfigurationModifier.java | 15 +++++++++++- .../cloud/common/util/TsfTagUtils.java | 6 +++-- .../gateway/context/GatewayConsulConfig.java | 24 ++++++++++++------- .../gateway/context/GatewayConsulRepo.java | 12 +++++++--- .../tsf/gateway/core/util/PluginUtil.java | 4 ++-- .../tsf/TsfCoreEnvironmentPostProcessor.java | 3 ++- 6 files changed, 46 insertions(+), 18 deletions(-) diff --git a/spring-cloud-starter-tencent-polaris-config/src/main/java/com/tencent/cloud/polaris/config/ConfigurationModifier.java b/spring-cloud-starter-tencent-polaris-config/src/main/java/com/tencent/cloud/polaris/config/ConfigurationModifier.java index 4f5840554..6b49e645f 100644 --- a/spring-cloud-starter-tencent-polaris-config/src/main/java/com/tencent/cloud/polaris/config/ConfigurationModifier.java +++ b/spring-cloud-starter-tencent-polaris-config/src/main/java/com/tencent/cloud/polaris/config/ConfigurationModifier.java @@ -18,6 +18,7 @@ package com.tencent.cloud.polaris.config; import java.util.ArrayList; +import java.util.Arrays; import java.util.Collections; import java.util.List; @@ -163,12 +164,24 @@ public class ConfigurationModifier implements PolarisConfigurationConfigModifier private void checkAddressAccessible(List configAddresses) { // check address can connect configAddresses.forEach(address -> { - String[] ipPort = address.split(":"); + String[] ipPort; + // check ipv6 address, format: [ipv6_ip]:port + if (address.contains("[") && address.contains("]")) { + int lastColonIndex = address.lastIndexOf(':'); + String port = address.substring(lastColonIndex + 1); + String ip = address.substring(1, lastColonIndex - 1); + ipPort = new String[]{ip, port}; + } + else { + ipPort = address.split(":"); + } if (ipPort.length != 2) { throw new IllegalArgumentException("Config server address (" + address + ") is wrong, please check address like grpc://183.47.111.8:8091."); } + LOGGER.info("[SCT] Check config server ipPort: {}", Arrays.asList(ipPort)); + if (!AddressUtils.accessible(ipPort[0], Integer.parseInt(ipPort[1]), 3000)) { String errMsg = "Config server address (" + address + ") can not be connected. Please check your config in bootstrap.yml" + " with spring.cloud.polaris.address or spring.cloud.polaris.config.address."; diff --git a/spring-cloud-tencent-commons/src/main/java/com/tencent/cloud/common/util/TsfTagUtils.java b/spring-cloud-tencent-commons/src/main/java/com/tencent/cloud/common/util/TsfTagUtils.java index 2c27dcc7f..b61b864a2 100644 --- a/spring-cloud-tencent-commons/src/main/java/com/tencent/cloud/common/util/TsfTagUtils.java +++ b/spring-cloud-tencent-commons/src/main/java/com/tencent/cloud/common/util/TsfTagUtils.java @@ -175,10 +175,12 @@ public final class TsfTagUtils { Map tsfDisposableMetadata = new HashMap<>(tagSize); if (CollectionUtils.isNotEmpty(tsfUserTagList)) { for (Tag tag : tsfUserTagList) { - if (Tag.ControlFlag.TRANSITIVE.equals(tag.getFlags())) { + if (tag.getFlags() != null && tag.getFlags().contains(Tag.ControlFlag.TRANSITIVE)) { tsfTransitiveMetadata.put(tag.getKey(), tag.getValue()); } - tsfDisposableMetadata.put(tag.getKey(), tag.getValue()); + else { + tsfDisposableMetadata.put(tag.getKey(), tag.getValue()); + } } mergedTransitiveMetadata.putAll(tsfTransitiveMetadata); mergedDisposableMetadata.putAll(tsfDisposableMetadata); diff --git a/spring-cloud-tencent-plugin-starters/spring-cloud-starter-tencent-gateway-plugin/src/main/java/com/tencent/cloud/plugin/gateway/context/GatewayConsulConfig.java b/spring-cloud-tencent-plugin-starters/spring-cloud-starter-tencent-gateway-plugin/src/main/java/com/tencent/cloud/plugin/gateway/context/GatewayConsulConfig.java index fea6745d4..7b467d2b3 100644 --- a/spring-cloud-tencent-plugin-starters/spring-cloud-starter-tencent-gateway-plugin/src/main/java/com/tencent/cloud/plugin/gateway/context/GatewayConsulConfig.java +++ b/spring-cloud-tencent-plugin-starters/spring-cloud-starter-tencent-gateway-plugin/src/main/java/com/tencent/cloud/plugin/gateway/context/GatewayConsulConfig.java @@ -90,21 +90,27 @@ public class GatewayConsulConfig { Response> watchResponse = consulClient.getKVValues(keyPrefix, consulConfigContext.getAclToken(), new QueryParams(consulConfigContext.getWaitTime(), index)); - if (watchResponse.getValue() == null) { - gatewayAllResult = loadResponseFromFile(); - if (!isFirstLoad) { - refreshAction.run(); - } - return; - } - Long newIndex = watchResponse.getConsulIndex(); if (logger.isDebugEnabled()) { - logger.debug("[watch] keyPrefix:{}, index: {}, newIndex: {}", keyPrefix, index, newIndex); + logger.debug("[watch] keyPrefix:{}, index: {}, newIndex: {}, response is empty:{}", keyPrefix, index, newIndex, watchResponse.getValue() == null); } + boolean change = false; if (newIndex != null && !Objects.equals(index, newIndex)) { + change = true; index = newIndex; + } + + if (watchResponse.getValue() == null) { + // only load from the cache file when the first load and response is empty. + if (isFirstLoad) { + gatewayAllResult = loadResponseFromFile(); + logger.debug("[watch] loadResponseFromFile, keyPrefix: {}", keyPrefix); + } + return; + } + + if (change) { gatewayAllResult = parseGroupResponse(watchResponse); if (!isFirstLoad) { refreshAction.run(); diff --git a/spring-cloud-tencent-plugin-starters/spring-cloud-starter-tencent-gateway-plugin/src/main/java/com/tencent/cloud/plugin/gateway/context/GatewayConsulRepo.java b/spring-cloud-tencent-plugin-starters/spring-cloud-starter-tencent-gateway-plugin/src/main/java/com/tencent/cloud/plugin/gateway/context/GatewayConsulRepo.java index 23ae205a1..69a224b43 100644 --- a/spring-cloud-tencent-plugin-starters/spring-cloud-starter-tencent-gateway-plugin/src/main/java/com/tencent/cloud/plugin/gateway/context/GatewayConsulRepo.java +++ b/spring-cloud-tencent-plugin-starters/spring-cloud-starter-tencent-gateway-plugin/src/main/java/com/tencent/cloud/plugin/gateway/context/GatewayConsulRepo.java @@ -311,7 +311,12 @@ public class GatewayConsulRepo { } GroupContext groupContext = groups.get(wildcardRule.getGroupId()); - groupContext.getRoutes().add(contextRoute); + if (groupContext != null && groupContext.getRoutes() != null) { + groupContext.getRoutes().add(contextRoute); + } + else { + logger.warn("path wildcard rule {} not found in group {}", wildcardRule.getWildCardId(), wildcardRule.getGroupId()); + } } } @@ -319,8 +324,9 @@ public class GatewayConsulRepo { contextGatewayProperties.setRoutes(routes); contextGatewayProperties.setPathRewrites(Optional.ofNullable(pathRewriteResult).map(PathRewriteResult::getResult) .orElse(new ArrayList<>())); - - logger.debug("Gateway config loaded. :{}", JacksonUtils.serialize2Json(contextGatewayProperties)); + if (logger.isDebugEnabled()) { + logger.debug("Gateway config loaded. :{}", JacksonUtils.serialize2Json(contextGatewayProperties)); + } contextGatewayPropertiesManager.setPathRewrites(contextGatewayProperties.getPathRewrites()); diff --git a/spring-cloud-tencent-plugin-starters/spring-cloud-starter-tencent-gateway-plugin/src/main/java/com/tencent/tsf/gateway/core/util/PluginUtil.java b/spring-cloud-tencent-plugin-starters/spring-cloud-starter-tencent-gateway-plugin/src/main/java/com/tencent/tsf/gateway/core/util/PluginUtil.java index 2798cf92d..5a4f5e0cf 100644 --- a/spring-cloud-tencent-plugin-starters/spring-cloud-starter-tencent-gateway-plugin/src/main/java/com/tencent/tsf/gateway/core/util/PluginUtil.java +++ b/spring-cloud-tencent-plugin-starters/spring-cloud-starter-tencent-gateway-plugin/src/main/java/com/tencent/tsf/gateway/core/util/PluginUtil.java @@ -139,8 +139,8 @@ public final class PluginUtil { if (path.charAt(0) != '/') { path = "/" + path; } - - String apiPath = StringUtils.substring(path, StringUtils.ordinalIndexOf(path, "/", 4)); + // apiPath is the path of downstream service. + String apiPath = path; boolean matched = antPathMatcher.match(preTagName, apiPath); if (matched) { Map pathTagMap = antPathMatcher.extractUriTemplateVariables(preTagName, apiPath); diff --git a/spring-cloud-tencent-polaris-context/src/main/java/com/tencent/cloud/polaris/context/config/extend/tsf/TsfCoreEnvironmentPostProcessor.java b/spring-cloud-tencent-polaris-context/src/main/java/com/tencent/cloud/polaris/context/config/extend/tsf/TsfCoreEnvironmentPostProcessor.java index 75a609102..4760fa5df 100644 --- a/spring-cloud-tencent-polaris-context/src/main/java/com/tencent/cloud/polaris/context/config/extend/tsf/TsfCoreEnvironmentPostProcessor.java +++ b/spring-cloud-tencent-polaris-context/src/main/java/com/tencent/cloud/polaris/context/config/extend/tsf/TsfCoreEnvironmentPostProcessor.java @@ -21,6 +21,7 @@ import java.util.HashMap; import java.util.Map; import com.tencent.cloud.common.tsf.TsfContextUtils; +import com.tencent.polaris.api.utils.IPAddressUtils; import com.tencent.polaris.api.utils.StringUtils; import org.apache.commons.logging.Log; @@ -164,7 +165,7 @@ public final class TsfCoreEnvironmentPostProcessor implements EnvironmentPostPro defaultProperties.put("spring.cloud.polaris.config.enabled", "true"); defaultProperties.put("spring.cloud.polaris.config.internal-enabled", "false"); defaultProperties.put("spring.cloud.polaris.config.data-source", "consul"); - defaultProperties.put("spring.cloud.polaris.config.address", "http://" + tsfConsulIp + ":" + tsfConsulPort); + defaultProperties.put("spring.cloud.polaris.config.address", "http://" + IPAddressUtils.getIpCompatible(tsfConsulIp) + ":" + tsfConsulPort); defaultProperties.put("spring.cloud.polaris.config.port", tsfConsulPort); defaultProperties.put("spring.cloud.polaris.config.token", tsfConsulToken); defaultProperties.put("spring.cloud.polaris.config.groups[0].namespace", "config");