feat: support tsf unit. (#1722)
parent
cfd769b701
commit
fa5d3ac2b5
@ -0,0 +1,32 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.common.util;
|
||||||
|
|
||||||
|
import com.tencent.polaris.api.utils.ClassUtils;
|
||||||
|
|
||||||
|
public final class EnvironmentUtils {
|
||||||
|
|
||||||
|
private final static boolean IS_GATEWAY = ClassUtils.isClassPresent("org.springframework.cloud.gateway.filter.GlobalFilter");
|
||||||
|
|
||||||
|
private EnvironmentUtils() {
|
||||||
|
}
|
||||||
|
|
||||||
|
public static boolean isGateway() {
|
||||||
|
return IS_GATEWAY;
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,56 @@
|
|||||||
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
|
<project xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||||
|
xmlns="http://maven.apache.org/POM/4.0.0"
|
||||||
|
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
|
||||||
|
<parent>
|
||||||
|
<artifactId>spring-cloud-tencent-plugin-starters</artifactId>
|
||||||
|
<groupId>com.tencent.cloud</groupId>
|
||||||
|
<version>${revision}</version>
|
||||||
|
<relativePath>../pom.xml</relativePath>
|
||||||
|
</parent>
|
||||||
|
<modelVersion>4.0.0</modelVersion>
|
||||||
|
|
||||||
|
<artifactId>spring-cloud-tencent-unit-plugin</artifactId>
|
||||||
|
<name>Spring Cloud Tencent Unit Plugin</name>
|
||||||
|
|
||||||
|
|
||||||
|
<dependencies>
|
||||||
|
<dependency>
|
||||||
|
<groupId>com.tencent.cloud</groupId>
|
||||||
|
<artifactId>spring-cloud-starter-tencent-polaris-discovery</artifactId>
|
||||||
|
<optional>true</optional>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.springframework.boot</groupId>
|
||||||
|
<artifactId>spring-boot-actuator-autoconfigure</artifactId>
|
||||||
|
<optional>true</optional>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
|
<dependency>
|
||||||
|
<groupId>com.fasterxml.jackson.core</groupId>
|
||||||
|
<artifactId>jackson-databind</artifactId>
|
||||||
|
<optional>true</optional>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
|
<dependency>
|
||||||
|
<groupId>com.fasterxml.jackson.dataformat</groupId>
|
||||||
|
<artifactId>jackson-dataformat-yaml</artifactId>
|
||||||
|
<optional>true</optional>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.springframework.boot</groupId>
|
||||||
|
<artifactId>spring-boot-starter-web</artifactId>
|
||||||
|
<optional>true</optional>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.springframework.cloud</groupId>
|
||||||
|
<artifactId>spring-cloud-starter-openfeign</artifactId>
|
||||||
|
<optional>true</optional>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
|
</dependencies>
|
||||||
|
|
||||||
|
</project>
|
@ -0,0 +1,54 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.plugin.unit.config;
|
||||||
|
|
||||||
|
import com.tencent.cloud.common.tsf.ConditionalOnOnlyTsfConsulEnabled;
|
||||||
|
import com.tencent.tsf.unit.core.GatewayUnitArchCallback;
|
||||||
|
import com.tencent.tsf.unit.core.TencentUnitManager;
|
||||||
|
import com.tencent.tsf.unit.core.TsfZoneFilterUnitCallback;
|
||||||
|
import com.tencent.tsf.unit.core.remote.TsfUnitConsulManager;
|
||||||
|
import jakarta.annotation.PostConstruct;
|
||||||
|
|
||||||
|
import org.springframework.beans.factory.annotation.Value;
|
||||||
|
import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
|
||||||
|
import org.springframework.context.annotation.Configuration;
|
||||||
|
|
||||||
|
|
||||||
|
@Configuration
|
||||||
|
public class GatewayUnitAutoConfiguration {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 网关时执行.
|
||||||
|
*/
|
||||||
|
@Configuration
|
||||||
|
@ConditionalOnOnlyTsfConsulEnabled
|
||||||
|
@ConditionalOnClass(name = "org.springframework.cloud.gateway.filter.GlobalFilter")
|
||||||
|
static class GatewayUnitEnable {
|
||||||
|
|
||||||
|
@Value("${spring.application.name:}")
|
||||||
|
private String applicationName;
|
||||||
|
|
||||||
|
|
||||||
|
@PostConstruct
|
||||||
|
public void init() {
|
||||||
|
TencentUnitManager.addArchCallback(new GatewayUnitArchCallback(applicationName));
|
||||||
|
TencentUnitManager.addRuleCallback(new TsfZoneFilterUnitCallback());
|
||||||
|
TsfUnitConsulManager.init();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,43 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.plugin.unit.config;
|
||||||
|
|
||||||
|
import com.tencent.cloud.plugin.unit.discovery.UnitFeignEagerLoadSmartLifecycle;
|
||||||
|
import com.tencent.cloud.plugin.unit.discovery.UnitPolarisDiscoveryClient;
|
||||||
|
import com.tencent.cloud.polaris.discovery.PolarisDiscoveryClient;
|
||||||
|
import com.tencent.cloud.polaris.eager.instrument.feign.FeignEagerLoadSmartLifecycle;
|
||||||
|
|
||||||
|
import org.springframework.beans.BeansException;
|
||||||
|
import org.springframework.beans.factory.config.BeanPostProcessor;
|
||||||
|
|
||||||
|
public class UnitBeanPostProcessor implements BeanPostProcessor {
|
||||||
|
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {
|
||||||
|
if (bean instanceof PolarisDiscoveryClient discoveryClient) {
|
||||||
|
return new UnitPolarisDiscoveryClient(discoveryClient);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (bean instanceof FeignEagerLoadSmartLifecycle) {
|
||||||
|
return new UnitFeignEagerLoadSmartLifecycle();
|
||||||
|
}
|
||||||
|
|
||||||
|
return bean;
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,37 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.plugin.unit.discovery;
|
||||||
|
|
||||||
|
import com.tencent.cloud.polaris.eager.instrument.feign.FeignEagerLoadSmartLifecycle;
|
||||||
|
import org.slf4j.Logger;
|
||||||
|
import org.slf4j.LoggerFactory;
|
||||||
|
|
||||||
|
public class UnitFeignEagerLoadSmartLifecycle extends FeignEagerLoadSmartLifecycle {
|
||||||
|
|
||||||
|
private static final Logger LOG = LoggerFactory.getLogger(UnitFeignEagerLoadSmartLifecycle.class);
|
||||||
|
|
||||||
|
|
||||||
|
public UnitFeignEagerLoadSmartLifecycle() {
|
||||||
|
super(null, null, null);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void start() {
|
||||||
|
LOG.info("ignore feign eager load in unit mode");
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,87 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.plugin.unit.discovery;
|
||||||
|
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
|
import com.tencent.cloud.common.constant.MetadataConstant;
|
||||||
|
import com.tencent.cloud.common.metadata.MetadataContext;
|
||||||
|
import com.tencent.cloud.common.metadata.MetadataContextHolder;
|
||||||
|
import com.tencent.cloud.polaris.discovery.PolarisDiscoveryClient;
|
||||||
|
import com.tencent.tsf.unit.core.TencentUnitContext;
|
||||||
|
import com.tencent.tsf.unit.core.TencentUnitManager;
|
||||||
|
import org.slf4j.Logger;
|
||||||
|
import org.slf4j.LoggerFactory;
|
||||||
|
|
||||||
|
import org.springframework.cloud.client.ServiceInstance;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Support unit discovery.
|
||||||
|
* TODO: support reactive discovery.
|
||||||
|
*/
|
||||||
|
public class UnitPolarisDiscoveryClient extends PolarisDiscoveryClient {
|
||||||
|
|
||||||
|
private static final Logger LOGGER = LoggerFactory.getLogger(UnitPolarisDiscoveryClient.class);
|
||||||
|
|
||||||
|
private final PolarisDiscoveryClient delegate;
|
||||||
|
|
||||||
|
public UnitPolarisDiscoveryClient(PolarisDiscoveryClient delegate) {
|
||||||
|
super(null);
|
||||||
|
this.delegate = delegate;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String description() {
|
||||||
|
return delegate.description();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public List<ServiceInstance> getInstances(String service) {
|
||||||
|
if (TencentUnitManager.isEnable()) {
|
||||||
|
// if service is not in the format of namespace/service, we will use the namespace in unit context
|
||||||
|
String[] parts = service.split("/");
|
||||||
|
if (LOGGER.isDebugEnabled()) {
|
||||||
|
LOGGER.debug("[getInstance] service:{}, unit context:{}", service, TencentUnitContext.getOriginCompositeContextMap());
|
||||||
|
}
|
||||||
|
|
||||||
|
if (parts.length != 2) {
|
||||||
|
String namespace = TencentUnitContext.getStringRouteTag(TencentUnitContext.CLOUD_SPACE_ROUTE_TARGET_NAMESPACE_ID);
|
||||||
|
|
||||||
|
MetadataContext metadataContext = MetadataContextHolder.get();
|
||||||
|
metadataContext.putFragmentContext(MetadataContext.FRAGMENT_APPLICATION_NONE,
|
||||||
|
MetadataConstant.POLARIS_TARGET_NAMESPACE, namespace);
|
||||||
|
return delegate.getInstances(service);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
MetadataContext metadataContext = MetadataContextHolder.get();
|
||||||
|
metadataContext.putFragmentContext(MetadataContext.FRAGMENT_APPLICATION_NONE,
|
||||||
|
MetadataConstant.POLARIS_TARGET_NAMESPACE, parts[0]);
|
||||||
|
|
||||||
|
return delegate.getInstances(parts[1]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
return delegate.getInstances(service);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public List<String> getServices() {
|
||||||
|
return delegate.getServices();
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,61 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.plugin.unit.instrument.feign;
|
||||||
|
|
||||||
|
import java.net.URI;
|
||||||
|
|
||||||
|
import com.tencent.cloud.common.constant.OrderConstant;
|
||||||
|
import com.tencent.cloud.plugin.unit.utils.SpringCloudUnitUtils;
|
||||||
|
import com.tencent.tsf.unit.core.TencentUnitContext;
|
||||||
|
import com.tencent.tsf.unit.core.TencentUnitManager;
|
||||||
|
import com.tencent.tsf.unit.core.model.UnitArch;
|
||||||
|
import feign.RequestInterceptor;
|
||||||
|
import feign.RequestTemplate;
|
||||||
|
|
||||||
|
import org.springframework.core.Ordered;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Interceptor used for setting Feign RequestTemplate metadata provider.
|
||||||
|
*
|
||||||
|
* @author lepdou, Hoatian Zhang
|
||||||
|
*/
|
||||||
|
public class UnitFeignRequestInterceptor implements RequestInterceptor, Ordered {
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int getOrder() {
|
||||||
|
return OrderConstant.Client.Feign.UNIT_INTERCEPTOR_ORDER;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void apply(RequestTemplate requestTemplate) {
|
||||||
|
// 开启单元化
|
||||||
|
if (TencentUnitManager.isEnable()) {
|
||||||
|
String httpServiceName = requestTemplate.feignTarget().url();
|
||||||
|
URI uri = URI.create(httpServiceName);
|
||||||
|
// 截取http://provider-demo 为 provider-demo,
|
||||||
|
String serviceName = uri.getHost();
|
||||||
|
|
||||||
|
SpringCloudUnitUtils.preRequestRecordUnitContext(serviceName);
|
||||||
|
|
||||||
|
if (TencentUnitContext.containRouteTag(TencentUnitContext.CLOUD_SPACE_ROUTE_GATEWAY)) {
|
||||||
|
UnitArch.Gateway gateway = (UnitArch.Gateway) TencentUnitContext.getObjectRouteTag(TencentUnitContext.CLOUD_SPACE_ROUTE_GATEWAY);
|
||||||
|
requestTemplate.target(uri.getScheme() + "//" + gateway.getServiceName());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,74 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.plugin.unit.instrument.resttemplate;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.net.URI;
|
||||||
|
|
||||||
|
import com.tencent.cloud.common.constant.OrderConstant;
|
||||||
|
import com.tencent.cloud.plugin.unit.utils.SpringCloudUnitUtils;
|
||||||
|
import com.tencent.tsf.unit.core.TencentUnitContext;
|
||||||
|
import com.tencent.tsf.unit.core.TencentUnitManager;
|
||||||
|
import com.tencent.tsf.unit.core.model.UnitArch;
|
||||||
|
|
||||||
|
import org.springframework.core.Ordered;
|
||||||
|
import org.springframework.http.HttpRequest;
|
||||||
|
import org.springframework.http.client.ClientHttpRequestExecution;
|
||||||
|
import org.springframework.http.client.ClientHttpRequestInterceptor;
|
||||||
|
import org.springframework.http.client.ClientHttpResponse;
|
||||||
|
import org.springframework.web.util.UriComponentsBuilder;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Interceptor used for unit in RestTemplate.
|
||||||
|
*
|
||||||
|
* @author Shedfree Wu
|
||||||
|
*/
|
||||||
|
public class UnitRestTemplateInterceptor implements ClientHttpRequestInterceptor, Ordered {
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int getOrder() {
|
||||||
|
return OrderConstant.Client.RestTemplate.UNIT_INTERCEPTOR_ORDER;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @see org.springframework.http.client.ClientHttpRequestInterceptor#intercept(org.springframework.http.HttpRequest, byte[], org.springframework.http.client.ClientHttpRequestExecution)
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public ClientHttpResponse intercept(HttpRequest request, byte[] body, ClientHttpRequestExecution execution) throws IOException {
|
||||||
|
return execution.execute(getHttpRequestWrapper(request), body);
|
||||||
|
}
|
||||||
|
|
||||||
|
public HttpRequest getHttpRequestWrapper(HttpRequest httpRequest) {
|
||||||
|
// 未开启单元化, 直接返回
|
||||||
|
if (!TencentUnitManager.isEnable()) {
|
||||||
|
return httpRequest;
|
||||||
|
}
|
||||||
|
|
||||||
|
String serviceName = httpRequest.getURI().getHost();
|
||||||
|
SpringCloudUnitUtils.preRequestRecordUnitContext(serviceName);
|
||||||
|
// 不需要转发到网关, 直接返回
|
||||||
|
if (!TencentUnitContext.containRouteTag(TencentUnitContext.CLOUD_SPACE_ROUTE_GATEWAY)) {
|
||||||
|
return httpRequest;
|
||||||
|
}
|
||||||
|
|
||||||
|
UnitArch.Gateway gateway = (UnitArch.Gateway) TencentUnitContext.getObjectRouteTag(TencentUnitContext.CLOUD_SPACE_ROUTE_GATEWAY);
|
||||||
|
URI unitRouteUri = UriComponentsBuilder.fromUri(httpRequest.getURI()).host(gateway.getServiceName()).build()
|
||||||
|
.toUri();
|
||||||
|
return new UriModifyHttpRequestWrapper(httpRequest, unitRouteUri);
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,37 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.plugin.unit.instrument.resttemplate;
|
||||||
|
|
||||||
|
import java.net.URI;
|
||||||
|
|
||||||
|
import org.springframework.http.HttpRequest;
|
||||||
|
import org.springframework.http.client.support.HttpRequestWrapper;
|
||||||
|
|
||||||
|
public class UriModifyHttpRequestWrapper extends HttpRequestWrapper {
|
||||||
|
|
||||||
|
private final URI uri;
|
||||||
|
|
||||||
|
public UriModifyHttpRequestWrapper(HttpRequest request, URI uri) {
|
||||||
|
super(request);
|
||||||
|
this.uri = uri;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public URI getURI() {
|
||||||
|
return uri;
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,53 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.plugin.unit.plugin;
|
||||||
|
|
||||||
|
import com.tencent.cloud.rpc.enhancement.plugin.EnhancedPlugin;
|
||||||
|
import com.tencent.cloud.rpc.enhancement.plugin.EnhancedPluginContext;
|
||||||
|
import com.tencent.cloud.rpc.enhancement.plugin.EnhancedPluginType;
|
||||||
|
import com.tencent.tsf.unit.core.TencentUnitContext;
|
||||||
|
import org.slf4j.Logger;
|
||||||
|
import org.slf4j.LoggerFactory;
|
||||||
|
|
||||||
|
import org.springframework.core.Ordered;
|
||||||
|
|
||||||
|
public class UnitClientFinallyEnhancedPlugin implements EnhancedPlugin {
|
||||||
|
|
||||||
|
private static final Logger LOG = LoggerFactory.getLogger(UnitClientFinallyEnhancedPlugin.class);
|
||||||
|
|
||||||
|
public UnitClientFinallyEnhancedPlugin() {
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public EnhancedPluginType getType() {
|
||||||
|
return EnhancedPluginType.Client.FINALLY;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void run(EnhancedPluginContext context) throws Throwable {
|
||||||
|
if (LOG.isDebugEnabled()) {
|
||||||
|
LOG.debug("clean unit context, unit context:{}", TencentUnitContext.getOriginCompositeContextMap());
|
||||||
|
}
|
||||||
|
TencentUnitContext.removeAll();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int getOrder() {
|
||||||
|
return Ordered.LOWEST_PRECEDENCE;
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,108 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.plugin.unit.plugin;
|
||||||
|
|
||||||
|
import java.util.Collection;
|
||||||
|
import java.util.Collections;
|
||||||
|
import java.util.LinkedHashMap;
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
|
import com.tencent.cloud.common.constant.MetadataConstant;
|
||||||
|
import com.tencent.cloud.common.util.JacksonUtils;
|
||||||
|
import com.tencent.cloud.common.util.ReflectionUtils;
|
||||||
|
import com.tencent.cloud.common.util.UrlUtils;
|
||||||
|
import com.tencent.cloud.rpc.enhancement.plugin.EnhancedPlugin;
|
||||||
|
import com.tencent.cloud.rpc.enhancement.plugin.EnhancedPluginContext;
|
||||||
|
import com.tencent.cloud.rpc.enhancement.plugin.EnhancedPluginType;
|
||||||
|
import com.tencent.cloud.rpc.enhancement.plugin.PluginOrderConstant;
|
||||||
|
import com.tencent.tsf.unit.core.TencentUnitContext;
|
||||||
|
import feign.Request;
|
||||||
|
import shade.polaris.com.google.common.collect.ImmutableMap;
|
||||||
|
|
||||||
|
import org.springframework.util.CollectionUtils;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Pre EnhancedPlugin for feign to encode unit metadata.
|
||||||
|
*
|
||||||
|
* @author Shedfree Wu
|
||||||
|
*/
|
||||||
|
public class UnitFeignEnhancedPlugin implements EnhancedPlugin {
|
||||||
|
@Override
|
||||||
|
public EnhancedPluginType getType() {
|
||||||
|
return EnhancedPluginType.Client.BEFORE_CALLING;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void run(EnhancedPluginContext context) throws Throwable {
|
||||||
|
if (!(context.getOriginRequest() instanceof Request request)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
TencentUnitContext.UnitCompositeContextMap unitCompositeContextMap = TencentUnitContext.getOriginCompositeContextMap();
|
||||||
|
if (!com.tencent.polaris.api.utils.CollectionUtils.isEmpty(unitCompositeContextMap.getSystemContext())) {
|
||||||
|
buildMetadataHeader(request, unitCompositeContextMap.getSystemContext(), MetadataConstant.HeaderName.TSF_UNIT);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set metadata into the request header for {@link Request} .
|
||||||
|
* @param request instance of {@link Request}
|
||||||
|
* @param metadata metadata map .
|
||||||
|
* @param headerName target metadata http header name .
|
||||||
|
*/
|
||||||
|
private void buildMetadataHeader(Request request, Map<String, String> metadata, String headerName) {
|
||||||
|
if (!CollectionUtils.isEmpty(metadata)) {
|
||||||
|
buildHeaderMap(request, ImmutableMap.of(headerName, JacksonUtils.serialize2Json(metadata)));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set headerMap into the request header for {@link Request} .
|
||||||
|
* @param request instance of {@link Request}
|
||||||
|
* @param headerMap header map .
|
||||||
|
*/
|
||||||
|
private void buildHeaderMap(Request request, Map<String, String> headerMap) {
|
||||||
|
if (!CollectionUtils.isEmpty(headerMap)) {
|
||||||
|
Map<String, Collection<String>> headers = getModifiableHeaders(request);
|
||||||
|
headerMap.forEach((key, value) -> headers.put(key, Collections.singletonList(UrlUtils.encode(value))));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The value obtained directly from the headers method is an unmodifiable map.
|
||||||
|
* If the Feign client uses the URL, the original headers are unmodifiable.
|
||||||
|
* @param request feign request
|
||||||
|
* @return modifiable headers
|
||||||
|
*/
|
||||||
|
private Map<String, Collection<String>> getModifiableHeaders(Request request) {
|
||||||
|
Map<String, Collection<String>> headers;
|
||||||
|
headers = (Map<String, Collection<String>>) ReflectionUtils.getFieldValue(request, "headers");
|
||||||
|
|
||||||
|
if (!(headers instanceof LinkedHashMap)) {
|
||||||
|
headers = new LinkedHashMap<>(headers);
|
||||||
|
ReflectionUtils.setFieldValue(request, "headers", headers);
|
||||||
|
}
|
||||||
|
return headers;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int getOrder() {
|
||||||
|
return PluginOrderConstant.ClientPluginOrder.CONSUMER_UNIT_METADATA_PLUGIN_ORDER;
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,81 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.plugin.unit.plugin;
|
||||||
|
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
|
import com.tencent.cloud.common.constant.MetadataConstant;
|
||||||
|
import com.tencent.cloud.common.util.JacksonUtils;
|
||||||
|
import com.tencent.cloud.common.util.UrlUtils;
|
||||||
|
import com.tencent.cloud.rpc.enhancement.plugin.EnhancedPlugin;
|
||||||
|
import com.tencent.cloud.rpc.enhancement.plugin.EnhancedPluginContext;
|
||||||
|
import com.tencent.cloud.rpc.enhancement.plugin.EnhancedPluginType;
|
||||||
|
import com.tencent.cloud.rpc.enhancement.plugin.PluginOrderConstant;
|
||||||
|
import com.tencent.polaris.api.utils.CollectionUtils;
|
||||||
|
import com.tencent.tsf.unit.core.TencentUnitContext;
|
||||||
|
import shade.polaris.com.google.common.collect.ImmutableMap;
|
||||||
|
|
||||||
|
import org.springframework.http.HttpRequest;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Pre EnhancedPlugin for rest template to encode unit metadata.
|
||||||
|
*
|
||||||
|
* @author Shedfree Wu
|
||||||
|
*/
|
||||||
|
public class UnitRestTemplateEnhancedPlugin implements EnhancedPlugin {
|
||||||
|
@Override
|
||||||
|
public EnhancedPluginType getType() {
|
||||||
|
return EnhancedPluginType.Client.BEFORE_CALLING;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void run(EnhancedPluginContext context) throws Throwable {
|
||||||
|
if (!(context.getOriginRequest() instanceof HttpRequest httpRequest)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
TencentUnitContext.UnitCompositeContextMap unitCompositeContextMap = TencentUnitContext.getOriginCompositeContextMap();
|
||||||
|
if (!CollectionUtils.isEmpty(unitCompositeContextMap.getSystemContext())) {
|
||||||
|
buildMetadataHeader(httpRequest, unitCompositeContextMap.getSystemContext(), MetadataConstant.HeaderName.TSF_UNIT);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private void buildHeaderMap(HttpRequest request, Map<String, String> headerMap) {
|
||||||
|
if (!CollectionUtils.isEmpty(headerMap)) {
|
||||||
|
headerMap.forEach((key, value) -> request.getHeaders().set(key, UrlUtils.encode(value)));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set metadata into the request header for {@link HttpRequest} .
|
||||||
|
*
|
||||||
|
* @param request instance of {@link HttpRequest}
|
||||||
|
* @param metadata metadata map .
|
||||||
|
* @param headerName target metadata http header name .
|
||||||
|
*/
|
||||||
|
private void buildMetadataHeader(HttpRequest request, Map<String, String> metadata, String headerName) {
|
||||||
|
if (!CollectionUtils.isEmpty(metadata)) {
|
||||||
|
buildHeaderMap(request, ImmutableMap.of(headerName, JacksonUtils.serialize2Json(metadata)));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int getOrder() {
|
||||||
|
return PluginOrderConstant.ClientPluginOrder.CONSUMER_UNIT_METADATA_PLUGIN_ORDER;
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,86 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.plugin.unit.plugin;
|
||||||
|
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
|
import com.tencent.cloud.common.constant.MetadataConstant;
|
||||||
|
import com.tencent.cloud.common.util.JacksonUtils;
|
||||||
|
import com.tencent.cloud.common.util.UrlUtils;
|
||||||
|
import com.tencent.cloud.rpc.enhancement.plugin.EnhancedPlugin;
|
||||||
|
import com.tencent.cloud.rpc.enhancement.plugin.EnhancedPluginContext;
|
||||||
|
import com.tencent.cloud.rpc.enhancement.plugin.EnhancedPluginType;
|
||||||
|
import com.tencent.cloud.rpc.enhancement.plugin.PluginOrderConstant;
|
||||||
|
import com.tencent.tsf.unit.core.TencentUnitContext;
|
||||||
|
import shade.polaris.com.google.common.collect.ImmutableMap;
|
||||||
|
|
||||||
|
import org.springframework.http.server.reactive.ServerHttpRequest;
|
||||||
|
import org.springframework.util.CollectionUtils;
|
||||||
|
import org.springframework.web.server.ServerWebExchange;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Pre EnhancedPlugin for scg to encode unit metadata.
|
||||||
|
*
|
||||||
|
* @author Shedfree Wu
|
||||||
|
*/
|
||||||
|
public class UnitScgEnhancedPlugin implements EnhancedPlugin {
|
||||||
|
@Override
|
||||||
|
public EnhancedPluginType getType() {
|
||||||
|
return EnhancedPluginType.Client.PRE;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void run(EnhancedPluginContext context) throws Throwable {
|
||||||
|
if (!(context.getOriginRequest() instanceof ServerWebExchange exchange)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// get request builder
|
||||||
|
ServerHttpRequest.Builder builder = exchange.getRequest().mutate();
|
||||||
|
|
||||||
|
TencentUnitContext.UnitCompositeContextMap unitCompositeContextMap = TencentUnitContext.getOriginCompositeContextMap();
|
||||||
|
if (!com.tencent.polaris.api.utils.CollectionUtils.isEmpty(unitCompositeContextMap.getSystemContext())) {
|
||||||
|
buildMetadataHeader(builder, unitCompositeContextMap.getSystemContext(), MetadataConstant.HeaderName.TSF_UNIT);
|
||||||
|
}
|
||||||
|
|
||||||
|
context.setOriginRequest(exchange.mutate().request(builder.build()).build());
|
||||||
|
}
|
||||||
|
|
||||||
|
private void buildHeaderMap(ServerHttpRequest.Builder builder, Map<String, String> headerMap) {
|
||||||
|
if (!CollectionUtils.isEmpty(headerMap)) {
|
||||||
|
headerMap.forEach((key, value) -> builder.header(key, UrlUtils.encode(value)));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set metadata into the request header for {@link ServerHttpRequest.Builder} .
|
||||||
|
* @param builder instance of {@link ServerHttpRequest.Builder}
|
||||||
|
* @param metadata metadata map .
|
||||||
|
* @param headerName target metadata http header name .
|
||||||
|
*/
|
||||||
|
private void buildMetadataHeader(ServerHttpRequest.Builder builder, Map<String, String> metadata, String headerName) {
|
||||||
|
if (!CollectionUtils.isEmpty(metadata)) {
|
||||||
|
buildHeaderMap(builder, ImmutableMap.of(headerName, JacksonUtils.serialize2Json(metadata)));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int getOrder() {
|
||||||
|
return PluginOrderConstant.ClientPluginOrder.CONSUMER_UNIT_METADATA_PLUGIN_ORDER;
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,99 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.plugin.unit.plugin;
|
||||||
|
|
||||||
|
import java.net.URLDecoder;
|
||||||
|
import java.nio.charset.StandardCharsets;
|
||||||
|
import java.util.Map;
|
||||||
|
import java.util.Optional;
|
||||||
|
|
||||||
|
import com.tencent.cloud.common.constant.MetadataConstant;
|
||||||
|
import com.tencent.cloud.common.util.JacksonUtils;
|
||||||
|
import com.tencent.cloud.rpc.enhancement.plugin.EnhancedPlugin;
|
||||||
|
import com.tencent.cloud.rpc.enhancement.plugin.EnhancedPluginContext;
|
||||||
|
import com.tencent.cloud.rpc.enhancement.plugin.EnhancedPluginType;
|
||||||
|
import com.tencent.cloud.rpc.enhancement.plugin.PluginOrderConstant;
|
||||||
|
import com.tencent.polaris.api.utils.StringUtils;
|
||||||
|
import com.tencent.tsf.unit.core.TencentUnitContext;
|
||||||
|
import com.tencent.tsf.unit.core.TencentUnitManager;
|
||||||
|
import com.tencent.tsf.unit.core.model.UnitTagPosition;
|
||||||
|
import jakarta.servlet.http.HttpServletRequest;
|
||||||
|
import org.slf4j.Logger;
|
||||||
|
import org.slf4j.LoggerFactory;
|
||||||
|
|
||||||
|
public class UnitServletPreEnhancedPlugin implements EnhancedPlugin {
|
||||||
|
private static final Logger logger = LoggerFactory.getLogger(UnitServletPreEnhancedPlugin.class);
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public EnhancedPluginType getType() {
|
||||||
|
return EnhancedPluginType.Server.PRE;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void run(EnhancedPluginContext context) throws Throwable {
|
||||||
|
if (!(context.getOriginRequest() instanceof HttpServletRequest httpServletRequest)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!TencentUnitManager.isEnable()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
TencentUnitContext.removeAll();
|
||||||
|
|
||||||
|
String unitContextEncoded = httpServletRequest.getHeader(MetadataConstant.HeaderName.TSF_UNIT);
|
||||||
|
if (StringUtils.isNotEmpty(unitContextEncoded)) {
|
||||||
|
Map<String, String> unitMap = JacksonUtils.deserialize2Map(URLDecoder.decode(unitContextEncoded, StandardCharsets.UTF_8));
|
||||||
|
|
||||||
|
TencentUnitContext.putSourceTags(unitMap);
|
||||||
|
if (TencentUnitManager.isContextPassingThroughEnabled()) {
|
||||||
|
// 不能传递所有的 key, 只需要传递客户要素和业务系统,灰度信息
|
||||||
|
Optional.ofNullable(unitMap.get(TencentUnitContext.CLOUD_SPACE_CUSTOMER_IDENTIFIER)).
|
||||||
|
ifPresent(value -> TencentUnitContext.putSystemTag(TencentUnitContext.CLOUD_SPACE_CUSTOMER_IDENTIFIER, value));
|
||||||
|
Optional.ofNullable(unitMap.get(TencentUnitContext.CLOUD_SPACE_TARGET_SYSTEM)).
|
||||||
|
ifPresent(value -> TencentUnitContext.putSystemTag(TencentUnitContext.CLOUD_SPACE_TARGET_SYSTEM, value));
|
||||||
|
Optional.ofNullable(unitMap.get(TencentUnitContext.CLOUD_SPACE_GRAY_UNIT_INFO)).
|
||||||
|
ifPresent(value -> TencentUnitContext.putSystemTag(TencentUnitContext.CLOUD_SPACE_GRAY_UNIT_INFO, value));
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
// 没有 passing through 标志,灰度信息也要透传
|
||||||
|
Optional.ofNullable(unitMap.get(TencentUnitContext.CLOUD_SPACE_GRAY_UNIT_INFO)).
|
||||||
|
ifPresent(value -> TencentUnitContext.putSystemTag(TencentUnitContext.CLOUD_SPACE_GRAY_UNIT_INFO, value));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
for (String grayKey : TencentUnitManager.getGrayUnitHeaderKey()) {
|
||||||
|
String value = httpServletRequest.getHeader(grayKey);
|
||||||
|
// 非空 value 才设置,便于匹配灰度规则时能否直接跳过
|
||||||
|
if (StringUtils.isNotEmpty(value)) {
|
||||||
|
TencentUnitContext.putGrayUserTag(UnitTagPosition.HEADER.name(), grayKey, value);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (logger.isDebugEnabled()) {
|
||||||
|
logger.debug("[getSerializeTagsFromRequestMeta] unit context:{}",
|
||||||
|
TencentUnitContext.getOriginCompositeContextMap());
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int getOrder() {
|
||||||
|
return PluginOrderConstant.ServerPluginOrder.TRACE_SERVER_PRE_PLUGIN_ORDER;
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,69 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.tsf.unit.core;
|
||||||
|
|
||||||
|
import com.tencent.polaris.api.utils.IPAddressUtils;
|
||||||
|
|
||||||
|
public final class Env {
|
||||||
|
|
||||||
|
private Env() {
|
||||||
|
}
|
||||||
|
|
||||||
|
private final static String consulToken;
|
||||||
|
|
||||||
|
private final static String consulHost;
|
||||||
|
|
||||||
|
private final static Integer consulPort;
|
||||||
|
|
||||||
|
private final static String namespaceId;
|
||||||
|
|
||||||
|
static {
|
||||||
|
// 只支持从环境变量取
|
||||||
|
consulHost = IPAddressUtils.getIpCompatible(getSystemProperty("tsf_consul_ip", "localhost"));
|
||||||
|
consulPort = Integer.parseInt(getSystemProperty("tsf_consul_port", "8500"));
|
||||||
|
consulToken = getSystemProperty("tsf_token", "");
|
||||||
|
namespaceId = getSystemProperty("tsf_namespace_id", "");
|
||||||
|
}
|
||||||
|
|
||||||
|
private static String getSystemProperty(String name, String defaultValue) {
|
||||||
|
String val = null;
|
||||||
|
if (System.getenv(name) != null) {
|
||||||
|
val = System.getenv(name);
|
||||||
|
}
|
||||||
|
if (System.getProperty(name) != null) {
|
||||||
|
val = System.getProperty(name);
|
||||||
|
}
|
||||||
|
return (val == null) ? defaultValue : val;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static String getConsulToken() {
|
||||||
|
return consulToken;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static String getConsulHost() {
|
||||||
|
return consulHost;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Integer getConsulPort() {
|
||||||
|
return consulPort;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static String getNamespaceId() {
|
||||||
|
return namespaceId;
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,89 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.tsf.unit.core;
|
||||||
|
|
||||||
|
import java.util.Map;
|
||||||
|
import java.util.Objects;
|
||||||
|
|
||||||
|
import com.tencent.polaris.api.utils.StringUtils;
|
||||||
|
import com.tencent.tsf.unit.core.model.UnitArch.Gateway;
|
||||||
|
import org.slf4j.Logger;
|
||||||
|
import org.slf4j.LoggerFactory;
|
||||||
|
|
||||||
|
public class GatewayUnitArchCallback implements IUnitChangeCallback {
|
||||||
|
|
||||||
|
private static final Logger LOGGER = LoggerFactory.getLogger(GatewayUnitArchCallback.class);
|
||||||
|
private final String applicationName;
|
||||||
|
|
||||||
|
public GatewayUnitArchCallback(String applicationName) {
|
||||||
|
this.applicationName = applicationName;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void callback() {
|
||||||
|
boolean enableUnit = false;
|
||||||
|
for (Map.Entry<String, Gateway> entry : TencentUnitManager.getLocalBusinessSystemGwMap().entrySet()) {
|
||||||
|
Gateway gateway = entry.getValue();
|
||||||
|
if (StringUtils.equals(applicationName, gateway.getServiceName())
|
||||||
|
&& StringUtils.equals(Env.getNamespaceId(), gateway.getNamespaceId())) {
|
||||||
|
enableUnit = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (!enableUnit) {
|
||||||
|
for (Map.Entry<String, Gateway> entry: TencentUnitManager.getLocalOnlyGwMap().entrySet()) {
|
||||||
|
Gateway gateway = entry.getValue();
|
||||||
|
if (StringUtils.equals(applicationName, gateway.getServiceName())
|
||||||
|
&& StringUtils.equals(Env.getNamespaceId(), gateway.getNamespaceId())) {
|
||||||
|
enableUnit = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (LOGGER.isDebugEnabled()) {
|
||||||
|
LOGGER.debug("[callback] enableUnit:{}, applicationName:{}, ns:{}, localBusinessSystemGwMap:{}, localOnlyGwMap:{}",
|
||||||
|
enableUnit, applicationName, Env.getNamespaceId(), TencentUnitManager.getLocalBusinessSystemGwMap(), TencentUnitManager.getLocalOnlyGwMap());
|
||||||
|
}
|
||||||
|
if (TencentUnitManager.isEnable() != enableUnit) {
|
||||||
|
LOGGER.info("[callback] unit enable change, new status:{}", enableUnit);
|
||||||
|
}
|
||||||
|
TencentUnitManager.setEnable(enableUnit);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getName() {
|
||||||
|
return this.getClass().getSimpleName();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean equals(Object o) {
|
||||||
|
if (this == o) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
if (!(o instanceof GatewayUnitArchCallback that)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
return StringUtils.equals(applicationName, that.applicationName) && StringUtils.equals(getName(), that.getName());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int hashCode() {
|
||||||
|
return Objects.hash(getName(), applicationName);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
@ -0,0 +1,26 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.tsf.unit.core;
|
||||||
|
|
||||||
|
public interface IUnitChangeCallback {
|
||||||
|
|
||||||
|
void callback();
|
||||||
|
|
||||||
|
String getName();
|
||||||
|
|
||||||
|
}
|
@ -0,0 +1,54 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.tsf.unit.core;
|
||||||
|
|
||||||
|
import java.util.Iterator;
|
||||||
|
import java.util.ServiceLoader;
|
||||||
|
|
||||||
|
import com.tencent.tsf.unit.core.mapping.api.IMappingService;
|
||||||
|
import com.tencent.tsf.unit.core.mapping.impl.CustomerMappingService;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 找到MappingService的实现.
|
||||||
|
*/
|
||||||
|
public final class MappingServiceLoader {
|
||||||
|
|
||||||
|
private MappingServiceLoader() {
|
||||||
|
}
|
||||||
|
|
||||||
|
private static IMappingService service;
|
||||||
|
|
||||||
|
static {
|
||||||
|
ServiceLoader<IMappingService> mappingServices = ServiceLoader.load(IMappingService.class);
|
||||||
|
if (mappingServices != null) {
|
||||||
|
Iterator<IMappingService> itr = mappingServices.iterator();
|
||||||
|
while (itr.hasNext()) {
|
||||||
|
service = itr.next();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// 默认实现
|
||||||
|
if (service == null) {
|
||||||
|
service = new CustomerMappingService();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static IMappingService getService() {
|
||||||
|
return service;
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,55 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.tsf.unit.core;
|
||||||
|
|
||||||
|
|
||||||
|
import com.tencent.polaris.api.utils.StringUtils;
|
||||||
|
|
||||||
|
public enum TransformAlgorithmEnum {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* hash后取模.
|
||||||
|
*/
|
||||||
|
HASHCODE,
|
||||||
|
/**
|
||||||
|
* 直接取模.
|
||||||
|
*/
|
||||||
|
MOD,
|
||||||
|
/**
|
||||||
|
* 字符串截取.
|
||||||
|
*/
|
||||||
|
SUBSTR,
|
||||||
|
/**
|
||||||
|
* 扩展用.
|
||||||
|
*/
|
||||||
|
OTHER;
|
||||||
|
|
||||||
|
public static TransformAlgorithmEnum getTransformAlgorith(String type) {
|
||||||
|
if (StringUtils.isEmpty(type)) {
|
||||||
|
return OTHER;
|
||||||
|
}
|
||||||
|
for (TransformAlgorithmEnum transformAlgorithmEnum : TransformAlgorithmEnum.values()) {
|
||||||
|
if (transformAlgorithmEnum.name().equalsIgnoreCase(type)) {
|
||||||
|
return transformAlgorithmEnum;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// 其他的当做 other
|
||||||
|
return OTHER;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
@ -0,0 +1,52 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.tsf.unit.core;
|
||||||
|
|
||||||
|
import java.util.Objects;
|
||||||
|
|
||||||
|
import com.tencent.polaris.api.utils.StringUtils;
|
||||||
|
import com.tencent.tsf.unit.core.zonefilter.TsfZoneFilterManager;
|
||||||
|
|
||||||
|
public class TsfZoneFilterUnitCallback implements IUnitChangeCallback {
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void callback() {
|
||||||
|
TsfZoneFilterManager.setDisabledZoneSet(TencentUnitManager.getDisableZoneSet());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getName() {
|
||||||
|
return this.getClass().getSimpleName();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean equals(Object o) {
|
||||||
|
if (this == o) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
if (!(o instanceof TsfZoneFilterUnitCallback that)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
return StringUtils.equals(getName(), that.getName());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int hashCode() {
|
||||||
|
return Objects.hash(getName());
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,112 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.tsf.unit.core;
|
||||||
|
|
||||||
|
|
||||||
|
import java.util.Objects;
|
||||||
|
|
||||||
|
import com.tencent.tsf.unit.core.model.UnitTagPosition;
|
||||||
|
|
||||||
|
public class UnitTag {
|
||||||
|
|
||||||
|
private UnitTagPosition tagPosition;
|
||||||
|
/**
|
||||||
|
* 标签名.
|
||||||
|
*/
|
||||||
|
private String tagField;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 标签运算符.
|
||||||
|
* 定义在 UnitTagConstant.OPERATOR
|
||||||
|
*/
|
||||||
|
private String tagOperator;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 标签的被运算对象值.
|
||||||
|
*/
|
||||||
|
private String tagValue;
|
||||||
|
|
||||||
|
public UnitTag() {
|
||||||
|
}
|
||||||
|
|
||||||
|
public UnitTag(String tagField, String tagValue) {
|
||||||
|
this.tagField = tagField;
|
||||||
|
this.tagValue = tagValue;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String toString() {
|
||||||
|
return "UnitTag{" +
|
||||||
|
"position=" + tagPosition +
|
||||||
|
", tagField='" + tagField + '\'' +
|
||||||
|
", tagOperator='" + tagOperator + '\'' +
|
||||||
|
", tagValue='" + tagValue + '\'' +
|
||||||
|
'}';
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean equals(Object o) {
|
||||||
|
if (this == o) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
if (!(o instanceof UnitTag tag)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
return Objects.equals(tagPosition, tag.tagPosition) &&
|
||||||
|
tagField.equals(tag.tagField) &&
|
||||||
|
tagOperator.equals(tag.tagOperator) &&
|
||||||
|
tagValue.equals(tag.tagValue);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int hashCode() {
|
||||||
|
return Objects.hash(tagField, tagOperator, tagValue);
|
||||||
|
}
|
||||||
|
|
||||||
|
public UnitTagPosition getTagPosition() {
|
||||||
|
return tagPosition;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setTagPosition(UnitTagPosition tagPosition) {
|
||||||
|
this.tagPosition = tagPosition;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getTagField() {
|
||||||
|
return tagField;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setTagField(String tagField) {
|
||||||
|
this.tagField = tagField;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getTagOperator() {
|
||||||
|
return tagOperator;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setTagOperator(String tagOperator) {
|
||||||
|
this.tagOperator = tagOperator;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getTagValue() {
|
||||||
|
return tagValue;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setTagValue(String tagValue) {
|
||||||
|
this.tagValue = tagValue;
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,67 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.tsf.unit.core;
|
||||||
|
|
||||||
|
public class UnitTagConstant {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 规则之间运算表达式的逻辑关系.
|
||||||
|
*/
|
||||||
|
public static class TagRuleRelation {
|
||||||
|
/**
|
||||||
|
* 与.
|
||||||
|
*/
|
||||||
|
public static final String AND = "AND";
|
||||||
|
/**
|
||||||
|
* 或.
|
||||||
|
*/
|
||||||
|
public static final String OR = "OR";
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 操作符.
|
||||||
|
*/
|
||||||
|
public static class OPERATOR {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 包含.
|
||||||
|
*/
|
||||||
|
public static final String IN = "IN";
|
||||||
|
/**
|
||||||
|
* 不包含.
|
||||||
|
*/
|
||||||
|
public static final String NOT_IN = "NOT_IN";
|
||||||
|
/**
|
||||||
|
* 等于.
|
||||||
|
*/
|
||||||
|
public static final String EQUAL = "EQUAL";
|
||||||
|
/**
|
||||||
|
* 不等于.
|
||||||
|
*/
|
||||||
|
public static final String NOT_EQUAL = "NOT_EQUAL";
|
||||||
|
/**
|
||||||
|
* 正则.
|
||||||
|
*/
|
||||||
|
public static final String REGEX = "REGEX";
|
||||||
|
/**
|
||||||
|
* 范围.
|
||||||
|
*/
|
||||||
|
public static final String RANGE = "RANGE";
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
@ -0,0 +1,49 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.tsf.unit.core.algorithm;
|
||||||
|
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
|
import com.tencent.polaris.api.utils.StringUtils;
|
||||||
|
import com.tencent.tsf.unit.core.TransformAlgorithmEnum;
|
||||||
|
|
||||||
|
public class HashCodeAlgorithm implements IUnitTransformAlgorithm {
|
||||||
|
|
||||||
|
private final Map<String, Object> options;
|
||||||
|
|
||||||
|
private final int mod;
|
||||||
|
|
||||||
|
public HashCodeAlgorithm(Map<String, Object> options) {
|
||||||
|
this.options = options;
|
||||||
|
mod = Integer.parseInt(String.valueOf(options.get("mod")));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getName() {
|
||||||
|
return TransformAlgorithmEnum.HASHCODE.name();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String transform(String cid) {
|
||||||
|
if (StringUtils.isEmpty(cid)) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
return String.valueOf(cid.hashCode() % mod);
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,25 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.tsf.unit.core.algorithm;
|
||||||
|
|
||||||
|
public interface IUnitTransformAlgorithm {
|
||||||
|
|
||||||
|
String getName();
|
||||||
|
|
||||||
|
String transform(String cid);
|
||||||
|
}
|
@ -0,0 +1,56 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.tsf.unit.core.algorithm;
|
||||||
|
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
|
import com.tencent.polaris.api.utils.StringUtils;
|
||||||
|
import com.tencent.tsf.unit.core.TransformAlgorithmEnum;
|
||||||
|
import com.tencent.tsf.unit.core.exception.ErrorCode;
|
||||||
|
import com.tencent.tsf.unit.core.exception.TencentUnitException;
|
||||||
|
|
||||||
|
public class ModAlgorithm implements IUnitTransformAlgorithm {
|
||||||
|
|
||||||
|
private final Map<String, Object> options;
|
||||||
|
|
||||||
|
private final int mod;
|
||||||
|
|
||||||
|
public ModAlgorithm(Map<String, Object> options) {
|
||||||
|
this.options = options;
|
||||||
|
mod = Integer.parseInt(String.valueOf(options.get("mod")));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getName() {
|
||||||
|
return TransformAlgorithmEnum.MOD.name();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String transform(String cid) {
|
||||||
|
if (StringUtils.isEmpty(cid)) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
try {
|
||||||
|
long id = Long.parseLong(cid);
|
||||||
|
return String.valueOf(id % mod);
|
||||||
|
}
|
||||||
|
catch (Exception e) {
|
||||||
|
throw new TencentUnitException(ErrorCode.CUSTOMER_NUMBER_TRANSFORM_ERROR, "format invalid, customNumber:" + cid, e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,41 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.tsf.unit.core.algorithm;
|
||||||
|
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
|
import com.tencent.tsf.unit.core.TransformAlgorithmEnum;
|
||||||
|
|
||||||
|
public class SubstrAlgorithm implements IUnitTransformAlgorithm {
|
||||||
|
|
||||||
|
private final Map<String, Object> options;
|
||||||
|
|
||||||
|
public SubstrAlgorithm(Map<String, Object> options) {
|
||||||
|
this.options = options;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getName() {
|
||||||
|
return TransformAlgorithmEnum.SUBSTR.name();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String transform(String cid) {
|
||||||
|
return cid;
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,71 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.tsf.unit.core.exception;
|
||||||
|
|
||||||
|
public enum ErrorCode {
|
||||||
|
/**
|
||||||
|
* 内部加载配置错误.
|
||||||
|
*/
|
||||||
|
LOAD_ERROR(10000),
|
||||||
|
/**
|
||||||
|
* 客户直接或间接输入的通用参数错误.
|
||||||
|
*/
|
||||||
|
COMMON_PARAMETER_ERROR(10001),
|
||||||
|
/**
|
||||||
|
* 客户号映射服务为空.
|
||||||
|
*/
|
||||||
|
MAPPING_SERVICE_EMPTY_ERROR(10002),
|
||||||
|
/**
|
||||||
|
* 客户号映射服务的 url 为空.
|
||||||
|
*/
|
||||||
|
MAPPING_URL_EMPTY_ERROR(10003),
|
||||||
|
/**
|
||||||
|
* 客户号映射服务的响应码错误.
|
||||||
|
*/
|
||||||
|
MAPPING_RESPONSE_CODE_ERROR(10004),
|
||||||
|
/**
|
||||||
|
* 客户号映射服务的响应体空错误.
|
||||||
|
*/
|
||||||
|
MAPPING_RESPONSE_EMPTY_BODY_ERROR(10005),
|
||||||
|
/**
|
||||||
|
* 客户号服务响应体解析后无 customer number.
|
||||||
|
*/
|
||||||
|
MAPPING_RESPONSE_CUSTOMER_NUMBER_EMPTY_ERROR(10006),
|
||||||
|
/**
|
||||||
|
* 客户号服务请求出现 IO 错误.
|
||||||
|
*/
|
||||||
|
MAPPING_REQUEST_IO_ERROR(10007),
|
||||||
|
/**
|
||||||
|
* 客户号转换错误.
|
||||||
|
*/
|
||||||
|
CUSTOMER_NUMBER_TRANSFORM_ERROR(10008),
|
||||||
|
/**
|
||||||
|
* 客户要素解析错误.
|
||||||
|
*/
|
||||||
|
CUSTOMER_IDENTIFIER_TRANSFORM_ERROR(10009);
|
||||||
|
|
||||||
|
private final int code;
|
||||||
|
|
||||||
|
ErrorCode(int code) {
|
||||||
|
this.code = code;
|
||||||
|
}
|
||||||
|
|
||||||
|
public int getCode() {
|
||||||
|
return code;
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,52 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.tsf.unit.core.exception;
|
||||||
|
|
||||||
|
public class TencentUnitException extends RuntimeException {
|
||||||
|
|
||||||
|
private final ErrorCode code;
|
||||||
|
|
||||||
|
public TencentUnitException(ErrorCode code) {
|
||||||
|
this.code = code;
|
||||||
|
}
|
||||||
|
|
||||||
|
public TencentUnitException(ErrorCode code, String message) {
|
||||||
|
super(message);
|
||||||
|
this.code = code;
|
||||||
|
}
|
||||||
|
|
||||||
|
public TencentUnitException(ErrorCode code, String message, Throwable cause) {
|
||||||
|
super(message, cause);
|
||||||
|
this.code = code;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getMessage() {
|
||||||
|
StringBuilder builder = new StringBuilder(String.format("ERR-%d(%s): ", code.getCode(), code.name()));
|
||||||
|
builder.append(super.getMessage());
|
||||||
|
Throwable cause = getCause();
|
||||||
|
if (null != cause) {
|
||||||
|
builder.append(", cause: ").append(cause.getMessage());
|
||||||
|
}
|
||||||
|
return builder.toString();
|
||||||
|
}
|
||||||
|
|
||||||
|
public ErrorCode getCode() {
|
||||||
|
return code;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
@ -0,0 +1,50 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.tsf.unit.core.mapping.api;
|
||||||
|
|
||||||
|
import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
|
||||||
|
|
||||||
|
@JsonIgnoreProperties(ignoreUnknown = true)
|
||||||
|
public class MappingEntity {
|
||||||
|
|
||||||
|
// 客户号
|
||||||
|
private String customerNumber;
|
||||||
|
|
||||||
|
public MappingEntity() {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
public MappingEntity(String customerNumber) {
|
||||||
|
this.customerNumber = customerNumber;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getCustomerNumber() {
|
||||||
|
return customerNumber;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setCustomerNumber(String customerNumber) {
|
||||||
|
this.customerNumber = customerNumber;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String toString() {
|
||||||
|
return "MappingEntity{" +
|
||||||
|
"customerNumber='" + customerNumber + '\'' +
|
||||||
|
'}';
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,112 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.tsf.unit.core.mapping.impl;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.util.concurrent.TimeUnit;
|
||||||
|
|
||||||
|
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||||
|
import com.tencent.polaris.api.utils.StringUtils;
|
||||||
|
import com.tencent.tsf.unit.core.TencentUnitManager;
|
||||||
|
import com.tencent.tsf.unit.core.exception.ErrorCode;
|
||||||
|
import com.tencent.tsf.unit.core.exception.TencentUnitException;
|
||||||
|
import com.tencent.tsf.unit.core.mapping.api.IMappingService;
|
||||||
|
import com.tencent.tsf.unit.core.mapping.api.MappingEntity;
|
||||||
|
import org.slf4j.Logger;
|
||||||
|
import org.slf4j.LoggerFactory;
|
||||||
|
import shade.polaris.okhttp3.HttpUrl;
|
||||||
|
import shade.polaris.okhttp3.OkHttpClient;
|
||||||
|
import shade.polaris.okhttp3.Request;
|
||||||
|
import shade.polaris.okhttp3.Response;
|
||||||
|
|
||||||
|
public class CustomerMappingService implements IMappingService {
|
||||||
|
|
||||||
|
private static final String DEFAULT_ROUTER_IDENTIFIER_QUERY_KEY = "RouterIdentifier";
|
||||||
|
|
||||||
|
private static final Logger LOG = LoggerFactory.getLogger(CustomerMappingService.class);
|
||||||
|
|
||||||
|
// 连接超时=2s,请求超时=2s
|
||||||
|
private final OkHttpClient client = new OkHttpClient.Builder().
|
||||||
|
connectTimeout(2, TimeUnit.SECONDS).readTimeout(2, TimeUnit.SECONDS).build();
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public MappingEntity processMapping(String params) {
|
||||||
|
String mappingUrl = getMappingUrl();
|
||||||
|
if (StringUtils.isEmpty(mappingUrl)) {
|
||||||
|
String msg = "[MappingService] mapping url is null";
|
||||||
|
LOG.warn(msg);
|
||||||
|
throw new TencentUnitException(ErrorCode.MAPPING_URL_EMPTY_ERROR, msg);
|
||||||
|
}
|
||||||
|
|
||||||
|
// params解析
|
||||||
|
String url = urlBuild(mappingUrl, params);
|
||||||
|
Request request = new Request.Builder().url(url).build();
|
||||||
|
try {
|
||||||
|
Response response = client.newCall(request).execute();
|
||||||
|
if (!response.isSuccessful()) {
|
||||||
|
String msg = String.format("request fail. url:%s, code:%s, err:%s",
|
||||||
|
url, response.code(), response.message());
|
||||||
|
LOG.error("[CustomerMappingService] " + msg);
|
||||||
|
if (response.body() != null) {
|
||||||
|
response.body().close();
|
||||||
|
}
|
||||||
|
throw new TencentUnitException(ErrorCode.MAPPING_RESPONSE_CODE_ERROR, msg);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (response.body() == null) {
|
||||||
|
String msg = String.format("response body is null. url:%s", url);
|
||||||
|
LOG.error("[CustomerMappingService] " + msg);
|
||||||
|
throw new TencentUnitException(ErrorCode.MAPPING_RESPONSE_EMPTY_BODY_ERROR, msg);
|
||||||
|
}
|
||||||
|
|
||||||
|
ObjectMapper objectMapper = new ObjectMapper();
|
||||||
|
MappingEntity entity = objectMapper.readValue(response.body().string(), MappingEntity.class);
|
||||||
|
response.body().close();
|
||||||
|
return entity;
|
||||||
|
}
|
||||||
|
catch (IOException e) {
|
||||||
|
String msg = String.format("occur IOException. url:%s, err:%s", url, e);
|
||||||
|
if (LOG.isDebugEnabled()) {
|
||||||
|
LOG.error("[CustomerMappingService] " + msg, e);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
LOG.error("[CustomerMappingService] " + msg);
|
||||||
|
}
|
||||||
|
throw new TencentUnitException(ErrorCode.MAPPING_REQUEST_IO_ERROR, msg, e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private String urlBuild(String mappingUrl, String params) {
|
||||||
|
if (params == null) {
|
||||||
|
return mappingUrl;
|
||||||
|
}
|
||||||
|
|
||||||
|
HttpUrl.Builder urlBuilder = HttpUrl.get(mappingUrl).newBuilder();
|
||||||
|
if (StringUtils.isNotEmpty(params)) {
|
||||||
|
urlBuilder.addQueryParameter(DEFAULT_ROUTER_IDENTIFIER_QUERY_KEY, params);
|
||||||
|
}
|
||||||
|
return urlBuilder.build().toString();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 每次都从配置中获取.
|
||||||
|
*/
|
||||||
|
public String getMappingUrl() {
|
||||||
|
return TencentUnitManager.getLocalCloudMappingApi();
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,446 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.tsf.unit.core.model;
|
||||||
|
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 详细定义参考 iwiki /p/4009047246.
|
||||||
|
*/
|
||||||
|
public class UnitArch {
|
||||||
|
|
||||||
|
private TencentUnitArch tencent;
|
||||||
|
|
||||||
|
public TencentUnitArch getTencent() {
|
||||||
|
return tencent;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setTencent(TencentUnitArch tencent) {
|
||||||
|
this.tencent = tencent;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class TencentUnitArch {
|
||||||
|
private UnitCloudArch unitCloudArchitecture;
|
||||||
|
|
||||||
|
public UnitCloudArch getUnitCloudArchitecture() {
|
||||||
|
return unitCloudArchitecture;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setUnitCloudArchitecture(UnitCloudArch unitCloudArchitecture) {
|
||||||
|
this.unitCloudArchitecture = unitCloudArchitecture;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class UnitCloudArch {
|
||||||
|
|
||||||
|
private String localCloudId;
|
||||||
|
|
||||||
|
private List<CloudSpace> cloudSpaces;
|
||||||
|
|
||||||
|
private List<BusinessSystem> businessSystems;
|
||||||
|
|
||||||
|
public String getLocalCloudId() {
|
||||||
|
return localCloudId;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setLocalCloudId(String localCloudId) {
|
||||||
|
this.localCloudId = localCloudId;
|
||||||
|
}
|
||||||
|
|
||||||
|
public List<CloudSpace> getCloudSpaces() {
|
||||||
|
return cloudSpaces;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setCloudSpaces(List<CloudSpace> cloudSpaces) {
|
||||||
|
this.cloudSpaces = cloudSpaces;
|
||||||
|
}
|
||||||
|
|
||||||
|
public List<BusinessSystem> getBusinessSystems() {
|
||||||
|
return businessSystems;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setBusinessSystems(
|
||||||
|
List<BusinessSystem> businessSystems) {
|
||||||
|
this.businessSystems = businessSystems;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class CloudSpace {
|
||||||
|
private String cloudId;
|
||||||
|
|
||||||
|
private String cloudName;
|
||||||
|
|
||||||
|
private String regionId;
|
||||||
|
|
||||||
|
private String RegionName;
|
||||||
|
|
||||||
|
private List<Sdu> sdus;
|
||||||
|
|
||||||
|
private List<Gdu> gdus;
|
||||||
|
|
||||||
|
private List<Sdu> graySdus;
|
||||||
|
|
||||||
|
private List<Gdu> grayGdus;
|
||||||
|
|
||||||
|
private List<Gateway> gateways;
|
||||||
|
|
||||||
|
private List<Gateway> scopeGateways;
|
||||||
|
|
||||||
|
private String mappingServiceUrl;
|
||||||
|
|
||||||
|
public String getCloudId() {
|
||||||
|
return cloudId;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setCloudId(String cloudId) {
|
||||||
|
this.cloudId = cloudId;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getCloudName() {
|
||||||
|
return cloudName;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setCloudName(String cloudName) {
|
||||||
|
this.cloudName = cloudName;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getRegionId() {
|
||||||
|
return regionId;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setRegionId(String regionId) {
|
||||||
|
this.regionId = regionId;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getRegionName() {
|
||||||
|
return RegionName;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setRegionName(String regionName) {
|
||||||
|
RegionName = regionName;
|
||||||
|
}
|
||||||
|
|
||||||
|
public List<Sdu> getSdus() {
|
||||||
|
return sdus;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setSdus(List<Sdu> sdus) {
|
||||||
|
this.sdus = sdus;
|
||||||
|
}
|
||||||
|
|
||||||
|
public List<Gdu> getGdus() {
|
||||||
|
return gdus;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setGdus(List<Gdu> gdus) {
|
||||||
|
this.gdus = gdus;
|
||||||
|
}
|
||||||
|
|
||||||
|
public List<Sdu> getGraySdus() {
|
||||||
|
return graySdus;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setGraySdus(List<Sdu> graySdus) {
|
||||||
|
this.graySdus = graySdus;
|
||||||
|
}
|
||||||
|
|
||||||
|
public List<Gdu> getGrayGdus() {
|
||||||
|
return grayGdus;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setGrayGdus(List<Gdu> grayGdus) {
|
||||||
|
this.grayGdus = grayGdus;
|
||||||
|
}
|
||||||
|
|
||||||
|
public List<Gateway> getGateways() {
|
||||||
|
return gateways;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setGateways(List<Gateway> gateways) {
|
||||||
|
this.gateways = gateways;
|
||||||
|
}
|
||||||
|
|
||||||
|
public List<Gateway> getScopeGateways() {
|
||||||
|
return scopeGateways;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setScopeGateways(List<Gateway> scopeGateways) {
|
||||||
|
this.scopeGateways = scopeGateways;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getMappingServiceUrl() {
|
||||||
|
return mappingServiceUrl;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setMappingServiceUrl(String mappingServiceUrl) {
|
||||||
|
this.mappingServiceUrl = mappingServiceUrl;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class Sdu extends DeploymentUnit {
|
||||||
|
private GduRule gduRule;
|
||||||
|
|
||||||
|
public GduRule getGduRule() {
|
||||||
|
return gduRule;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setGduRule(GduRule gduRule) {
|
||||||
|
this.gduRule = gduRule;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class Gdu extends DeploymentUnit {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class DeploymentUnit {
|
||||||
|
private String id;
|
||||||
|
|
||||||
|
private String name;
|
||||||
|
|
||||||
|
private String zoneId;
|
||||||
|
|
||||||
|
private String zoneName;
|
||||||
|
|
||||||
|
private List<UnitNamespace> namespaces;
|
||||||
|
|
||||||
|
public String getId() {
|
||||||
|
return id;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setId(String id) {
|
||||||
|
this.id = id;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getName() {
|
||||||
|
return name;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setName(String name) {
|
||||||
|
this.name = name;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getZoneId() {
|
||||||
|
return zoneId;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setZoneId(String zoneId) {
|
||||||
|
this.zoneId = zoneId;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getZoneName() {
|
||||||
|
return zoneName;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setZoneName(String zoneName) {
|
||||||
|
this.zoneName = zoneName;
|
||||||
|
}
|
||||||
|
|
||||||
|
public List<UnitNamespace> getNamespaces() {
|
||||||
|
return namespaces;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setNamespaces(List<UnitNamespace> namespaces) {
|
||||||
|
this.namespaces = namespaces;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class Gateway {
|
||||||
|
private String id;
|
||||||
|
|
||||||
|
private Address address;
|
||||||
|
|
||||||
|
private String businessSystemName;
|
||||||
|
|
||||||
|
private RouteScope routeScope;
|
||||||
|
|
||||||
|
private String serviceName;
|
||||||
|
|
||||||
|
private String namespaceId;
|
||||||
|
|
||||||
|
public String getId() {
|
||||||
|
return id;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setId(String id) {
|
||||||
|
this.id = id;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Address getAddress() {
|
||||||
|
return address;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setAddress(Address address) {
|
||||||
|
this.address = address;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getBusinessSystemName() {
|
||||||
|
return businessSystemName;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setBusinessSystemName(String businessSystemName) {
|
||||||
|
this.businessSystemName = businessSystemName;
|
||||||
|
}
|
||||||
|
|
||||||
|
public RouteScope getRouteScope() {
|
||||||
|
return routeScope;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setRouteScope(RouteScope routeScope) {
|
||||||
|
this.routeScope = routeScope;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getServiceName() {
|
||||||
|
return serviceName;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setServiceName(String serviceName) {
|
||||||
|
this.serviceName = serviceName;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getNamespaceId() {
|
||||||
|
return namespaceId;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setNamespaceId(String namespaceId) {
|
||||||
|
this.namespaceId = namespaceId;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String toString() {
|
||||||
|
return "Gateway{" +
|
||||||
|
"id='" + id + '\'' +
|
||||||
|
", address=" + address +
|
||||||
|
", businessSystemName='" + businessSystemName + '\'' +
|
||||||
|
", serviceName='" + serviceName + '\'' +
|
||||||
|
", namespaceId='" + namespaceId + '\'' +
|
||||||
|
'}';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class Address {
|
||||||
|
private String host;
|
||||||
|
|
||||||
|
private String port;
|
||||||
|
|
||||||
|
public String getHost() {
|
||||||
|
return host;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setHost(String host) {
|
||||||
|
this.host = host;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getPort() {
|
||||||
|
return port;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setPort(String port) {
|
||||||
|
this.port = port;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String toString() {
|
||||||
|
return "Address{" +
|
||||||
|
"host='" + host + '\'' +
|
||||||
|
", port='" + port + '\'' +
|
||||||
|
'}';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class GduRule {
|
||||||
|
private GduRuleRoute route;
|
||||||
|
|
||||||
|
public GduRuleRoute getRoute() {
|
||||||
|
return route;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setRoute(GduRuleRoute route) {
|
||||||
|
this.route = route;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class BusinessSystem {
|
||||||
|
private String id;
|
||||||
|
|
||||||
|
private String name;
|
||||||
|
|
||||||
|
private String type;
|
||||||
|
|
||||||
|
public String getId() {
|
||||||
|
return id;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setId(String id) {
|
||||||
|
this.id = id;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getName() {
|
||||||
|
return name;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setName(String name) {
|
||||||
|
this.name = name;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getType() {
|
||||||
|
return type;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setType(String type) {
|
||||||
|
this.type = type;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class GduRuleRoute {
|
||||||
|
private String cloudSpaceId;
|
||||||
|
|
||||||
|
private String unitId;
|
||||||
|
|
||||||
|
public String getCloudSpaceId() {
|
||||||
|
return cloudSpaceId;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setCloudSpaceId(String cloudSpaceId) {
|
||||||
|
this.cloudSpaceId = cloudSpaceId;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getUnitId() {
|
||||||
|
return unitId;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setUnitId(String unitId) {
|
||||||
|
this.unitId = unitId;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public enum RouteScope {
|
||||||
|
/**
|
||||||
|
* LOCAL.
|
||||||
|
*/
|
||||||
|
LOCAL,
|
||||||
|
/**
|
||||||
|
* REMOTE.
|
||||||
|
*/
|
||||||
|
REMOTE,
|
||||||
|
/**
|
||||||
|
* LOCAL_REMOTE.
|
||||||
|
*/
|
||||||
|
LOCAL_REMOTE
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,67 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.tsf.unit.core.model;
|
||||||
|
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
|
public class UnitGray {
|
||||||
|
|
||||||
|
private TencentUnitGray tencent;
|
||||||
|
|
||||||
|
public TencentUnitGray getTencent() {
|
||||||
|
return tencent;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setTencent(TencentUnitGray tencent) {
|
||||||
|
this.tencent = tencent;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class TencentUnitGray {
|
||||||
|
private UnitGrayList unitGrayList;
|
||||||
|
|
||||||
|
public UnitGrayList getUnitGrayList() {
|
||||||
|
return unitGrayList;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setUnitGrayList(UnitGrayList unitGrayList) {
|
||||||
|
this.unitGrayList = unitGrayList;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class UnitGrayList {
|
||||||
|
private String version;
|
||||||
|
|
||||||
|
private List<String> ids;
|
||||||
|
|
||||||
|
public String getVersion() {
|
||||||
|
return version;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setVersion(String version) {
|
||||||
|
this.version = version;
|
||||||
|
}
|
||||||
|
|
||||||
|
public List<String> getIds() {
|
||||||
|
return ids;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setIds(List<String> ids) {
|
||||||
|
this.ids = ids;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,60 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.tsf.unit.core.model;
|
||||||
|
|
||||||
|
public class UnitNamespace {
|
||||||
|
|
||||||
|
private String id;
|
||||||
|
|
||||||
|
private String name;
|
||||||
|
|
||||||
|
private String businessSystemName;
|
||||||
|
|
||||||
|
public String getId() {
|
||||||
|
return id;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setId(String id) {
|
||||||
|
this.id = id;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getName() {
|
||||||
|
return name;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setName(String name) {
|
||||||
|
this.name = name;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getBusinessSystemName() {
|
||||||
|
return businessSystemName;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setBusinessSystemName(String businessSystemName) {
|
||||||
|
this.businessSystemName = businessSystemName;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String toString() {
|
||||||
|
return "UnitNamespace{" +
|
||||||
|
"id='" + id + '\'' +
|
||||||
|
", name='" + name + '\'' +
|
||||||
|
", businessSystemName='" + businessSystemName + '\'' +
|
||||||
|
'}';
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,566 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.tsf.unit.core.model;
|
||||||
|
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
|
import com.fasterxml.jackson.annotation.JsonIgnore;
|
||||||
|
import com.tencent.tsf.unit.core.UnitTag;
|
||||||
|
import com.tencent.tsf.unit.core.algorithm.IUnitTransformAlgorithm;
|
||||||
|
|
||||||
|
public class UnitRouteInfo {
|
||||||
|
|
||||||
|
private TencentUnitRouteRule tencent;
|
||||||
|
|
||||||
|
public TencentUnitRouteRule getTencent() {
|
||||||
|
return tencent;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setTencent(TencentUnitRouteRule tencent) {
|
||||||
|
this.tencent = tencent;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class TencentUnitRouteRule {
|
||||||
|
private UnitRouteRule unitRouteRule;
|
||||||
|
|
||||||
|
private List<UnitRoute> gduRouteRule;
|
||||||
|
|
||||||
|
private GrayUnitRouteRule grayUnitRouteRule;
|
||||||
|
|
||||||
|
private RouterIdentifier routerIdentifier;
|
||||||
|
|
||||||
|
public UnitRouteRule getUnitRouteRule() {
|
||||||
|
return unitRouteRule;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setUnitRouteRule(UnitRouteRule unitRouteRule) {
|
||||||
|
this.unitRouteRule = unitRouteRule;
|
||||||
|
}
|
||||||
|
|
||||||
|
public List<UnitRoute> getGduRouteRule() {
|
||||||
|
return gduRouteRule;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setGduRouteRule(List<UnitRoute> gduRouteRule) {
|
||||||
|
this.gduRouteRule = gduRouteRule;
|
||||||
|
}
|
||||||
|
|
||||||
|
public GrayUnitRouteRule getGrayUnitRouteRule() {
|
||||||
|
return grayUnitRouteRule;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setGrayUnitRouteRule(
|
||||||
|
GrayUnitRouteRule grayUnitRouteRule) {
|
||||||
|
this.grayUnitRouteRule = grayUnitRouteRule;
|
||||||
|
}
|
||||||
|
|
||||||
|
public RouterIdentifier getRouterIdentifier() {
|
||||||
|
return routerIdentifier;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setRouterIdentifier(
|
||||||
|
RouterIdentifier routerIdentifier) {
|
||||||
|
this.routerIdentifier = routerIdentifier;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class GrayUnitRouteRule {
|
||||||
|
|
||||||
|
private List<GrayUnitRoute> unitRoutes;
|
||||||
|
|
||||||
|
public List<GrayUnitRoute> getUnitRoutes() {
|
||||||
|
return unitRoutes;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setUnitRoutes(
|
||||||
|
List<GrayUnitRoute> unitRoutes) {
|
||||||
|
this.unitRoutes = unitRoutes;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class UnitRouteRule {
|
||||||
|
private String id;
|
||||||
|
|
||||||
|
private String name;
|
||||||
|
|
||||||
|
private String desc;
|
||||||
|
|
||||||
|
private Boolean passingThroughEnabled;
|
||||||
|
|
||||||
|
private List<TagTransform> tagTransforms;
|
||||||
|
|
||||||
|
private List<UnitRoute> unitRoutes;
|
||||||
|
|
||||||
|
public String getId() {
|
||||||
|
return id;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setId(String id) {
|
||||||
|
this.id = id;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getName() {
|
||||||
|
return name;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setName(String name) {
|
||||||
|
this.name = name;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getDesc() {
|
||||||
|
return desc;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setDesc(String desc) {
|
||||||
|
this.desc = desc;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Boolean getPassingThroughEnabled() {
|
||||||
|
return passingThroughEnabled;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setPassingThroughEnabled(Boolean passingThroughEnabled) {
|
||||||
|
this.passingThroughEnabled = passingThroughEnabled;
|
||||||
|
}
|
||||||
|
|
||||||
|
public List<TagTransform> getTagTransforms() {
|
||||||
|
return tagTransforms;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setTagTransforms(
|
||||||
|
List<TagTransform> tagTransforms) {
|
||||||
|
this.tagTransforms = tagTransforms;
|
||||||
|
}
|
||||||
|
|
||||||
|
public List<UnitRoute> getUnitRoutes() {
|
||||||
|
return unitRoutes;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setUnitRoutes(List<UnitRoute> unitRoutes) {
|
||||||
|
this.unitRoutes = unitRoutes;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class TagTransform {
|
||||||
|
private TagTransformLocation source;
|
||||||
|
|
||||||
|
private TransformAction transform;
|
||||||
|
|
||||||
|
private TagTransformLocation destination;
|
||||||
|
|
||||||
|
public TagTransformLocation getSource() {
|
||||||
|
return source;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setSource(TagTransformLocation source) {
|
||||||
|
this.source = source;
|
||||||
|
}
|
||||||
|
|
||||||
|
public TransformAction getTransform() {
|
||||||
|
return transform;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setTransform(TransformAction transform) {
|
||||||
|
this.transform = transform;
|
||||||
|
}
|
||||||
|
|
||||||
|
public TagTransformLocation getDestination() {
|
||||||
|
return destination;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setDestination(TagTransformLocation destination) {
|
||||||
|
this.destination = destination;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class TagTransformLocation {
|
||||||
|
private String tagName;
|
||||||
|
|
||||||
|
public String getTagName() {
|
||||||
|
return tagName;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setTagName(String tagName) {
|
||||||
|
this.tagName = tagName;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class TransformAction {
|
||||||
|
private TransformAlgorithm algorithm;
|
||||||
|
// 解析 algorithm 后放入的实际操作类
|
||||||
|
@JsonIgnore
|
||||||
|
private IUnitTransformAlgorithm unitTransformAlgorithm;
|
||||||
|
|
||||||
|
public TransformAlgorithm getAlgorithm() {
|
||||||
|
return algorithm;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setAlgorithm(TransformAlgorithm algorithm) {
|
||||||
|
this.algorithm = algorithm;
|
||||||
|
}
|
||||||
|
|
||||||
|
public IUnitTransformAlgorithm getUnitTransformAlgorithm() {
|
||||||
|
return unitTransformAlgorithm;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setUnitTransformAlgorithm(
|
||||||
|
IUnitTransformAlgorithm unitTransformAlgorithm) {
|
||||||
|
this.unitTransformAlgorithm = unitTransformAlgorithm;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class TransformAlgorithm {
|
||||||
|
private String name;
|
||||||
|
// algorithm 的操作算子,由 name 决定
|
||||||
|
private Map<String, Object> options;
|
||||||
|
|
||||||
|
public String getName() {
|
||||||
|
return name;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setName(String name) {
|
||||||
|
this.name = name;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Map<String, Object> getOptions() {
|
||||||
|
return options;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setOptions(Map<String, Object> options) {
|
||||||
|
this.options = options;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class GrayUnitRoute {
|
||||||
|
private GrayUnitRouteMatch match;
|
||||||
|
|
||||||
|
private GrayMatchRoute route;
|
||||||
|
|
||||||
|
public GrayUnitRouteMatch getMatch() {
|
||||||
|
return match;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setMatch(GrayUnitRouteMatch match) {
|
||||||
|
this.match = match;
|
||||||
|
}
|
||||||
|
|
||||||
|
public GrayMatchRoute getRoute() {
|
||||||
|
return route;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setRoute(GrayMatchRoute route) {
|
||||||
|
this.route = route;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class UnitRoute {
|
||||||
|
private UnitRouteMatch match;
|
||||||
|
|
||||||
|
private MatchRoute route;
|
||||||
|
|
||||||
|
public UnitRouteMatch getMatch() {
|
||||||
|
return match;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setMatch(UnitRouteMatch match) {
|
||||||
|
this.match = match;
|
||||||
|
}
|
||||||
|
|
||||||
|
public MatchRoute getRoute() {
|
||||||
|
return route;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setRoute(MatchRoute route) {
|
||||||
|
this.route = route;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class GrayUnitRouteMatch extends UnitRouteMatch {
|
||||||
|
private Boolean grayListEnabled;
|
||||||
|
|
||||||
|
public Boolean getGrayListEnabled() {
|
||||||
|
return grayListEnabled;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setGrayListEnabled(Boolean grayListEnabled) {
|
||||||
|
this.grayListEnabled = grayListEnabled;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class UnitRouteMatch {
|
||||||
|
private String name;
|
||||||
|
|
||||||
|
private String operator;
|
||||||
|
|
||||||
|
private List<UnitTag> conditions;
|
||||||
|
|
||||||
|
public String getName() {
|
||||||
|
return name;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setName(String name) {
|
||||||
|
this.name = name;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getOperator() {
|
||||||
|
return operator;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setOperator(String operator) {
|
||||||
|
this.operator = operator;
|
||||||
|
}
|
||||||
|
|
||||||
|
public List<UnitTag> getConditions() {
|
||||||
|
return conditions;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setConditions(List<UnitTag> conditions) {
|
||||||
|
this.conditions = conditions;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class GrayMatchRoute {
|
||||||
|
|
||||||
|
private List<GrayMatchRouteUnit> units;
|
||||||
|
|
||||||
|
public List<GrayMatchRouteUnit> getUnits() {
|
||||||
|
return units;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setUnits(
|
||||||
|
List<GrayMatchRouteUnit> units) {
|
||||||
|
this.units = units;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class GrayMatchRouteUnit {
|
||||||
|
private String id;
|
||||||
|
|
||||||
|
public String getId() {
|
||||||
|
return id;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setId(String id) {
|
||||||
|
this.id = id;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String toString() {
|
||||||
|
return "GrayMatchRouteUnit{" +
|
||||||
|
"id='" + id + '\'' +
|
||||||
|
'}';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class MatchRoute {
|
||||||
|
private String unitId;
|
||||||
|
|
||||||
|
private MatchRouteFailover failover;
|
||||||
|
|
||||||
|
public String getUnitId() {
|
||||||
|
return unitId;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setUnitId(String unitId) {
|
||||||
|
this.unitId = unitId;
|
||||||
|
}
|
||||||
|
|
||||||
|
public MatchRouteFailover getFailover() {
|
||||||
|
return failover;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setFailover(MatchRouteFailover failover) {
|
||||||
|
this.failover = failover;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getActualUnitId() {
|
||||||
|
if (failover != null && failover.getEnabled()) {
|
||||||
|
return failover.getRoute().getUnitId();
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
return unitId;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class MatchRouteFailover {
|
||||||
|
private Boolean enabled;
|
||||||
|
|
||||||
|
private FailoverRoute route;
|
||||||
|
|
||||||
|
private String scope;
|
||||||
|
|
||||||
|
public Boolean getEnabled() {
|
||||||
|
return enabled;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setEnabled(Boolean enabled) {
|
||||||
|
this.enabled = enabled;
|
||||||
|
}
|
||||||
|
|
||||||
|
public FailoverRoute getRoute() {
|
||||||
|
return route;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setRoute(FailoverRoute route) {
|
||||||
|
this.route = route;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getScope() {
|
||||||
|
return scope;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setScope(String scope) {
|
||||||
|
this.scope = scope;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class FailoverRoute {
|
||||||
|
private String unitId;
|
||||||
|
|
||||||
|
private FailoverRouteLocationFilter locationFilter;
|
||||||
|
|
||||||
|
public String getUnitId() {
|
||||||
|
return unitId;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setUnitId(String unitId) {
|
||||||
|
this.unitId = unitId;
|
||||||
|
}
|
||||||
|
|
||||||
|
public FailoverRouteLocationFilter getLocationFilter() {
|
||||||
|
return locationFilter;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setLocationFilter(FailoverRouteLocationFilter locationFilter) {
|
||||||
|
this.locationFilter = locationFilter;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class FailoverRouteLocationFilter {
|
||||||
|
private UnitRouteMatch zoneFilter;
|
||||||
|
|
||||||
|
public UnitRouteMatch getZoneFilter() {
|
||||||
|
return zoneFilter;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setZoneFilter(UnitRouteMatch zoneFilter) {
|
||||||
|
this.zoneFilter = zoneFilter;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class RouterIdentifier {
|
||||||
|
private String keySeparator;
|
||||||
|
|
||||||
|
private String keyValueSeparator;
|
||||||
|
|
||||||
|
private String shardingIdentifierKey;
|
||||||
|
|
||||||
|
private String routerIdentifierHeader;
|
||||||
|
|
||||||
|
private List<MappingService> shardingIdentifierMappingServices;
|
||||||
|
|
||||||
|
@JsonIgnore
|
||||||
|
private Map<String, MappingService> mappingServiceMap;
|
||||||
|
|
||||||
|
public RouterIdentifier() {
|
||||||
|
}
|
||||||
|
|
||||||
|
public RouterIdentifier(String keySeparator, String keyValueSeparator,
|
||||||
|
String shardingIdentifierKey,
|
||||||
|
String routerIdentifierHeader) {
|
||||||
|
this.keySeparator = keySeparator;
|
||||||
|
this.keyValueSeparator = keyValueSeparator;
|
||||||
|
this.shardingIdentifierKey = shardingIdentifierKey;
|
||||||
|
this.routerIdentifierHeader = routerIdentifierHeader;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getKeySeparator() {
|
||||||
|
return keySeparator;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setKeySeparator(String keySeparator) {
|
||||||
|
this.keySeparator = keySeparator;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getKeyValueSeparator() {
|
||||||
|
return keyValueSeparator;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setKeyValueSeparator(String keyValueSeparator) {
|
||||||
|
this.keyValueSeparator = keyValueSeparator;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getShardingIdentifierKey() {
|
||||||
|
return shardingIdentifierKey;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setShardingIdentifierKey(String shardingIdentifierKey) {
|
||||||
|
this.shardingIdentifierKey = shardingIdentifierKey;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getRouterIdentifierHeader() {
|
||||||
|
return routerIdentifierHeader;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setRouterIdentifierHeader(String routerIdentifierHeader) {
|
||||||
|
this.routerIdentifierHeader = routerIdentifierHeader;
|
||||||
|
}
|
||||||
|
|
||||||
|
public List<MappingService> getShardingIdentifierMappingServices() {
|
||||||
|
return shardingIdentifierMappingServices;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setShardingIdentifierMappingServices(
|
||||||
|
List<MappingService> shardingIdentifierMappingServices) {
|
||||||
|
this.shardingIdentifierMappingServices = shardingIdentifierMappingServices;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Map<String, MappingService> getMappingServiceMap() {
|
||||||
|
return mappingServiceMap;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setMappingServiceMap(
|
||||||
|
Map<String, MappingService> mappingServiceMap) {
|
||||||
|
this.mappingServiceMap = mappingServiceMap;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class MappingService {
|
||||||
|
private String cloudId;
|
||||||
|
|
||||||
|
private String apiPath;
|
||||||
|
|
||||||
|
public String getCloudId() {
|
||||||
|
return cloudId;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setCloudId(String cloudId) {
|
||||||
|
this.cloudId = cloudId;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getApiPath() {
|
||||||
|
return apiPath;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setApiPath(String apiPath) {
|
||||||
|
this.apiPath = apiPath;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,56 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.tsf.unit.core.model;
|
||||||
|
|
||||||
|
|
||||||
|
import com.fasterxml.jackson.annotation.JsonCreator;
|
||||||
|
|
||||||
|
public enum UnitTagPosition {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* HTTP HEADER.
|
||||||
|
*/
|
||||||
|
HEADER,
|
||||||
|
/**
|
||||||
|
* HTTP QUERY.
|
||||||
|
*/
|
||||||
|
QUERY,
|
||||||
|
/**
|
||||||
|
* HTTP COOKIE.
|
||||||
|
*/
|
||||||
|
COOKIE,
|
||||||
|
/**
|
||||||
|
* HTTP PATH.
|
||||||
|
*/
|
||||||
|
PATH,
|
||||||
|
/**
|
||||||
|
* TSF TAG.
|
||||||
|
*/
|
||||||
|
TSF_TAG;
|
||||||
|
|
||||||
|
@JsonCreator
|
||||||
|
public static UnitTagPosition fromString(String key) {
|
||||||
|
for (UnitTagPosition tagPosition : UnitTagPosition.values()) {
|
||||||
|
if (tagPosition.name().equalsIgnoreCase(key)) {
|
||||||
|
return tagPosition;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
@ -0,0 +1,29 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.tsf.unit.core.model;
|
||||||
|
|
||||||
|
public enum UnitType {
|
||||||
|
/**
|
||||||
|
* SDU.
|
||||||
|
*/
|
||||||
|
SDU,
|
||||||
|
/**
|
||||||
|
* GDU.
|
||||||
|
*/
|
||||||
|
GDU
|
||||||
|
}
|
@ -0,0 +1,105 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.tsf.unit.core.remote;
|
||||||
|
|
||||||
|
import com.ecwid.consul.v1.ConsulClient;
|
||||||
|
import com.ecwid.consul.v1.QueryParams;
|
||||||
|
import com.ecwid.consul.v1.Response;
|
||||||
|
import com.ecwid.consul.v1.kv.model.GetValue;
|
||||||
|
import com.fasterxml.jackson.core.JsonProcessingException;
|
||||||
|
import com.fasterxml.jackson.databind.DeserializationFeature;
|
||||||
|
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||||
|
import com.fasterxml.jackson.dataformat.yaml.YAMLFactory;
|
||||||
|
import com.tencent.cloud.common.util.GzipUtil;
|
||||||
|
import com.tencent.tsf.unit.core.Env;
|
||||||
|
import com.tencent.tsf.unit.core.TencentUnitManager;
|
||||||
|
import com.tencent.tsf.unit.core.model.UnitArch;
|
||||||
|
import org.slf4j.Logger;
|
||||||
|
import org.slf4j.LoggerFactory;
|
||||||
|
|
||||||
|
public final class TencentUnitArchKVLoader {
|
||||||
|
|
||||||
|
private static final Logger LOGGER = LoggerFactory.getLogger(TencentUnitArchKVLoader.class);
|
||||||
|
/**
|
||||||
|
* consul 长轮询等待时间.
|
||||||
|
*/
|
||||||
|
private final static Integer watchTime = 55;
|
||||||
|
/**
|
||||||
|
* 数据当前游标.
|
||||||
|
*/
|
||||||
|
private static Long index = -1L;
|
||||||
|
private static String rawContent;
|
||||||
|
|
||||||
|
private TencentUnitArchKVLoader() {
|
||||||
|
}
|
||||||
|
|
||||||
|
private static String getUnitArchKey() {
|
||||||
|
return "unit/cloudArchitecture/data";
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void syncUnitArch() {
|
||||||
|
String newContent = null;
|
||||||
|
try {
|
||||||
|
ConsulClient client = TsfUnitConsulManager.getConsulClient();
|
||||||
|
|
||||||
|
if (client == null) {
|
||||||
|
LOGGER.warn("[syncUnitArch] tsf unit consul client is null");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
Response<GetValue> response = client.getKVValue(getUnitArchKey(),
|
||||||
|
Env.getConsulToken(), new QueryParams(watchTime, index));
|
||||||
|
|
||||||
|
if (LOGGER.isDebugEnabled()) {
|
||||||
|
LOGGER.debug("[syncUnitArch] resp:{}", response);
|
||||||
|
}
|
||||||
|
// data not change
|
||||||
|
if (response.getConsulIndex() == null || index.equals(response.getConsulIndex())) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
index = response.getConsulIndex();
|
||||||
|
// 推空保护,启动后理论上不存在单元化配置被删除的场景
|
||||||
|
if (response.getValue() != null) {
|
||||||
|
// 控制台 gzip 压缩加 base64 转换,这里进行解压
|
||||||
|
newContent = GzipUtil.base64DecodeDecompress(response.getValue().getDecodedValue());
|
||||||
|
loadUnitArch(newContent);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
catch (Throwable t) {
|
||||||
|
if (LOGGER.isDebugEnabled()) {
|
||||||
|
LOGGER.debug("[syncUnitArch] newContent:{} error:", newContent, t);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
LOGGER.warn("[syncUnitArch] error: {}", t.getMessage());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void loadUnitArch(String content) throws JsonProcessingException {
|
||||||
|
LOGGER.info("[unit] unit arch config old raw content:\n{}", rawContent);
|
||||||
|
|
||||||
|
ObjectMapper mapper = new ObjectMapper(new YAMLFactory());
|
||||||
|
mapper.configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false);
|
||||||
|
TencentUnitManager.setUnitArch(mapper.readValue(content, UnitArch.class));
|
||||||
|
|
||||||
|
rawContent = content;
|
||||||
|
LOGGER.info("[unit] unit arch config new raw content:\n{}", rawContent);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
@ -0,0 +1,103 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.tsf.unit.core.remote;
|
||||||
|
|
||||||
|
import com.ecwid.consul.v1.ConsulClient;
|
||||||
|
import com.ecwid.consul.v1.QueryParams;
|
||||||
|
import com.ecwid.consul.v1.Response;
|
||||||
|
import com.ecwid.consul.v1.kv.model.GetValue;
|
||||||
|
import com.fasterxml.jackson.core.JsonProcessingException;
|
||||||
|
import com.fasterxml.jackson.databind.DeserializationFeature;
|
||||||
|
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||||
|
import com.fasterxml.jackson.dataformat.yaml.YAMLFactory;
|
||||||
|
import com.tencent.cloud.common.util.GzipUtil;
|
||||||
|
import com.tencent.tsf.unit.core.Env;
|
||||||
|
import com.tencent.tsf.unit.core.TencentUnitManager;
|
||||||
|
import com.tencent.tsf.unit.core.model.UnitGray;
|
||||||
|
import org.slf4j.Logger;
|
||||||
|
import org.slf4j.LoggerFactory;
|
||||||
|
|
||||||
|
public final class TencentUnitGrayKVLoader {
|
||||||
|
|
||||||
|
private static final Logger LOGGER = LoggerFactory.getLogger(TencentUnitGrayKVLoader.class);
|
||||||
|
/**
|
||||||
|
* consul 长轮询等待时间.
|
||||||
|
*/
|
||||||
|
private final static Integer watchTime = 55;
|
||||||
|
/**
|
||||||
|
* 数据当前游标.
|
||||||
|
*/
|
||||||
|
private static Long index = -1L;
|
||||||
|
private static String rawContent;
|
||||||
|
|
||||||
|
private TencentUnitGrayKVLoader() {
|
||||||
|
}
|
||||||
|
|
||||||
|
private static String getUnitGrayKey() {
|
||||||
|
return "unit/grayList/data";
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void syncUnitGray() {
|
||||||
|
String newContent = null;
|
||||||
|
try {
|
||||||
|
ConsulClient client = TsfUnitConsulManager.getConsulClient();
|
||||||
|
|
||||||
|
if (client == null) {
|
||||||
|
LOGGER.warn("[syncUnitGray] tsf unit consul client is null");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
Response<GetValue> response = client.getKVValue(getUnitGrayKey(),
|
||||||
|
Env.getConsulToken(), new QueryParams(watchTime, index));
|
||||||
|
|
||||||
|
if (LOGGER.isDebugEnabled()) {
|
||||||
|
LOGGER.debug("[syncUnitGray] resp:{}", response);
|
||||||
|
}
|
||||||
|
// data not change
|
||||||
|
if (response.getConsulIndex() == null || index.equals(response.getConsulIndex())) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
index = response.getConsulIndex();
|
||||||
|
// 推空保护,启动后理论上不存在单元化配置被删除的场景
|
||||||
|
if (response.getValue() != null) {
|
||||||
|
// 控制台 gzip 压缩加 base64 转换,这里进行解压
|
||||||
|
newContent = GzipUtil.base64DecodeDecompress(response.getValue().getDecodedValue());
|
||||||
|
loadUnitGray(newContent);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
catch (Throwable t) {
|
||||||
|
if (LOGGER.isTraceEnabled()) {
|
||||||
|
LOGGER.trace("[syncUnitGray] newContent:{} error:", newContent, t);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
LOGGER.warn("[syncUnitGray] error: {}", t.getMessage());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void loadUnitGray(String content) throws JsonProcessingException {
|
||||||
|
LOGGER.info("[unit] unit gray old raw content:\n{}", rawContent);
|
||||||
|
|
||||||
|
ObjectMapper mapper = new ObjectMapper(new YAMLFactory());
|
||||||
|
mapper.configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false);
|
||||||
|
TencentUnitManager.setUnitGray(mapper.readValue(content, UnitGray.class));
|
||||||
|
|
||||||
|
rawContent = content;
|
||||||
|
LOGGER.info("[unit] unit gray new raw content:\n{}", rawContent);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
@ -0,0 +1,103 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.tsf.unit.core.remote;
|
||||||
|
|
||||||
|
import com.ecwid.consul.v1.ConsulClient;
|
||||||
|
import com.ecwid.consul.v1.QueryParams;
|
||||||
|
import com.ecwid.consul.v1.Response;
|
||||||
|
import com.ecwid.consul.v1.kv.model.GetValue;
|
||||||
|
import com.fasterxml.jackson.core.JsonProcessingException;
|
||||||
|
import com.fasterxml.jackson.databind.DeserializationFeature;
|
||||||
|
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||||
|
import com.fasterxml.jackson.dataformat.yaml.YAMLFactory;
|
||||||
|
import com.tencent.cloud.common.util.GzipUtil;
|
||||||
|
import com.tencent.tsf.unit.core.Env;
|
||||||
|
import com.tencent.tsf.unit.core.TencentUnitManager;
|
||||||
|
import com.tencent.tsf.unit.core.model.UnitRouteInfo;
|
||||||
|
import org.slf4j.Logger;
|
||||||
|
import org.slf4j.LoggerFactory;
|
||||||
|
|
||||||
|
public final class TencentUnitRouteRuleKVLoader {
|
||||||
|
|
||||||
|
private static final Logger LOGGER = LoggerFactory.getLogger(TencentUnitRouteRuleKVLoader.class);
|
||||||
|
/**
|
||||||
|
* consul 长轮询等待时间.
|
||||||
|
*/
|
||||||
|
private final static Integer watchTime = 55;
|
||||||
|
/**
|
||||||
|
* 数据当前游标.
|
||||||
|
*/
|
||||||
|
private static Long index = -1L;
|
||||||
|
private static String rawContent;
|
||||||
|
|
||||||
|
private TencentUnitRouteRuleKVLoader() {
|
||||||
|
}
|
||||||
|
|
||||||
|
private static String getUnitRouteRuleKey() {
|
||||||
|
return "unit/routeRule/data";
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void syncUnitRouteRule() {
|
||||||
|
String newContent = null;
|
||||||
|
try {
|
||||||
|
ConsulClient client = TsfUnitConsulManager.getConsulClient();
|
||||||
|
|
||||||
|
if (client == null) {
|
||||||
|
LOGGER.warn("[syncUnitRouteRule] tsf unit consul client is null");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
Response<GetValue> response = client.getKVValue(getUnitRouteRuleKey(),
|
||||||
|
Env.getConsulToken(), new QueryParams(watchTime, index));
|
||||||
|
|
||||||
|
if (LOGGER.isDebugEnabled()) {
|
||||||
|
LOGGER.debug("[syncUnitRouteRule] resp:{}", response);
|
||||||
|
}
|
||||||
|
// data not change
|
||||||
|
if (response.getConsulIndex() == null || index.equals(response.getConsulIndex())) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
index = response.getConsulIndex();
|
||||||
|
// 推空保护,启动后理论上不存在单元化配置被删除的场景
|
||||||
|
if (response.getValue() != null) {
|
||||||
|
// 控制台 gzip 压缩加 base64 转换,这里进行解压
|
||||||
|
newContent = GzipUtil.base64DecodeDecompress(response.getValue().getDecodedValue());
|
||||||
|
loadUnitRouteRule(newContent);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
catch (Throwable t) {
|
||||||
|
if (LOGGER.isDebugEnabled()) {
|
||||||
|
LOGGER.debug("[syncUnitRouteRule] newContent:{} error:", newContent, t);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
LOGGER.warn("[syncUnitRouteRule] error: {}", t.getMessage());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void loadUnitRouteRule(String content) throws JsonProcessingException {
|
||||||
|
LOGGER.info("[unit] unit route rule old raw content:\n{}", rawContent);
|
||||||
|
|
||||||
|
ObjectMapper mapper = new ObjectMapper(new YAMLFactory());
|
||||||
|
mapper.configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false);
|
||||||
|
TencentUnitManager.setUnitRouteRule(mapper.readValue(content, UnitRouteInfo.class));
|
||||||
|
|
||||||
|
rawContent = content;
|
||||||
|
LOGGER.info("[unit] unit route rule new raw content:\n{}", rawContent);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
@ -0,0 +1,70 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.tsf.unit.core.remote;
|
||||||
|
|
||||||
|
import java.util.concurrent.Executors;
|
||||||
|
import java.util.concurrent.ScheduledExecutorService;
|
||||||
|
import java.util.concurrent.ThreadFactory;
|
||||||
|
import java.util.concurrent.TimeUnit;
|
||||||
|
import java.util.concurrent.atomic.AtomicInteger;
|
||||||
|
|
||||||
|
import com.ecwid.consul.v1.ConsulClient;
|
||||||
|
import com.tencent.polaris.api.utils.IPAddressUtils;
|
||||||
|
import com.tencent.tsf.unit.core.Env;
|
||||||
|
|
||||||
|
public final class TsfUnitConsulManager {
|
||||||
|
|
||||||
|
protected static final AtomicInteger POOL_SEQ = new AtomicInteger(1);
|
||||||
|
|
||||||
|
// 只需要 3 个长轮训
|
||||||
|
private final static ScheduledExecutorService executorService = Executors.newScheduledThreadPool(3, new ThreadFactory() {
|
||||||
|
@Override
|
||||||
|
public Thread newThread(Runnable r) {
|
||||||
|
Thread t = new Thread(r);
|
||||||
|
t.setName("tsf-unit-consul-" + POOL_SEQ.getAndIncrement());
|
||||||
|
t.setDaemon(true); // 设置为守护线程
|
||||||
|
return t;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
private static ConsulClient consulClient = null;
|
||||||
|
|
||||||
|
private static volatile boolean init = false;
|
||||||
|
|
||||||
|
private TsfUnitConsulManager() {
|
||||||
|
}
|
||||||
|
|
||||||
|
public static synchronized void init() {
|
||||||
|
if (!init) {
|
||||||
|
init = true;
|
||||||
|
consulClient = new ConsulClient(IPAddressUtils.getIpCompatible(Env.getConsulHost()), Env.getConsulPort());
|
||||||
|
|
||||||
|
// 初始化先同步拉取一次
|
||||||
|
TencentUnitArchKVLoader.syncUnitArch();
|
||||||
|
TencentUnitRouteRuleKVLoader.syncUnitRouteRule();
|
||||||
|
TencentUnitGrayKVLoader.syncUnitGray();
|
||||||
|
// 启动长轮训定时任务
|
||||||
|
executorService.scheduleAtFixedRate(TencentUnitArchKVLoader::syncUnitArch, 55, 1, TimeUnit.SECONDS);
|
||||||
|
executorService.scheduleAtFixedRate(TencentUnitRouteRuleKVLoader::syncUnitRouteRule, 55, 1, TimeUnit.SECONDS);
|
||||||
|
executorService.scheduleAtFixedRate(TencentUnitGrayKVLoader::syncUnitGray, 55, 1, TimeUnit.SECONDS);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static ConsulClient getConsulClient() {
|
||||||
|
return consulClient;
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1 @@
|
|||||||
|
com.tencent.cloud.plugin.unit.config.GatewayUnitAutoConfiguration
|
@ -0,0 +1,42 @@
|
|||||||
|
/*
|
||||||
|
* Tencent is pleased to support the open source community by making spring-cloud-tencent available.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2021 Tencent. 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.plugin.unit.config;
|
||||||
|
|
||||||
|
import org.junit.jupiter.api.Test;
|
||||||
|
|
||||||
|
import org.springframework.boot.autoconfigure.AutoConfigurations;
|
||||||
|
import org.springframework.boot.test.context.runner.ApplicationContextRunner;
|
||||||
|
|
||||||
|
import static org.assertj.core.api.Assertions.assertThat;
|
||||||
|
|
||||||
|
|
||||||
|
public class UnitAutoConfigurationTest {
|
||||||
|
|
||||||
|
private final ApplicationContextRunner contextRunner = new ApplicationContextRunner()
|
||||||
|
.withConfiguration(AutoConfigurations.of(UnitAutoConfiguration.class))
|
||||||
|
.withPropertyValues(
|
||||||
|
"tsf_consul_ip=localhost"
|
||||||
|
);
|
||||||
|
|
||||||
|
@Test
|
||||||
|
void shouldCreateBeansWhenConditionsMet() {
|
||||||
|
contextRunner.run(context -> {
|
||||||
|
assertThat(context).hasSingleBean(UnitBeanPostProcessor.class);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
Loading…
Reference in new issue