diff --git a/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/main/java/com/tencent/cloud/metadata/context/MetadataContext.java b/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/main/java/com/tencent/cloud/metadata/context/MetadataContext.java index 61f28ffe8..8b9ee06f7 100644 --- a/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/main/java/com/tencent/cloud/metadata/context/MetadataContext.java +++ b/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/main/java/com/tencent/cloud/metadata/context/MetadataContext.java @@ -17,6 +17,8 @@ package com.tencent.cloud.metadata.context; +import com.tencent.cloud.metadata.util.JacksonUtils; + import java.util.Collections; import java.util.HashMap; import java.util.Map; @@ -74,4 +76,12 @@ public class MetadataContext { public void putAllSystemMetadata(Map systemMetadata) { this.systemMetadata.putAll(systemMetadata); } + + @Override + public String toString() { + return "MetadataContext{" + + "transitiveCustomMetadata=" + JacksonUtils.serialize2Json(transitiveCustomMetadata) + + ", systemMetadata=" + JacksonUtils.serialize2Json(systemMetadata) + + '}'; + } } diff --git a/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/main/java/com/tencent/cloud/metadata/core/filter/MetadataReactiveFilter.java b/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/main/java/com/tencent/cloud/metadata/core/filter/MetadataReactiveFilter.java index 12b9f6f6c..9c4004eff 100644 --- a/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/main/java/com/tencent/cloud/metadata/core/filter/MetadataReactiveFilter.java +++ b/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/main/java/com/tencent/cloud/metadata/core/filter/MetadataReactiveFilter.java @@ -70,25 +70,21 @@ public class MetadataReactiveFilter implements WebFilter, Ordered { LOG.debug("Get upstream metadata string: {}", customMetadataStr); // create custom metadata. - Map upstreamCustomMetadataMap = JacksonUtils.deserializeMetadataMap(customMetadataStr); + Map upstreamCustomMetadataMap = JacksonUtils.deserialize2Map(customMetadataStr); // create system metadata. Map systemMetadataMap = new HashMap<>(); systemMetadataMap.put(LOCAL_NAMESPACE, MetadataContextHolder.LOCAL_NAMESPACE); systemMetadataMap.put(LOCAL_SERVICE, MetadataContextHolder.LOCAL_SERVICE); - systemMetadataMap.put(LOCAL_PATH, serverHttpRequest.getURI().getRawPath()); + systemMetadataMap.put(LOCAL_PATH, serverHttpRequest.getURI().getPath()); - try { - MetadataContextHolder.init(upstreamCustomMetadataMap, systemMetadataMap); + MetadataContextHolder.init(upstreamCustomMetadataMap, systemMetadataMap); - // Save to ServerWebExchange. - serverWebExchange.getAttributes() - .put(MetadataConstant.HeaderName.METADATA_CONTEXT, MetadataContextHolder.get()); - return webFilterChain.filter(serverWebExchange).doFinally((type) -> MetadataContextHolder.remove()); - } catch (RuntimeException e) { - throw e; - } finally { - MetadataContextHolder.remove(); - } + // Save to ServerWebExchange. + serverWebExchange.getAttributes() + .put(MetadataConstant.HeaderName.METADATA_CONTEXT, MetadataContextHolder.get()); + return webFilterChain.filter(serverWebExchange) + .doOnError(throwable -> LOG.error("handle metadata[{}] error.", MetadataContextHolder.get())) + .doFinally((type) -> MetadataContextHolder.remove()); } -} +} \ No newline at end of file diff --git a/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/main/java/com/tencent/cloud/metadata/core/filter/MetadataServletFilter.java b/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/main/java/com/tencent/cloud/metadata/core/filter/MetadataServletFilter.java index a478bb17e..ff4e57b65 100644 --- a/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/main/java/com/tencent/cloud/metadata/core/filter/MetadataServletFilter.java +++ b/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/main/java/com/tencent/cloud/metadata/core/filter/MetadataServletFilter.java @@ -64,7 +64,7 @@ public class MetadataServletFilter extends OncePerRequestFilter { LOG.debug("Get upstream metadata string: {}", customMetadataStr); // create custom metadata. - Map upstreamCustomMetadataMap = JacksonUtils.deserializeMetadataMap(customMetadataStr); + Map upstreamCustomMetadataMap = JacksonUtils.deserialize2Map(customMetadataStr); // create system metadata. Map systemMetadataMap = new HashMap<>(); diff --git a/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/main/java/com/tencent/cloud/metadata/core/interceptor/feign/Metadata2HeaderFeignInterceptor.java b/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/main/java/com/tencent/cloud/metadata/core/interceptor/feign/Metadata2HeaderFeignInterceptor.java index 0c6f0d2d7..11c33ed0e 100644 --- a/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/main/java/com/tencent/cloud/metadata/core/interceptor/feign/Metadata2HeaderFeignInterceptor.java +++ b/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/main/java/com/tencent/cloud/metadata/core/interceptor/feign/Metadata2HeaderFeignInterceptor.java @@ -57,7 +57,7 @@ public class Metadata2HeaderFeignInterceptor implements RequestInterceptor, Orde if (!CollectionUtils.isEmpty(requestTemplate.headers()) && !CollectionUtils.isEmpty(requestTemplate.headers().get(CUSTOM_METADATA))) { for (String headerMetadataStr : requestTemplate.headers().get(CUSTOM_METADATA)) { - Map headerMetadataMap = JacksonUtils.deserializeMetadataMap(headerMetadataStr); + Map headerMetadataMap = JacksonUtils.deserialize2Map(headerMetadataStr); for (String key : headerMetadataMap.keySet()) { metadataContext.putTransitiveCustomMetadata(key, headerMetadataMap.get(key)); } @@ -66,7 +66,7 @@ public class Metadata2HeaderFeignInterceptor implements RequestInterceptor, Orde Map customMetadata = metadataContext.getAllTransitiveCustomMetadata(); if (!CollectionUtils.isEmpty(customMetadata)) { - String metadataStr = JacksonUtils.serializeToJson(customMetadata); + String metadataStr = JacksonUtils.serialize2Json(customMetadata); requestTemplate.removeHeader(CUSTOM_METADATA); try { requestTemplate.header(CUSTOM_METADATA, diff --git a/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/main/java/com/tencent/cloud/metadata/core/interceptor/resttemplate/MetadataRestTemplateInterceptor.java b/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/main/java/com/tencent/cloud/metadata/core/interceptor/resttemplate/MetadataRestTemplateInterceptor.java index 025db7784..090f572ac 100644 --- a/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/main/java/com/tencent/cloud/metadata/core/interceptor/resttemplate/MetadataRestTemplateInterceptor.java +++ b/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/main/java/com/tencent/cloud/metadata/core/interceptor/resttemplate/MetadataRestTemplateInterceptor.java @@ -59,14 +59,14 @@ public class MetadataRestTemplateInterceptor implements ClientHttpRequestInterce // add new metadata and cover old String metadataStr = httpRequest.getHeaders().getFirst(MetadataConstant.HeaderName.CUSTOM_METADATA); if (!StringUtils.isEmpty(metadataStr)) { - Map headerMetadataMap = JacksonUtils.deserializeMetadataMap(metadataStr); + Map headerMetadataMap = JacksonUtils.deserialize2Map(metadataStr); for (String key : headerMetadataMap.keySet()) { metadataContext.putTransitiveCustomMetadata(key, headerMetadataMap.get(key)); } } Map customMetadata = metadataContext.getAllTransitiveCustomMetadata(); if (!CollectionUtils.isEmpty(customMetadata)) { - metadataStr = JacksonUtils.serializeToJson(customMetadata); + metadataStr = JacksonUtils.serialize2Json(customMetadata); try { httpRequest.getHeaders().set(MetadataConstant.HeaderName.CUSTOM_METADATA, URLEncoder.encode(metadataStr, "UTF-8")); diff --git a/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/main/java/com/tencent/cloud/metadata/util/JacksonUtils.java b/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/main/java/com/tencent/cloud/metadata/util/JacksonUtils.java index 14cfe468c..a5b9d156b 100644 --- a/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/main/java/com/tencent/cloud/metadata/util/JacksonUtils.java +++ b/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/main/java/com/tencent/cloud/metadata/util/JacksonUtils.java @@ -45,7 +45,7 @@ public class JacksonUtils { * @param type of object * @return Json String */ - public static String serializeToJson(T object) { + public static String serialize2Json(T object) { try { return OM.writeValueAsString(object); } catch (JsonProcessingException e) { @@ -60,7 +60,7 @@ public class JacksonUtils { * @param jsonStr Json String * @return Map */ - public static Map deserializeMetadataMap(String jsonStr) { + public static Map deserialize2Map(String jsonStr) { try { if (StringUtils.hasText(jsonStr)) { return OM.readValue(jsonStr, Map.class); diff --git a/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/main/java/com/tencent/cloud/metadata/util/MetadataUtils.java b/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/main/java/com/tencent/cloud/metadata/util/MetadataUtils.java index f2f85fccb..08372f48f 100644 --- a/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/main/java/com/tencent/cloud/metadata/util/MetadataUtils.java +++ b/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/main/java/com/tencent/cloud/metadata/util/MetadataUtils.java @@ -47,7 +47,7 @@ public class MetadataUtils { // Transfer string to map. if (StringUtils.hasText(newMetadataStr)) { - Map requestMetadataMap = JacksonUtils.deserializeMetadataMap(newMetadataStr); + Map requestMetadataMap = JacksonUtils.deserialize2Map(newMetadataStr); // metadata from upstream cover local metadata for this thread. for (String key : requestMetadataMap.keySet()) { diff --git a/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/test/java/com/tencent/cloud/metadata/core/intercepter/feign/Metadata2HeaderFeignInterceptorTest.java b/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/test/java/com/tencent/cloud/metadata/core/intercepter/feign/Metadata2HeaderFeignInterceptorTest.java index 7ec940542..ad32c4dc6 100644 --- a/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/test/java/com/tencent/cloud/metadata/core/intercepter/feign/Metadata2HeaderFeignInterceptorTest.java +++ b/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/test/java/com/tencent/cloud/metadata/core/intercepter/feign/Metadata2HeaderFeignInterceptorTest.java @@ -80,7 +80,7 @@ public class Metadata2HeaderFeignInterceptorTest { @RequestMapping("/test") public String test(@RequestHeader(MetadataConstant.HeaderName.CUSTOM_METADATA) String customMetadataStr) throws UnsupportedEncodingException { - String systemMetadataStr = JacksonUtils.serializeToJson(MetadataContextHolder.get().getAllSystemMetadata()); + String systemMetadataStr = JacksonUtils.serialize2Json(MetadataContextHolder.get().getAllSystemMetadata()); return URLDecoder.decode(customMetadataStr, "UTF-8") + systemMetadataStr; } diff --git a/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/test/java/com/tencent/cloud/metadata/core/intercepter/resttemplate/MetadataRestTemplateInterceptorTest.java b/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/test/java/com/tencent/cloud/metadata/core/intercepter/resttemplate/MetadataRestTemplateInterceptorTest.java index fb2e44544..3fcc704f9 100644 --- a/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/test/java/com/tencent/cloud/metadata/core/intercepter/resttemplate/MetadataRestTemplateInterceptorTest.java +++ b/spring-cloud-tencent-starters/spring-cloud-tencent-metadata/src/test/java/com/tencent/cloud/metadata/core/intercepter/resttemplate/MetadataRestTemplateInterceptorTest.java @@ -93,7 +93,7 @@ public class MetadataRestTemplateInterceptorTest { public String test(@RequestHeader(MetadataConstant.HeaderName.CUSTOM_METADATA) String customMetadataStr) throws UnsupportedEncodingException { String systemMetadataStr = - JacksonUtils.serializeToJson(MetadataContextHolder.get().getAllSystemMetadata()); + JacksonUtils.serialize2Json(MetadataContextHolder.get().getAllSystemMetadata()); return URLDecoder.decode(customMetadataStr, "UTF-8") + systemMetadataStr; } diff --git a/spring-cloud-tencent-starters/spring-cloud-tencent-polaris-gateway/src/main/java/com/tencent/cloud/polaris/gateway/config/PolarisGatewayAutoConfiguration.java b/spring-cloud-tencent-starters/spring-cloud-tencent-polaris-gateway/src/main/java/com/tencent/cloud/polaris/gateway/config/PolarisGatewayAutoConfiguration.java index da5be3654..1ecbc478a 100644 --- a/spring-cloud-tencent-starters/spring-cloud-tencent-polaris-gateway/src/main/java/com/tencent/cloud/polaris/gateway/config/PolarisGatewayAutoConfiguration.java +++ b/spring-cloud-tencent-starters/spring-cloud-tencent-polaris-gateway/src/main/java/com/tencent/cloud/polaris/gateway/config/PolarisGatewayAutoConfiguration.java @@ -20,6 +20,7 @@ package com.tencent.cloud.polaris.gateway.config; import com.netflix.zuul.ZuulFilter; import com.netflix.zuul.http.ZuulServlet; import com.tencent.cloud.polaris.gateway.core.scg.filter.Metadata2HeaderScgFilter; +import com.tencent.cloud.polaris.gateway.core.scg.filter.MetadataFirstScgFilter; import com.tencent.cloud.polaris.gateway.core.zuul.filter.Metadata2HeaderZuulFilter; import com.tencent.cloud.polaris.gateway.core.zuul.filter.MetadataFirstZuulFilter; import com.tencent.cloud.polaris.gateway.core.zuul.filter.RateLimitZuulFilter; @@ -57,6 +58,11 @@ public class PolarisGatewayAutoConfiguration { @Configuration(proxyBeanMethods = false) @ConditionalOnClass(GlobalFilter.class) static class PolarisGatewayScgAutoConfiguration { + @Bean + public GlobalFilter metadataFirstScgFilter() { + return new MetadataFirstScgFilter(); + } + @Bean public GlobalFilter metadata2HeaderScgFilter() { return new Metadata2HeaderScgFilter(); diff --git a/spring-cloud-tencent-starters/spring-cloud-tencent-polaris-gateway/src/main/java/com/tencent/cloud/polaris/gateway/core/scg/filter/Metadata2HeaderScgFilter.java b/spring-cloud-tencent-starters/spring-cloud-tencent-polaris-gateway/src/main/java/com/tencent/cloud/polaris/gateway/core/scg/filter/Metadata2HeaderScgFilter.java index 679fa5173..654c1f18e 100644 --- a/spring-cloud-tencent-starters/spring-cloud-tencent-polaris-gateway/src/main/java/com/tencent/cloud/polaris/gateway/core/scg/filter/Metadata2HeaderScgFilter.java +++ b/spring-cloud-tencent-starters/spring-cloud-tencent-polaris-gateway/src/main/java/com/tencent/cloud/polaris/gateway/core/scg/filter/Metadata2HeaderScgFilter.java @@ -64,7 +64,7 @@ public class Metadata2HeaderScgFilter extends AbstractGlobalFilter { } Map customMetadata = metadataContext.getAllTransitiveCustomMetadata(); if (!CollectionUtils.isEmpty(customMetadata)) { - String metadataStr = JacksonUtils.serializeToJson(customMetadata); + String metadataStr = JacksonUtils.serialize2Json(customMetadata); try { builder.header(MetadataConstant.HeaderName.CUSTOM_METADATA, URLEncoder.encode(metadataStr, "UTF-8")); } catch (UnsupportedEncodingException e) { diff --git a/spring-cloud-tencent-starters/spring-cloud-tencent-polaris-gateway/src/main/java/com/tencent/cloud/polaris/gateway/core/scg/filter/MetadataFirstScgFilter.java b/spring-cloud-tencent-starters/spring-cloud-tencent-polaris-gateway/src/main/java/com/tencent/cloud/polaris/gateway/core/scg/filter/MetadataFirstScgFilter.java new file mode 100644 index 000000000..8e061abe0 --- /dev/null +++ b/spring-cloud-tencent-starters/spring-cloud-tencent-polaris-gateway/src/main/java/com/tencent/cloud/polaris/gateway/core/scg/filter/MetadataFirstScgFilter.java @@ -0,0 +1,66 @@ +/* + * Tencent is pleased to support the open source community by making Spring Cloud Tencent available. + * + * Copyright (C) 2019 THL A29 Limited, a Tencent company. All rights reserved. + * + * Licensed under the BSD 3-Clause License (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * https://opensource.org/licenses/BSD-3-Clause + * + * Unless required by applicable law or agreed to in writing, software distributed + * under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR + * CONDITIONS OF ANY KIND, either express or implied. See the License for the + * specific language governing permissions and limitations under the License. + * + */ + +package com.tencent.cloud.polaris.gateway.core.scg.filter; + +import com.tencent.cloud.metadata.constant.MetadataConstant; +import com.tencent.cloud.metadata.context.MetadataContext; +import com.tencent.cloud.metadata.context.MetadataContextHolder; +import org.springframework.cloud.gateway.filter.GatewayFilterChain; +import org.springframework.cloud.gateway.route.Route; +import org.springframework.web.server.ServerWebExchange; +import reactor.core.publisher.Mono; + +import static org.springframework.cloud.gateway.filter.RouteToRequestUrlFilter.ROUTE_TO_URL_FILTER_ORDER; +import static org.springframework.cloud.gateway.support.ServerWebExchangeUtils.GATEWAY_ROUTE_ATTR; + +/** + * @author Haotian Zhang + */ +public class MetadataFirstScgFilter extends AbstractGlobalFilter { + + @Override + public int getOrder() { + return ROUTE_TO_URL_FILTER_ORDER + 1; + } + + @Override + public boolean shouldFilter(ServerWebExchange exchange, GatewayFilterChain chain) { + return true; + } + + @Override + public Mono doFilter(ServerWebExchange exchange, GatewayFilterChain chain) { + // get request context + Route route = exchange.getAttribute(GATEWAY_ROUTE_ATTR); + + // get metadata of current thread + MetadataContext metadataContext = exchange.getAttribute(MetadataConstant.HeaderName.METADATA_CONTEXT); + + // TODO 对端命名空间暂时与本地命名空间相同 + metadataContext.putSystemMetadata(MetadataConstant.SystemMetadataKey.PEER_NAMESPACE, + MetadataContextHolder.get().getSystemMetadata(MetadataConstant.SystemMetadataKey.LOCAL_NAMESPACE)); + metadataContext.putSystemMetadata(MetadataConstant.SystemMetadataKey.PEER_SERVICE, route.getId()); + metadataContext.putSystemMetadata(MetadataConstant.SystemMetadataKey.PEER_PATH, + exchange.getRequest().getURI().getPath()); + + exchange.getAttributes().put(MetadataConstant.HeaderName.METADATA_CONTEXT, metadataContext); + + return chain.filter(exchange); + } +} diff --git a/spring-cloud-tencent-starters/spring-cloud-tencent-polaris-gateway/src/main/java/com/tencent/cloud/polaris/gateway/core/zuul/filter/Metadata2HeaderZuulFilter.java b/spring-cloud-tencent-starters/spring-cloud-tencent-polaris-gateway/src/main/java/com/tencent/cloud/polaris/gateway/core/zuul/filter/Metadata2HeaderZuulFilter.java index 53972c6c5..4b743f070 100644 --- a/spring-cloud-tencent-starters/spring-cloud-tencent-polaris-gateway/src/main/java/com/tencent/cloud/polaris/gateway/core/zuul/filter/Metadata2HeaderZuulFilter.java +++ b/spring-cloud-tencent-starters/spring-cloud-tencent-polaris-gateway/src/main/java/com/tencent/cloud/polaris/gateway/core/zuul/filter/Metadata2HeaderZuulFilter.java @@ -66,7 +66,7 @@ public class Metadata2HeaderZuulFilter extends ZuulFilter { // add new metadata and cover old Map customMetadata = metadataContext.getAllTransitiveCustomMetadata(); if (!CollectionUtils.isEmpty(customMetadata)) { - String metadataStr = JacksonUtils.serializeToJson(customMetadata); + String metadataStr = JacksonUtils.serialize2Json(customMetadata); try { requestContext.addZuulRequestHeader(MetadataConstant.HeaderName.CUSTOM_METADATA, URLEncoder.encode(metadataStr, "UTF-8"));