You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@servicecomb.apache.org by li...@apache.org on 2020/04/09 00:38:08 UTC

[servicecomb-java-chassis] 01/02: [SCB-1849]refactor: modify transport client module to use the new mechanism to initialize client

This is an automated email from the ASF dual-hosted git repository.

liubao pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/servicecomb-java-chassis.git

commit 3bb24cb2968b2471bfdd254e6318de5a6d726bc0
Author: liubao <bi...@qq.com>
AuthorDate: Tue Apr 7 16:01:18 2020 +0800

    [SCB-1849]refactor: modify transport client module to use the new mechanism to initialize client
---
 .../core/transport/AbstractTransport.java          | 12 +--
 .../src/main/resources/microservice.yaml           |  2 +-
 demo/demo-pojo/pojo-client/pom.xml                 |  4 +
 .../servicecomb/demo/pojo/client/PojoClient.java   | 16 ++++
 .../src/main/resources/microservice.yaml           |  6 +-
 .../demo/springmvc/client/SpringmvcClient.java     | 16 ++++
 .../client/ConfigCenterHttpClientOptionsSPI.java   | 51 +++++++++++++
 .../edge/core/CommonHttpEdgeDispatcher.java        | 18 ++---
 .../edge/core/EdgeRestServerVerticle.java          |  4 -
 .../edge/core/EdgeRestTransportClient.java         | 20 ++++-
 .../foundation/vertx/SharedVertxFactory.java       | 21 +++--
 .../vertx/client/http/HttpClientOptionsSPI.java    | 32 ++++++++
 .../foundation/vertx/client/http/HttpClients.java  | 51 +++++++++++--
 .../foundation/vertx/TestSharedVertxFactory.java   | 12 ++-
 .../metrics/core/VertxMetersInitializer.java       | 10 +--
 .../metrics/core/TestVertxMetersInitializer.java   | 26 +------
 .../client/http/RegistryHttpClientOptionsSPI.java  | 51 +++++++++++++
 .../client/Http2TransportHttpClientOptionsSPI.java | 64 ++++++++++++++++
 .../client/HttpTransportHttpClientOptionsSPI.java  | 89 +++++++++++++++++-----
 .../transport/rest/client/RestTransportClient.java | 77 +++----------------
 .../rest/client/TransportClientConfig.java         | 22 +++++-
 ...undation.vertx.client.http.HttpClientOptionsSPI | 19 +++++
 .../rest/client/TestRestTransportClient.java       | 88 ---------------------
 23 files changed, 456 insertions(+), 255 deletions(-)

diff --git a/core/src/main/java/org/apache/servicecomb/core/transport/AbstractTransport.java b/core/src/main/java/org/apache/servicecomb/core/transport/AbstractTransport.java
index 90e4479..0a215a0 100644
--- a/core/src/main/java/org/apache/servicecomb/core/transport/AbstractTransport.java
+++ b/core/src/main/java/org/apache/servicecomb/core/transport/AbstractTransport.java
@@ -33,6 +33,7 @@ import org.apache.servicecomb.core.Transport;
 import org.apache.servicecomb.foundation.common.exceptions.ServiceCombException;
 import org.apache.servicecomb.foundation.common.net.NetUtils;
 import org.apache.servicecomb.foundation.common.net.URIEndpointObject;
+import org.apache.servicecomb.foundation.vertx.SharedVertxFactory;
 import org.apache.servicecomb.serviceregistry.RegistryUtils;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
@@ -47,16 +48,7 @@ public abstract class AbstractTransport implements Transport {
    */
   public static final String ENDPOINT_KEY = "servicecomb.endpoint";
 
-  private static final long REQUEST_TIMEOUT_CFG_FAIL = -1;
-
-  // 所有transport使用同一个vertx实例,避免创建太多的线程
-  private static TransportVertxFactory transportVertxFactory = new TransportVertxFactory();
-
-  public static TransportVertxFactory getTransportVertxFactory() {
-    return transportVertxFactory;
-  }
-
-  protected Vertx transportVertx = getTransportVertxFactory().getTransportVertx();
+  protected Vertx transportVertx = SharedVertxFactory.getSharedVertx();
 
   protected Endpoint endpoint;
 
diff --git a/demo/demo-edge/authentication/src/main/resources/microservice.yaml b/demo/demo-edge/authentication/src/main/resources/microservice.yaml
index d6a13c8..a6f6221 100644
--- a/demo/demo-edge/authentication/src/main/resources/microservice.yaml
+++ b/demo/demo-edge/authentication/src/main/resources/microservice.yaml
@@ -24,7 +24,7 @@ servicecomb:
     registry:
       address: http://127.0.0.1:30100
   rest:
-    address: 0.0.0.0:7070
+    address: 0.0.0.0:7070?protocol=http2
     server:
       # for test case run in one core machine
       verticle-count: 1
diff --git a/demo/demo-pojo/pojo-client/pom.xml b/demo/demo-pojo/pojo-client/pom.xml
index 0a7f29f..f547329 100644
--- a/demo/demo-pojo/pojo-client/pom.xml
+++ b/demo/demo-pojo/pojo-client/pom.xml
@@ -38,6 +38,10 @@
     </dependency>
     <dependency>
       <groupId>org.apache.servicecomb</groupId>
+      <artifactId>metrics-core</artifactId>
+    </dependency>
+    <dependency>
+      <groupId>org.apache.servicecomb</groupId>
       <artifactId>foundation-test-scaffolding</artifactId>
       <scope>compile</scope>
     </dependency>
diff --git a/demo/demo-pojo/pojo-client/src/main/java/org/apache/servicecomb/demo/pojo/client/PojoClient.java b/demo/demo-pojo/pojo-client/src/main/java/org/apache/servicecomb/demo/pojo/client/PojoClient.java
index 31c7a24..71a1d82 100644
--- a/demo/demo-pojo/pojo-client/src/main/java/org/apache/servicecomb/demo/pojo/client/PojoClient.java
+++ b/demo/demo-pojo/pojo-client/src/main/java/org/apache/servicecomb/demo/pojo/client/PojoClient.java
@@ -42,6 +42,7 @@ import org.apache.servicecomb.demo.smartcare.SmartCare;
 import org.apache.servicecomb.foundation.common.utils.BeanUtils;
 import org.apache.servicecomb.foundation.common.utils.Log4jUtils;
 import org.apache.servicecomb.foundation.test.scaffolding.config.ArchaiusUtils;
+import org.apache.servicecomb.foundation.vertx.client.http.HttpClients;
 import org.apache.servicecomb.provider.pojo.RpcReference;
 import org.apache.servicecomb.swagger.invocation.context.ContextUtils;
 import org.apache.servicecomb.swagger.invocation.context.InvocationContext;
@@ -108,6 +109,7 @@ public class PojoClient {
   }
 
   public static void run() throws Exception {
+    testHttpClientsIsOk();
     CategorizedTestCaseRunner.runCategorizedTestCase("pojo");
 
     smartcare = BeanUtils.getBean("smartcare");
@@ -170,6 +172,20 @@ public class PojoClient {
     }
   }
 
+  private static void testHttpClientsIsOk() {
+    TestMgr.check(HttpClients.getClient("registry") != null, true);
+    TestMgr.check(HttpClients.getClient("registry-watch") != null, false);
+    TestMgr.check(HttpClients.getClient("config-center") != null, false);
+    TestMgr.check(HttpClients.getClient("http-transport-client") != null, false);
+    TestMgr.check(HttpClients.getClient("http2-transport-client") != null, true);
+
+    TestMgr.check(HttpClients.getClient("registry", false) != null, true);
+    TestMgr.check(HttpClients.getClient("registry-watch", false) != null, false);
+    TestMgr.check(HttpClients.getClient("config-center", false) != null, false);
+    TestMgr.check(HttpClients.getClient("http-transport-client", false) != null, false);
+    TestMgr.check(HttpClients.getClient("http2-transport-client", false) != null, true);
+  }
+
   /**
    * Only in http transport, traceId will be set to invocation if null.
    * But in highway, nothing done.
diff --git a/demo/demo-pojo/pojo-client/src/main/resources/microservice.yaml b/demo/demo-pojo/pojo-client/src/main/resources/microservice.yaml
index 47b01f5..ad15db8 100644
--- a/demo/demo-pojo/pojo-client/src/main/resources/microservice.yaml
+++ b/demo/demo-pojo/pojo-client/src/main/resources/microservice.yaml
@@ -29,6 +29,7 @@ servicecomb:
         watch: false
         empty:
           protection: true
+  rest.client.enabled: false # using only http2
   handler:
     chain:
       Consumer:
@@ -38,4 +39,7 @@ servicecomb:
       enabled: false
   loadbalance:
     strategy:
-      name: Random
\ No newline at end of file
+      name: Random
+  metrics:
+    window_time: 12000
+    publisher.defaultLog.enabled: false # when in testing , can turn on
\ No newline at end of file
diff --git a/demo/demo-springmvc/springmvc-client/src/main/java/org/apache/servicecomb/demo/springmvc/client/SpringmvcClient.java b/demo/demo-springmvc/springmvc-client/src/main/java/org/apache/servicecomb/demo/springmvc/client/SpringmvcClient.java
index 1b299fe..6f7bdde 100644
--- a/demo/demo-springmvc/springmvc-client/src/main/java/org/apache/servicecomb/demo/springmvc/client/SpringmvcClient.java
+++ b/demo/demo-springmvc/springmvc-client/src/main/java/org/apache/servicecomb/demo/springmvc/client/SpringmvcClient.java
@@ -29,6 +29,7 @@ import org.apache.servicecomb.demo.controller.Person;
 import org.apache.servicecomb.foundation.common.utils.BeanUtils;
 import org.apache.servicecomb.foundation.common.utils.Log4jUtils;
 import org.apache.servicecomb.foundation.test.scaffolding.config.ArchaiusUtils;
+import org.apache.servicecomb.foundation.vertx.client.http.HttpClients;
 import org.apache.servicecomb.provider.springmvc.reference.CseRestTemplate;
 import org.apache.servicecomb.provider.springmvc.reference.RestTemplateBuilder;
 import org.apache.servicecomb.provider.springmvc.reference.UrlWithProviderPrefixClientHttpRequestFactory;
@@ -79,6 +80,7 @@ public class SpringmvcClient {
   }
 
   public static void run() throws Exception {
+    testHttpClientsIsOk();
     testConfigurationDuplicate();
 
     templateUrlWithServiceName.setRequestFactory(new UrlWithServiceNameClientHttpRequestFactory());
@@ -107,6 +109,20 @@ public class SpringmvcClient {
     CategorizedTestCaseRunner.runCategorizedTestCase(microserviceName);
   }
 
+  private static void testHttpClientsIsOk() {
+    TestMgr.check(HttpClients.getClient("registry") != null, true);
+    TestMgr.check(HttpClients.getClient("registry-watch") != null, true);
+    TestMgr.check(HttpClients.getClient("config-center") != null, true);
+    TestMgr.check(HttpClients.getClient("http-transport-client") != null, true);
+    TestMgr.check(HttpClients.getClient("http2-transport-client") != null, true);
+
+    TestMgr.check(HttpClients.getClient("registry", false) != null, true);
+    TestMgr.check(HttpClients.getClient("registry-watch", false) != null, true);
+    TestMgr.check(HttpClients.getClient("config-center", false) != null, true);
+    TestMgr.check(HttpClients.getClient("http-transport-client", false) != null, true);
+    TestMgr.check(HttpClients.getClient("http2-transport-client", false) != null, true);
+  }
+
   private static void testRestTransport(String microserviceName, String prefix) {
     changeTransport(microserviceName, "rest");
 
diff --git a/dynamic-config/config-cc/src/main/java/org/apache/servicecomb/config/client/ConfigCenterHttpClientOptionsSPI.java b/dynamic-config/config-cc/src/main/java/org/apache/servicecomb/config/client/ConfigCenterHttpClientOptionsSPI.java
index 1c78058..3b3c4d8 100644
--- a/dynamic-config/config-cc/src/main/java/org/apache/servicecomb/config/client/ConfigCenterHttpClientOptionsSPI.java
+++ b/dynamic-config/config-cc/src/main/java/org/apache/servicecomb/config/client/ConfigCenterHttpClientOptionsSPI.java
@@ -22,6 +22,7 @@ import org.apache.servicecomb.deployment.DeploymentProvider;
 import org.apache.servicecomb.foundation.vertx.client.http.HttpClientOptionsSPI;
 
 import io.vertx.core.VertxOptions;
+import io.vertx.core.http.HttpClientOptions;
 import io.vertx.core.http.HttpVersion;
 
 public class ConfigCenterHttpClientOptionsSPI implements HttpClientOptionsSPI {
@@ -53,6 +54,11 @@ public class ConfigCenterHttpClientOptionsSPI implements HttpClientOptionsSPI {
   }
 
   @Override
+  public boolean useSharedVertx() {
+    return false;
+  }
+
+  @Override
   public int getInstanceCount() {
     return ConfigCenterConfig.INSTANCE.getVerticalInstanceCount();
   }
@@ -88,6 +94,51 @@ public class ConfigCenterHttpClientOptionsSPI implements HttpClientOptionsSPI {
   }
 
   @Override
+  public boolean isTryUseCompression() {
+    return HttpClientOptions.DEFAULT_TRY_USE_COMPRESSION;
+  }
+
+  @Override
+  public int getMaxWaitQueueSize() {
+    return HttpClientOptions.DEFAULT_MAX_WAIT_QUEUE_SIZE;
+  }
+
+  @Override
+  public int getMaxPoolSize() {
+    return HttpClientOptions.DEFAULT_MAX_POOL_SIZE;
+  }
+
+  @Override
+  public boolean isKeepAlive() {
+    return HttpClientOptions.DEFAULT_KEEP_ALIVE;
+  }
+
+  @Override
+  public int getMaxHeaderSize() {
+    return HttpClientOptions.DEFAULT_MAX_HEADER_SIZE;
+  }
+
+  @Override
+  public int getKeepAliveTimeout() {
+    return HttpClientOptions.DEFAULT_KEEP_ALIVE_TIMEOUT;
+  }
+
+  @Override
+  public int getHttp2MultiplexingLimit() {
+    return HttpClientOptions.DEFAULT_HTTP2_MULTIPLEXING_LIMIT;
+  }
+
+  @Override
+  public int getHttp2MaxPoolSize() {
+    return HttpClientOptions.DEFAULT_HTTP2_MAX_POOL_SIZE;
+  }
+
+  @Override
+  public boolean isUseAlpn() {
+    return HttpClientOptions.DEFAULT_USE_ALPN;
+  }
+
+  @Override
   public boolean isProxyEnable() {
     return ConfigCenterConfig.INSTANCE.isProxyEnable();
   }
diff --git a/edge/edge-core/src/main/java/org/apache/servicecomb/edge/core/CommonHttpEdgeDispatcher.java b/edge/edge-core/src/main/java/org/apache/servicecomb/edge/core/CommonHttpEdgeDispatcher.java
index ac8f30d..f8daa9a 100644
--- a/edge/edge-core/src/main/java/org/apache/servicecomb/edge/core/CommonHttpEdgeDispatcher.java
+++ b/edge/edge-core/src/main/java/org/apache/servicecomb/edge/core/CommonHttpEdgeDispatcher.java
@@ -34,6 +34,8 @@ import org.apache.servicecomb.loadbalance.filter.ServerDiscoveryFilter;
 import org.apache.servicecomb.serviceregistry.RegistryUtils;
 import org.apache.servicecomb.serviceregistry.discovery.DiscoveryContext;
 import org.apache.servicecomb.serviceregistry.discovery.DiscoveryTree;
+import org.apache.servicecomb.transport.rest.client.Http2TransportHttpClientOptionsSPI;
+import org.apache.servicecomb.transport.rest.client.HttpTransportHttpClientOptionsSPI;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
@@ -136,16 +138,16 @@ public class CommonHttpEdgeDispatcher extends AbstractEdgeDispatcher {
         .setSsl(endpointObject.isSslEnabled())
         .setURI(uri);
 
-    // TODO: now use registry client, after next PR transport client is fixed, using that.
-    HttpClient httpClient = HttpClients.getClient("registry").getHttpClient();
+    HttpClient httpClient;
+    if (endpointObject.isHttp2Enabled()) {
+      httpClient = HttpClients.getClient(Http2TransportHttpClientOptionsSPI.CLIENT_NAME, false).getHttpClient();
+    } else {
+      httpClient = HttpClients.getClient(HttpTransportHttpClientOptionsSPI.CLIENT_NAME, false).getHttpClient();
+    }
     HttpClientRequest httpClientRequest = httpClient
         .request(context.request().method(), requestOptions, httpClientResponse -> {
           context.response().setStatusCode(httpClientResponse.statusCode());
           httpClientResponse.headers().forEach((header) -> {
-            // any headers need to exclude can add here
-//              if ("Content-Length".equalsIgnoreCase(header.getKey())) {
-//                return;
-//              }
             context.response().headers().set(header.getKey(), header.getValue());
           });
           httpClientResponse.handler(data -> {
@@ -154,10 +156,6 @@ public class CommonHttpEdgeDispatcher extends AbstractEdgeDispatcher {
           httpClientResponse.endHandler((v) -> context.response().end());
         });
     context.request().headers().forEach((header) -> {
-      // any headers need to exclude can add here
-//              if ("Content-Length".equalsIgnoreCase(header.getKey())) {
-//                return;
-//              }
       httpClientRequest.headers().set(header.getKey(), header.getValue());
     });
     context.request().handler(data -> httpClientRequest.write(data));
diff --git a/edge/edge-core/src/main/java/org/apache/servicecomb/edge/core/EdgeRestServerVerticle.java b/edge/edge-core/src/main/java/org/apache/servicecomb/edge/core/EdgeRestServerVerticle.java
index a7d7529..5135bf5 100644
--- a/edge/edge-core/src/main/java/org/apache/servicecomb/edge/core/EdgeRestServerVerticle.java
+++ b/edge/edge-core/src/main/java/org/apache/servicecomb/edge/core/EdgeRestServerVerticle.java
@@ -16,15 +16,11 @@
  */
 package org.apache.servicecomb.edge.core;
 
-import org.apache.servicecomb.transport.rest.client.RestTransportClient;
 import org.apache.servicecomb.transport.rest.vertx.RestServerVerticle;
 
 public class EdgeRestServerVerticle extends RestServerVerticle {
   @Override
   public void start() throws Exception {
     super.start();
-
-    RestTransportClient restClient = (RestTransportClient) config().getValue(RestTransportClient.class.getName());
-    restClient.getClientMgr().findClientPool(false, context);
   }
 }
diff --git a/edge/edge-core/src/main/java/org/apache/servicecomb/edge/core/EdgeRestTransportClient.java b/edge/edge-core/src/main/java/org/apache/servicecomb/edge/core/EdgeRestTransportClient.java
index f09cf93..dcd3b97 100644
--- a/edge/edge-core/src/main/java/org/apache/servicecomb/edge/core/EdgeRestTransportClient.java
+++ b/edge/edge-core/src/main/java/org/apache/servicecomb/edge/core/EdgeRestTransportClient.java
@@ -17,17 +17,29 @@
 package org.apache.servicecomb.edge.core;
 
 import org.apache.servicecomb.core.Invocation;
-import org.apache.servicecomb.foundation.vertx.client.ClientPoolManager;
+import org.apache.servicecomb.foundation.common.net.URIEndpointObject;
 import org.apache.servicecomb.foundation.vertx.client.http.HttpClientWithContext;
+import org.apache.servicecomb.foundation.vertx.client.http.HttpClients;
+import org.apache.servicecomb.transport.rest.client.Http2TransportHttpClientOptionsSPI;
+import org.apache.servicecomb.transport.rest.client.HttpTransportHttpClientOptionsSPI;
 import org.apache.servicecomb.transport.rest.client.RestTransportClient;
 
 import io.vertx.core.Context;
 
 public class EdgeRestTransportClient extends RestTransportClient {
   @Override
-  protected HttpClientWithContext findHttpClientPool(ClientPoolManager<HttpClientWithContext> clientMgr,
-      Invocation invocation) {
+  protected HttpClientWithContext findHttpClientPool(Invocation invocation) {
     Context invocationContext = (Context) invocation.getHandlerContext().get(EdgeInvocation.EDGE_INVOCATION_CONTEXT);
-    return clientMgr.findClientPool(invocation.isSync(), invocationContext);
+
+    URIEndpointObject endpoint = (URIEndpointObject) invocation.getEndpoint().getAddress();
+    HttpClientWithContext httpClientWithContext;
+    if (endpoint.isHttp2Enabled()) {
+      httpClientWithContext = HttpClients
+          .getClient(Http2TransportHttpClientOptionsSPI.CLIENT_NAME, invocation.isSync(), invocationContext);
+    } else {
+      httpClientWithContext = HttpClients
+          .getClient(HttpTransportHttpClientOptionsSPI.CLIENT_NAME, invocation.isSync(), invocationContext);
+    }
+    return httpClientWithContext;
   }
 }
diff --git a/core/src/main/java/org/apache/servicecomb/core/transport/TransportVertxFactory.java b/foundations/foundation-vertx/src/main/java/org/apache/servicecomb/foundation/vertx/SharedVertxFactory.java
similarity index 75%
rename from core/src/main/java/org/apache/servicecomb/core/transport/TransportVertxFactory.java
rename to foundations/foundation-vertx/src/main/java/org/apache/servicecomb/foundation/vertx/SharedVertxFactory.java
index c2227fb..4b3b955 100644
--- a/core/src/main/java/org/apache/servicecomb/core/transport/TransportVertxFactory.java
+++ b/foundations/foundation-vertx/src/main/java/org/apache/servicecomb/foundation/vertx/SharedVertxFactory.java
@@ -14,9 +14,8 @@
  * See the License for the specific language governing permissions and
  * limitations under the License.
  */
-package org.apache.servicecomb.core.transport;
+package org.apache.servicecomb.foundation.vertx;
 
-import org.apache.servicecomb.foundation.vertx.VertxUtils;
 import org.apache.servicecomb.foundation.vertx.metrics.DefaultVertxMetricsFactory;
 import org.apache.servicecomb.foundation.vertx.metrics.MetricsOptionsEx;
 
@@ -24,15 +23,15 @@ import io.vertx.core.Vertx;
 import io.vertx.core.VertxOptions;
 import io.vertx.core.shareddata.Shareable;
 
-public class TransportVertxFactory {
-  static class TransportVertxInfo implements Shareable {
+public class SharedVertxFactory {
+  static class SharedVertxInfo implements Shareable {
     public VertxOptions vertxOptions = new VertxOptions();
 
     public DefaultVertxMetricsFactory metricsFactory = new DefaultVertxMetricsFactory();
 
     public MetricsOptionsEx metricsOptionsEx = (MetricsOptionsEx) metricsFactory.newOptions();
 
-    public TransportVertxInfo() {
+    public SharedVertxInfo() {
       vertxOptions.setMetricsOptions(metricsOptionsEx);
     }
   }
@@ -41,18 +40,18 @@ public class TransportVertxFactory {
 
   private static final String INFO = "transport-vertx-info";
 
-  public DefaultVertxMetricsFactory getMetricsFactory() {
-    TransportVertxInfo info = (TransportVertxInfo) getTransportVertx().sharedData().getLocalMap(LOCAL_MAP_NAME)
+  public static DefaultVertxMetricsFactory getMetricsFactory() {
+    SharedVertxInfo info = (SharedVertxInfo) getSharedVertx().sharedData().getLocalMap(LOCAL_MAP_NAME)
         .get(INFO);
     return info.metricsFactory;
   }
 
-  public Vertx getTransportVertx() {
-    return VertxUtils.getVertxMap().computeIfAbsent("transport", this::createTransportVertx);
+  public static Vertx getSharedVertx() {
+    return VertxUtils.getVertxMap().computeIfAbsent("transport", SharedVertxFactory::createSharedVertx);
   }
 
-  private Vertx createTransportVertx(String name) {
-    TransportVertxInfo info = new TransportVertxInfo();
+  private static Vertx createSharedVertx(String name) {
+    SharedVertxInfo info = new SharedVertxInfo();
 
     Vertx vertx = VertxUtils.init(info.vertxOptions);
     info.metricsFactory.setVertx(vertx, info.vertxOptions);
diff --git a/foundations/foundation-vertx/src/main/java/org/apache/servicecomb/foundation/vertx/client/http/HttpClientOptionsSPI.java b/foundations/foundation-vertx/src/main/java/org/apache/servicecomb/foundation/vertx/client/http/HttpClientOptionsSPI.java
index a538a42..dc942ae 100644
--- a/foundations/foundation-vertx/src/main/java/org/apache/servicecomb/foundation/vertx/client/http/HttpClientOptionsSPI.java
+++ b/foundations/foundation-vertx/src/main/java/org/apache/servicecomb/foundation/vertx/client/http/HttpClientOptionsSPI.java
@@ -44,6 +44,9 @@ public interface HttpClientOptionsSPI {
   /*****************  vert.x common settings ***************************/
   int getEventLoopPoolSize();
 
+  boolean useSharedVertx();
+
+  /*****************  vert.x vertical common settings ***************************/
   int getInstanceCount();
 
   boolean isWorker();
@@ -59,6 +62,24 @@ public interface HttpClientOptionsSPI {
 
   int getIdleTimeoutInSeconds();
 
+  boolean isTryUseCompression();
+
+  int getMaxWaitQueueSize();
+
+  int getMaxPoolSize();
+
+  boolean isKeepAlive();
+
+  int getMaxHeaderSize();
+
+  int getKeepAliveTimeout();
+
+  /***************** http 2 settings ****************************/
+  int getHttp2MultiplexingLimit();
+
+  int getHttp2MaxPoolSize();
+
+  boolean isUseAlpn();
   /*****************  proxy settings ***************************/
   boolean isProxyEnable();
 
@@ -79,6 +100,13 @@ public interface HttpClientOptionsSPI {
     httpClientOptions.setProtocolVersion(spi.getHttpVersion());
     httpClientOptions.setConnectTimeout(spi.getConnectTimeoutInMillis());
     httpClientOptions.setIdleTimeout(spi.getIdleTimeoutInSeconds());
+    httpClientOptions.setTryUseCompression(spi.isTryUseCompression());
+    httpClientOptions.setMaxWaitQueueSize(spi.getMaxWaitQueueSize());
+    httpClientOptions.setMaxPoolSize(spi.getMaxPoolSize());
+    httpClientOptions.setKeepAlive(spi.isKeepAlive());
+    httpClientOptions.setMaxHeaderSize(spi.getMaxHeaderSize());
+    httpClientOptions.setKeepAliveTimeout(spi.getKeepAliveTimeout());
+
     if (spi.isProxyEnable()) {
       ProxyOptions proxy = new ProxyOptions();
       proxy.setHost(spi.getProxyHost());
@@ -88,8 +116,12 @@ public interface HttpClientOptionsSPI {
           Encryptions.decode(spi.getProxyPassword(), spi.getConfigTag()));
       httpClientOptions.setProxyOptions(proxy);
     }
+
     if (spi.getHttpVersion() == HttpVersion.HTTP_2) {
       httpClientOptions.setHttp2ClearTextUpgrade(false);
+      httpClientOptions.setUseAlpn(spi.isUseAlpn());
+      httpClientOptions.setHttp2MultiplexingLimit(spi.getHttp2MultiplexingLimit());
+      httpClientOptions.setHttp2MaxPoolSize(spi.getHttp2MaxPoolSize());
     }
 
     if (spi.isSsl()) {
diff --git a/foundations/foundation-vertx/src/main/java/org/apache/servicecomb/foundation/vertx/client/http/HttpClients.java b/foundations/foundation-vertx/src/main/java/org/apache/servicecomb/foundation/vertx/client/http/HttpClients.java
index 79b18ff..3db635d 100644
--- a/foundations/foundation-vertx/src/main/java/org/apache/servicecomb/foundation/vertx/client/http/HttpClients.java
+++ b/foundations/foundation-vertx/src/main/java/org/apache/servicecomb/foundation/vertx/client/http/HttpClients.java
@@ -23,6 +23,7 @@ import java.util.Map;
 
 import org.apache.servicecomb.foundation.common.utils.SPIServiceUtils;
 import org.apache.servicecomb.foundation.vertx.AddressResolverConfig;
+import org.apache.servicecomb.foundation.vertx.SharedVertxFactory;
 import org.apache.servicecomb.foundation.vertx.VertxUtils;
 import org.apache.servicecomb.foundation.vertx.client.ClientPoolManager;
 import org.apache.servicecomb.foundation.vertx.client.ClientVerticle;
@@ -31,6 +32,7 @@ import org.slf4j.LoggerFactory;
 
 import com.google.common.annotations.VisibleForTesting;
 
+import io.vertx.core.Context;
 import io.vertx.core.DeploymentOptions;
 import io.vertx.core.Vertx;
 import io.vertx.core.VertxOptions;
@@ -78,12 +80,18 @@ public class HttpClients {
   }
 
   private static ClientPoolManager<HttpClientWithContext> createClientPoolManager(HttpClientOptionsSPI option) {
-    VertxOptions vertxOptions = new VertxOptions()
-        .setAddressResolverOptions(AddressResolverConfig.getAddressResover(option.getConfigTag()))
-        .setEventLoopPoolSize(option.getEventLoopPoolSize());
+    Vertx vertx;
 
-    // Maybe we can deploy only one vert.x for the application. However this has did it like this.
-    Vertx vertx = VertxUtils.getOrCreateVertxByName(option.clientName(), vertxOptions);
+    if (option.useSharedVertx()) {
+      vertx = SharedVertxFactory.getSharedVertx();
+    } else {
+      VertxOptions vertxOptions = new VertxOptions()
+          .setAddressResolverOptions(AddressResolverConfig.getAddressResover(option.getConfigTag()))
+          .setEventLoopPoolSize(option.getEventLoopPoolSize());
+
+      // Maybe we can deploy only one vert.x for the application. However this has did it like this.
+      vertx = VertxUtils.getOrCreateVertxByName(option.clientName(), vertxOptions);
+    }
 
     ClientPoolManager<HttpClientWithContext> clientPoolManager = new ClientPoolManager<>(vertx,
         new HttpClientPoolFactory(HttpClientOptionsSPI.createHttpClientOptions(option)));
@@ -107,6 +115,39 @@ public class HttpClients {
    * @return the deployed instance name
    */
   public static HttpClientWithContext getClient(String clientName) {
+    if (httpClients.get(clientName) == null) {
+      LOGGER.error("client name [{}] not exists, should only happen in tests.", clientName);
+      return null;
+    }
     return httpClients.get(clientName).findThreadBindClientPool();
   }
+
+  /**
+   * get client instance by name
+   * @param clientName instance name
+   * @param sync reactive or not. false for reactive.
+   * @return the deployed instance name
+   */
+  public static HttpClientWithContext getClient(String clientName, boolean sync) {
+    if (httpClients.get(clientName) == null) {
+      LOGGER.error("client name [{}] not exists, should only happen in tests.", clientName);
+      return null;
+    }
+    return httpClients.get(clientName).findClientPool(sync);
+  }
+
+  /**
+   * get client instance by name
+   * @param clientName instance name
+   * @param sync reactive or not. false for reactive.
+   * @param targetContext running context
+   * @return the deployed instance name
+   */
+  public static HttpClientWithContext getClient(String clientName, boolean sync, Context targetContext) {
+    if (httpClients.get(clientName) == null) {
+      LOGGER.error("client name [{}] not exists, should only happen in tests.", clientName);
+      return null;
+    }
+    return httpClients.get(clientName).findClientPool(sync, targetContext);
+  }
 }
diff --git a/core/src/test/java/org/apache/servicecomb/core/transport/TestTransportVertxFactory.java b/foundations/foundation-vertx/src/test/java/org/apache/servicecomb/foundation/vertx/TestSharedVertxFactory.java
similarity index 71%
rename from core/src/test/java/org/apache/servicecomb/core/transport/TestTransportVertxFactory.java
rename to foundations/foundation-vertx/src/test/java/org/apache/servicecomb/foundation/vertx/TestSharedVertxFactory.java
index fee477f..a27c47f 100644
--- a/core/src/test/java/org/apache/servicecomb/core/transport/TestTransportVertxFactory.java
+++ b/foundations/foundation-vertx/src/test/java/org/apache/servicecomb/foundation/vertx/TestSharedVertxFactory.java
@@ -14,19 +14,17 @@
  * See the License for the specific language governing permissions and
  * limitations under the License.
  */
-package org.apache.servicecomb.core.transport;
+package org.apache.servicecomb.foundation.vertx;
 
 import org.junit.Assert;
 import org.junit.Test;
 
-public class TestTransportVertxFactory {
+public class TestSharedVertxFactory {
   @Test
   public void getTransportVertx() {
-    TransportVertxFactory vertxFactory = new TransportVertxFactory();
+    Assert.assertNotNull(SharedVertxFactory.getSharedVertx());
+    Assert.assertSame(SharedVertxFactory.getSharedVertx(), SharedVertxFactory.getSharedVertx());
 
-    Assert.assertNotNull(vertxFactory.getTransportVertx());
-    Assert.assertSame(vertxFactory.getTransportVertx(), vertxFactory.getTransportVertx());
-
-    vertxFactory.getTransportVertx().close();
+    SharedVertxFactory.getSharedVertx().close();
   }
 }
diff --git a/metrics/metrics-core/src/main/java/org/apache/servicecomb/metrics/core/VertxMetersInitializer.java b/metrics/metrics-core/src/main/java/org/apache/servicecomb/metrics/core/VertxMetersInitializer.java
index 188025d..fe2185a 100644
--- a/metrics/metrics-core/src/main/java/org/apache/servicecomb/metrics/core/VertxMetersInitializer.java
+++ b/metrics/metrics-core/src/main/java/org/apache/servicecomb/metrics/core/VertxMetersInitializer.java
@@ -16,10 +16,10 @@
  */
 package org.apache.servicecomb.metrics.core;
 
-import org.apache.servicecomb.core.transport.AbstractTransport;
 import org.apache.servicecomb.foundation.metrics.MetricsBootstrapConfig;
 import org.apache.servicecomb.foundation.metrics.MetricsInitializer;
 import org.apache.servicecomb.foundation.metrics.registry.GlobalRegistry;
+import org.apache.servicecomb.foundation.vertx.SharedVertxFactory;
 import org.apache.servicecomb.metrics.core.meter.vertx.HttpClientEndpointsMeter;
 import org.apache.servicecomb.metrics.core.meter.vertx.ServerEndpointsMeter;
 import org.apache.servicecomb.metrics.core.meter.vertx.VertxEndpointsMeter;
@@ -45,9 +45,7 @@ public class VertxMetersInitializer implements MetricsInitializer {
     Id endpointsId = registry.createId(VERTX_ENDPOINTS);
     VertxEndpointsMeter clientMeter = new HttpClientEndpointsMeter(
         endpointsId.withTag(ENDPOINTS_TYPE, ENDPOINTS_CLINET),
-        AbstractTransport
-            .getTransportVertxFactory()
-            .getMetricsFactory()
+        SharedVertxFactory.getMetricsFactory()
             .getVertxMetrics()
             .getClientEndpointMetricManager()
             .getClientEndpointMetricMap());
@@ -55,9 +53,7 @@ public class VertxMetersInitializer implements MetricsInitializer {
 
     VertxEndpointsMeter serverMeter = new ServerEndpointsMeter(
         endpointsId.withTag(ENDPOINTS_TYPE, ENDPOINTS_SERVER),
-        AbstractTransport
-            .getTransportVertxFactory()
-            .getMetricsFactory()
+        SharedVertxFactory.getMetricsFactory()
             .getVertxMetrics()
             .getServerEndpointMetricMap());
     SpectatorUtils.registerMeter(registry, serverMeter);
diff --git a/metrics/metrics-core/src/test/java/org/apache/servicecomb/metrics/core/TestVertxMetersInitializer.java b/metrics/metrics-core/src/test/java/org/apache/servicecomb/metrics/core/TestVertxMetersInitializer.java
index 02a0259..175255d 100644
--- a/metrics/metrics-core/src/test/java/org/apache/servicecomb/metrics/core/TestVertxMetersInitializer.java
+++ b/metrics/metrics-core/src/test/java/org/apache/servicecomb/metrics/core/TestVertxMetersInitializer.java
@@ -19,12 +19,11 @@ package org.apache.servicecomb.metrics.core;
 import java.util.ArrayList;
 import java.util.List;
 
-import org.apache.servicecomb.core.transport.AbstractTransport;
-import org.apache.servicecomb.core.transport.TransportVertxFactory;
 import org.apache.servicecomb.foundation.metrics.PolledEvent;
 import org.apache.servicecomb.foundation.metrics.registry.GlobalRegistry;
 import org.apache.servicecomb.foundation.test.scaffolding.config.ArchaiusUtils;
 import org.apache.servicecomb.foundation.test.scaffolding.log.LogCollector;
+import org.apache.servicecomb.foundation.vertx.SharedVertxFactory;
 import org.apache.servicecomb.foundation.vertx.VertxUtils;
 import org.apache.servicecomb.foundation.vertx.client.http.HttpClients;
 import org.apache.servicecomb.metrics.core.publish.DefaultLogPublisher;
@@ -47,7 +46,6 @@ import io.vertx.core.Future;
 import io.vertx.core.http.HttpClient;
 import io.vertx.core.http.HttpServer;
 import io.vertx.ext.web.Router;
-import mockit.Expectations;
 
 public class TestVertxMetersInitializer {
   GlobalRegistry globalRegistry = new GlobalRegistry(new ManualClock());
@@ -56,8 +54,6 @@ public class TestVertxMetersInitializer {
 
   EventBus eventBus = new EventBus();
 
-  TransportVertxFactory transportVertxFactory;
-
   VertxMetersInitializer vertxMetersInitializer = new VertxMetersInitializer();
 
   DefaultLogPublisher logPublisher = new DefaultLogPublisher();
@@ -115,29 +111,13 @@ public class TestVertxMetersInitializer {
 
   @Test
   public void init() throws InterruptedException {
-    transportVertxFactory = new TransportVertxFactory();
-    new Expectations(AbstractTransport.class) {
-      {
-        AbstractTransport.getTransportVertxFactory();
-        result = transportVertxFactory;
-      }
-    };
-    // TODO will be fixed by next vertx update.
-//    new Expectations(VertxUtils.class) {
-//      {
-
-//        VertxUtils.getEventLoopContextCreatedCount(anyString);
-//        result = 4;
-//      }
-//    };
-
     globalRegistry.add(registry);
     vertxMetersInitializer.init(globalRegistry, eventBus, null);
     logPublisher.init(null, eventBus, null);
     VertxUtils
-        .blockDeploy(transportVertxFactory.getTransportVertx(), TestServerVerticle.class, new DeploymentOptions());
+        .blockDeploy(SharedVertxFactory.getSharedVertx(), TestServerVerticle.class, new DeploymentOptions());
     VertxUtils
-        .blockDeploy(transportVertxFactory.getTransportVertx(), TestClientVerticle.class, new DeploymentOptions());
+        .blockDeploy(SharedVertxFactory.getSharedVertx(), TestClientVerticle.class, new DeploymentOptions());
 
     globalRegistry.poll(1);
     List<Meter> meters = Lists.newArrayList(registry.iterator());
diff --git a/service-registry/src/main/java/org/apache/servicecomb/serviceregistry/client/http/RegistryHttpClientOptionsSPI.java b/service-registry/src/main/java/org/apache/servicecomb/serviceregistry/client/http/RegistryHttpClientOptionsSPI.java
index 304c10c..b8869e0 100644
--- a/service-registry/src/main/java/org/apache/servicecomb/serviceregistry/client/http/RegistryHttpClientOptionsSPI.java
+++ b/service-registry/src/main/java/org/apache/servicecomb/serviceregistry/client/http/RegistryHttpClientOptionsSPI.java
@@ -23,6 +23,7 @@ import org.apache.servicecomb.serviceregistry.config.ServiceRegistryConfig;
 import com.netflix.config.DynamicPropertyFactory;
 
 import io.vertx.core.VertxOptions;
+import io.vertx.core.http.HttpClientOptions;
 import io.vertx.core.http.HttpVersion;
 
 public class RegistryHttpClientOptionsSPI implements HttpClientOptionsSPI {
@@ -57,6 +58,11 @@ public class RegistryHttpClientOptionsSPI implements HttpClientOptionsSPI {
   }
 
   @Override
+  public boolean useSharedVertx() {
+    return false;
+  }
+
+  @Override
   public int getInstanceCount() {
     return serviceRegistryConfig.getInstances();
   }
@@ -92,6 +98,51 @@ public class RegistryHttpClientOptionsSPI implements HttpClientOptionsSPI {
   }
 
   @Override
+  public boolean isTryUseCompression() {
+    return false;
+  }
+
+  @Override
+  public int getMaxWaitQueueSize() {
+    return HttpClientOptions.DEFAULT_MAX_WAIT_QUEUE_SIZE;
+  }
+
+  @Override
+  public int getMaxPoolSize() {
+    return HttpClientOptions.DEFAULT_MAX_POOL_SIZE;
+  }
+
+  @Override
+  public boolean isKeepAlive() {
+    return HttpClientOptions.DEFAULT_KEEP_ALIVE;
+  }
+
+  @Override
+  public int getMaxHeaderSize() {
+    return HttpClientOptions.DEFAULT_MAX_HEADER_SIZE;
+  }
+
+  @Override
+  public int getKeepAliveTimeout() {
+    return HttpClientOptions.DEFAULT_KEEP_ALIVE_TIMEOUT;
+  }
+
+  @Override
+  public int getHttp2MultiplexingLimit() {
+    return HttpClientOptions.DEFAULT_HTTP2_MULTIPLEXING_LIMIT;
+  }
+
+  @Override
+  public int getHttp2MaxPoolSize() {
+    return HttpClientOptions.DEFAULT_HTTP2_MAX_POOL_SIZE;
+  }
+
+  @Override
+  public boolean isUseAlpn() {
+    return HttpClientOptions.DEFAULT_USE_ALPN;
+  }
+
+  @Override
   public boolean isProxyEnable() {
     return serviceRegistryConfig.isProxyEnable();
   }
diff --git a/transports/transport-rest/transport-rest-client/src/main/java/org/apache/servicecomb/transport/rest/client/Http2TransportHttpClientOptionsSPI.java b/transports/transport-rest/transport-rest-client/src/main/java/org/apache/servicecomb/transport/rest/client/Http2TransportHttpClientOptionsSPI.java
new file mode 100644
index 0000000..e201c67
--- /dev/null
+++ b/transports/transport-rest/transport-rest-client/src/main/java/org/apache/servicecomb/transport/rest/client/Http2TransportHttpClientOptionsSPI.java
@@ -0,0 +1,64 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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 org.apache.servicecomb.transport.rest.client;
+
+import io.vertx.core.http.HttpVersion;
+
+public class Http2TransportHttpClientOptionsSPI extends HttpTransportHttpClientOptionsSPI {
+  public static final String CLIENT_NAME = "http2-transport-client";
+
+  @Override
+  public String clientName() {
+    return CLIENT_NAME;
+  }
+
+  @Override
+  public int getOrder() {
+    return super.getOrder() + 1;
+  }
+
+  @Override
+  public boolean enabled() {
+    return TransportClientConfig.isHttp2TransportClientEnabled();
+  }
+
+  @Override
+  public HttpVersion getHttpVersion() {
+    return HttpVersion.HTTP_2;
+  }
+
+  @Override
+  public boolean isUseAlpn() {
+    return TransportClientConfig.getUseAlpn();
+  }
+
+  @Override
+  public int getHttp2MultiplexingLimit() {
+    return TransportClientConfig.getHttp2MultiplexingLimit();
+  }
+
+  @Override
+  public int getHttp2MaxPoolSize() {
+    return TransportClientConfig.getHttp2ConnectionMaxPoolSize();
+  }
+
+  @Override
+  public int getIdleTimeoutInSeconds() {
+    return TransportClientConfig.getHttp2ConnectionIdleTimeoutInSeconds();
+  }
+}
diff --git a/dynamic-config/config-cc/src/main/java/org/apache/servicecomb/config/client/ConfigCenterHttpClientOptionsSPI.java b/transports/transport-rest/transport-rest-client/src/main/java/org/apache/servicecomb/transport/rest/client/HttpTransportHttpClientOptionsSPI.java
similarity index 51%
copy from dynamic-config/config-cc/src/main/java/org/apache/servicecomb/config/client/ConfigCenterHttpClientOptionsSPI.java
copy to transports/transport-rest/transport-rest-client/src/main/java/org/apache/servicecomb/transport/rest/client/HttpTransportHttpClientOptionsSPI.java
index 1c78058..619bb03 100644
--- a/dynamic-config/config-cc/src/main/java/org/apache/servicecomb/config/client/ConfigCenterHttpClientOptionsSPI.java
+++ b/transports/transport-rest/transport-rest-client/src/main/java/org/apache/servicecomb/transport/rest/client/HttpTransportHttpClientOptionsSPI.java
@@ -15,17 +15,18 @@
  * limitations under the License.
  */
 
-package org.apache.servicecomb.config.client;
+package org.apache.servicecomb.transport.rest.client;
 
-import org.apache.servicecomb.deployment.Deployment;
-import org.apache.servicecomb.deployment.DeploymentProvider;
 import org.apache.servicecomb.foundation.vertx.client.http.HttpClientOptionsSPI;
 
 import io.vertx.core.VertxOptions;
+import io.vertx.core.http.HttpClientOptions;
 import io.vertx.core.http.HttpVersion;
 
-public class ConfigCenterHttpClientOptionsSPI implements HttpClientOptionsSPI {
-  public static final String CLIENT_NAME = "config-center";
+public class HttpTransportHttpClientOptionsSPI implements HttpClientOptionsSPI {
+  public static final String CLIENT_NAME = "http-transport-client";
+
+  public static final String CLIENT_TAG = "rest.consumer";
 
   @Override
   public String clientName() {
@@ -34,27 +35,33 @@ public class ConfigCenterHttpClientOptionsSPI implements HttpClientOptionsSPI {
 
   @Override
   public int getOrder() {
-    return -100;
+    return 100;
   }
 
   @Override
   public boolean enabled() {
-    return Deployment.getSystemBootStrapInfo(DeploymentProvider.SYSTEM_KEY_CONFIG_CENTER) != null;
+    return TransportClientConfig.isHttpTransportClientEnabled();
   }
 
   @Override
   public String getConfigTag() {
-    return "cc.consumer";
+    return CLIENT_TAG;
   }
 
   @Override
   public int getEventLoopPoolSize() {
-    return ConfigCenterConfig.INSTANCE.getEventLoopSize();
+    // not reading this, using shared transport vert.x
+    return -1;
+  }
+
+  @Override
+  public boolean useSharedVertx() {
+    return true;
   }
 
   @Override
   public int getInstanceCount() {
-    return ConfigCenterConfig.INSTANCE.getVerticalInstanceCount();
+    return TransportClientConfig.getThreadCount();
   }
 
   @Override
@@ -79,41 +86,87 @@ public class ConfigCenterHttpClientOptionsSPI implements HttpClientOptionsSPI {
 
   @Override
   public int getConnectTimeoutInMillis() {
-    return ConfigCenterConfig.INSTANCE.getConnectionTimeout();
+    return TransportClientConfig.getConnectionTimeoutInMillis();
   }
 
   @Override
   public int getIdleTimeoutInSeconds() {
-    return ConfigCenterConfig.INSTANCE.getIdleTimeoutInSeconds();
+    return TransportClientConfig.getConnectionIdleTimeoutInSeconds();
+  }
+
+  @Override
+  public boolean isTryUseCompression() {
+    return TransportClientConfig.getConnectionCompression();
+  }
+
+  @Override
+  public int getMaxWaitQueueSize() {
+    return TransportClientConfig.getMaxWaitQueueSize();
+  }
+
+  @Override
+  public int getMaxPoolSize() {
+    return TransportClientConfig.getConnectionMaxPoolSize();
+  }
+
+  @Override
+  public boolean isKeepAlive() {
+    return TransportClientConfig.getConnectionKeepAlive();
+  }
+
+  @Override
+  public int getMaxHeaderSize() {
+    return TransportClientConfig.getMaxHeaderSize();
+  }
+
+  @Override
+  public int getKeepAliveTimeout() {
+    return TransportClientConfig.getConnectionIdleTimeoutInSeconds();
+  }
+
+  @Override
+  public int getHttp2MultiplexingLimit() {
+    return HttpClientOptions.DEFAULT_HTTP2_MULTIPLEXING_LIMIT;
+  }
+
+  @Override
+  public int getHttp2MaxPoolSize() {
+    return HttpClientOptions.DEFAULT_HTTP2_MAX_POOL_SIZE;
+  }
+
+  @Override
+  public boolean isUseAlpn() {
+    return HttpClientOptions.DEFAULT_USE_ALPN;
   }
 
   @Override
   public boolean isProxyEnable() {
-    return ConfigCenterConfig.INSTANCE.isProxyEnable();
+    // now transport proxy not implemented
+    return false;
   }
 
   @Override
   public String getProxyHost() {
-    return ConfigCenterConfig.INSTANCE.getProxyHost();
+    return null;
   }
 
   @Override
   public int getProxyPort() {
-    return ConfigCenterConfig.INSTANCE.getProxyPort();
+    return 0;
   }
 
   @Override
   public String getProxyUsername() {
-    return ConfigCenterConfig.INSTANCE.getProxyUsername();
+    return null;
   }
 
   @Override
   public String getProxyPassword() {
-    return ConfigCenterConfig.INSTANCE.getProxyPasswd();
+    return null;
   }
 
   @Override
   public boolean isSsl() {
-    return ConfigCenterConfig.INSTANCE.getServerUri().get(0).startsWith("https");
+    return true;
   }
 }
diff --git a/transports/transport-rest/transport-rest-client/src/main/java/org/apache/servicecomb/transport/rest/client/RestTransportClient.java b/transports/transport-rest/transport-rest-client/src/main/java/org/apache/servicecomb/transport/rest/client/RestTransportClient.java
index eeee42a..334d63d 100644
--- a/transports/transport-rest/transport-rest-client/src/main/java/org/apache/servicecomb/transport/rest/client/RestTransportClient.java
+++ b/transports/transport-rest/transport-rest-client/src/main/java/org/apache/servicecomb/transport/rest/client/RestTransportClient.java
@@ -23,88 +23,28 @@ import org.apache.servicecomb.common.rest.filter.HttpClientFilter;
 import org.apache.servicecomb.core.Invocation;
 import org.apache.servicecomb.foundation.common.net.URIEndpointObject;
 import org.apache.servicecomb.foundation.common.utils.SPIServiceUtils;
-import org.apache.servicecomb.foundation.vertx.VertxTLSBuilder;
-import org.apache.servicecomb.foundation.vertx.VertxUtils;
-import org.apache.servicecomb.foundation.vertx.client.ClientPoolManager;
-import org.apache.servicecomb.foundation.vertx.client.ClientVerticle;
-import org.apache.servicecomb.foundation.vertx.client.http.HttpClientPoolFactory;
 import org.apache.servicecomb.foundation.vertx.client.http.HttpClientWithContext;
+import org.apache.servicecomb.foundation.vertx.client.http.HttpClients;
 import org.apache.servicecomb.swagger.invocation.AsyncResponse;
 import org.apache.servicecomb.transport.rest.client.http.RestClientInvocation;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
-import io.vertx.core.DeploymentOptions;
 import io.vertx.core.Vertx;
-import io.vertx.core.http.HttpClientOptions;
-import io.vertx.core.http.HttpVersion;
 
 public class RestTransportClient {
   private static final Logger LOGGER = LoggerFactory.getLogger(RestTransportClient.class);
 
-  private static final String SSL_KEY = "rest.consumer";
-
-  protected ClientPoolManager<HttpClientWithContext> clientMgr;
-
-  private ClientPoolManager<HttpClientWithContext> clientMgrHttp2;
-
   private List<HttpClientFilter> httpClientFilters;
 
-  public ClientPoolManager<HttpClientWithContext> getClientMgr() {
-    return clientMgr;
-  }
-
   public void init(Vertx vertx) throws Exception {
     httpClientFilters = SPIServiceUtils.getSortedService(HttpClientFilter.class);
-
-    HttpClientOptions httpClientOptions = createHttpClientOptions(false);
-    clientMgr = new ClientPoolManager<>(vertx, new HttpClientPoolFactory(httpClientOptions));
-
-    HttpClientOptions httpClientOptionsHttp2 = createHttpClientOptions(true);
-
-    clientMgrHttp2 = new ClientPoolManager<>(vertx, new HttpClientPoolFactory(httpClientOptionsHttp2));
-
-    DeploymentOptions deployOptions = VertxUtils.createClientDeployOptions(clientMgr,
-        TransportClientConfig.getThreadCount());
-    VertxUtils.blockDeploy(vertx, ClientVerticle.class, deployOptions);
-
-    DeploymentOptions deployOptionsHttp2 = VertxUtils.createClientDeployOptions(clientMgrHttp2,
-        TransportClientConfig.getThreadCount());
-    VertxUtils.blockDeploy(vertx, ClientVerticle.class, deployOptionsHttp2);
-  }
-
-  private static HttpClientOptions createHttpClientOptions(boolean http2) {
-    HttpClientOptions httpClientOptions = new HttpClientOptions();
-    httpClientOptions
-        .setTryUseCompression(TransportClientConfig.getConnectionCompression())
-        .setMaxWaitQueueSize(TransportClientConfig.getMaxWaitQueueSize());
-    if (http2) {
-      httpClientOptions.setUseAlpn(TransportClientConfig.getUseAlpn())
-          .setHttp2ClearTextUpgrade(false)
-          .setProtocolVersion(HttpVersion.HTTP_2)
-          .setHttp2MultiplexingLimit(TransportClientConfig.getHttp2MultiplexingLimit())
-          .setHttp2MaxPoolSize(TransportClientConfig.getHttp2ConnectionMaxPoolSize())
-          .setIdleTimeout(TransportClientConfig.getHttp2ConnectionIdleTimeoutInSeconds());
-    } else {
-      httpClientOptions.setMaxPoolSize(TransportClientConfig.getConnectionMaxPoolSize())
-          .setKeepAlive(TransportClientConfig.getConnectionKeepAlive())
-          .setMaxHeaderSize(TransportClientConfig.getMaxHeaderSize())
-          .setKeepAliveTimeout(TransportClientConfig.getConnectionIdleTimeoutInSeconds())
-          .setIdleTimeout(TransportClientConfig.getConnectionIdleTimeoutInSeconds());
-    }
-    VertxTLSBuilder.buildHttpClientOptions(SSL_KEY, httpClientOptions);
-    return httpClientOptions;
   }
 
   public void send(Invocation invocation, AsyncResponse asyncResp) {
-    URIEndpointObject endpoint = (URIEndpointObject) invocation.getEndpoint().getAddress();
 
-    ClientPoolManager<HttpClientWithContext> currentClientMgr = clientMgr;
-    if (endpoint.isHttp2Enabled()) {
-      currentClientMgr = clientMgrHttp2;
-    }
+    HttpClientWithContext httpClientWithContext = findHttpClientPool(invocation);
 
-    HttpClientWithContext httpClientWithContext = findHttpClientPool(currentClientMgr, invocation);
     RestClientInvocation restClientInvocation = new RestClientInvocation(httpClientWithContext, httpClientFilters);
 
     try {
@@ -115,8 +55,15 @@ public class RestTransportClient {
     }
   }
 
-  protected HttpClientWithContext findHttpClientPool(ClientPoolManager<HttpClientWithContext> currentClientMgr,
-      Invocation invocation) {
-    return currentClientMgr.findClientPool(invocation.isSync());
+  protected HttpClientWithContext findHttpClientPool(Invocation invocation) {
+    URIEndpointObject endpoint = (URIEndpointObject) invocation.getEndpoint().getAddress();
+    HttpClientWithContext httpClientWithContext;
+    if (endpoint.isHttp2Enabled()) {
+      httpClientWithContext = HttpClients
+          .getClient(Http2TransportHttpClientOptionsSPI.CLIENT_NAME, invocation.isSync());
+    } else {
+      httpClientWithContext = HttpClients.getClient(HttpTransportHttpClientOptionsSPI.CLIENT_NAME, invocation.isSync());
+    }
+    return httpClientWithContext;
   }
 }
diff --git a/transports/transport-rest/transport-rest-client/src/main/java/org/apache/servicecomb/transport/rest/client/TransportClientConfig.java b/transports/transport-rest/transport-rest-client/src/main/java/org/apache/servicecomb/transport/rest/client/TransportClientConfig.java
index 3acb70b..c9a2fab 100644
--- a/transports/transport-rest/transport-rest-client/src/main/java/org/apache/servicecomb/transport/rest/client/TransportClientConfig.java
+++ b/transports/transport-rest/transport-rest-client/src/main/java/org/apache/servicecomb/transport/rest/client/TransportClientConfig.java
@@ -68,6 +68,13 @@ public final class TransportClientConfig {
         .get();
   }
 
+  public static boolean isHttp2TransportClientEnabled() {
+    return DynamicPropertyFactory.getInstance()
+        .getBooleanProperty("servicecomb.rest.client.http2.enabled",
+            true)
+        .get();
+  }
+
   public static int getConnectionMaxPoolSize() {
     return DynamicPropertyFactory.getInstance()
         .getIntProperty("servicecomb.rest.client.connection.maxPoolSize", HttpClientOptions.DEFAULT_MAX_POOL_SIZE)
@@ -99,10 +106,23 @@ public final class TransportClientConfig {
         .get();
   }
 
-  public static int getMaxWaitQueueSize(){
+  public static int getMaxWaitQueueSize() {
     return DynamicPropertyFactory.getInstance()
         .getIntProperty("servicecomb.rest.client.maxWaitQueueSize",
             HttpClientOptions.DEFAULT_MAX_WAIT_QUEUE_SIZE)
         .get();
   }
+
+  public static boolean isHttpTransportClientEnabled() {
+    return DynamicPropertyFactory.getInstance()
+        .getBooleanProperty("servicecomb.rest.client.enabled",
+            true)
+        .get();
+  }
+
+  public static int getConnectionTimeoutInMillis() {
+    return DynamicPropertyFactory.getInstance()
+        .getIntProperty("servicecomb.rest.client.connection.timeoutInMillis", 30)
+        .get();
+  }
 }
diff --git a/transports/transport-rest/transport-rest-client/src/main/resources/META-INF/services/org.apache.servicecomb.foundation.vertx.client.http.HttpClientOptionsSPI b/transports/transport-rest/transport-rest-client/src/main/resources/META-INF/services/org.apache.servicecomb.foundation.vertx.client.http.HttpClientOptionsSPI
new file mode 100644
index 0000000..b7e5b35
--- /dev/null
+++ b/transports/transport-rest/transport-rest-client/src/main/resources/META-INF/services/org.apache.servicecomb.foundation.vertx.client.http.HttpClientOptionsSPI
@@ -0,0 +1,19 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one or more
+# contributor license agreements.  See the NOTICE file distributed with
+# this work for additional information regarding copyright ownership.
+# The ASF licenses this file to You under the Apache License, Version 2.0
+# (the "License"); you may not use this file except in compliance with
+# the License.  You may obtain a copy of the License at
+#
+#     http://www.apache.org/licenses/LICENSE-2.0
+#
+# 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.
+#
+
+org.apache.servicecomb.transport.rest.client.HttpTransportHttpClientOptionsSPI
+org.apache.servicecomb.transport.rest.client.Http2TransportHttpClientOptionsSPI
\ No newline at end of file
diff --git a/transports/transport-rest/transport-rest-client/src/test/java/org/apache/servicecomb/transport/rest/client/TestRestTransportClient.java b/transports/transport-rest/transport-rest-client/src/test/java/org/apache/servicecomb/transport/rest/client/TestRestTransportClient.java
index 353c764..7ef39f5 100644
--- a/transports/transport-rest/transport-rest-client/src/test/java/org/apache/servicecomb/transport/rest/client/TestRestTransportClient.java
+++ b/transports/transport-rest/transport-rest-client/src/test/java/org/apache/servicecomb/transport/rest/client/TestRestTransportClient.java
@@ -17,17 +17,9 @@
 
 package org.apache.servicecomb.transport.rest.client;
 
-import java.lang.reflect.Field;
-
 import org.apache.servicecomb.common.rest.RestConst;
-import org.apache.servicecomb.common.rest.definition.RestOperationMeta;
-import org.apache.servicecomb.core.Endpoint;
 import org.apache.servicecomb.core.Invocation;
 import org.apache.servicecomb.core.definition.OperationMeta;
-import org.apache.servicecomb.foundation.common.net.URIEndpointObject;
-import org.apache.servicecomb.foundation.vertx.VertxUtils;
-import org.apache.servicecomb.foundation.vertx.client.ClientPoolManager;
-import org.apache.servicecomb.foundation.vertx.client.http.HttpClientWithContext;
 import org.apache.servicecomb.swagger.invocation.AsyncResponse;
 import org.junit.After;
 import org.junit.Assert;
@@ -35,16 +27,6 @@ import org.junit.Before;
 import org.junit.Test;
 import org.mockito.Mockito;
 
-import io.vertx.core.AbstractVerticle;
-import io.vertx.core.DeploymentOptions;
-import io.vertx.core.Vertx;
-import io.vertx.core.http.HttpClientOptions;
-import io.vertx.core.http.impl.HttpClientImpl;
-import mockit.Deencapsulation;
-import mockit.Mock;
-import mockit.MockUp;
-import mockit.Mocked;
-
 public class TestRestTransportClient {
 
   private RestTransportClient instance = null;
@@ -55,18 +37,6 @@ public class TestRestTransportClient {
 
   OperationMeta operationMeta = Mockito.mock(OperationMeta.class);
 
-  RestOperationMeta swaggerRestOperation = Mockito.mock(RestOperationMeta.class);
-
-  URIEndpointObject uriEndpointObject = Mockito.mock(URIEndpointObject.class);
-
-  Endpoint endPoint = Mockito.mock(Endpoint.class);
-
-  HttpClientWithContext httpClientWithContext = Mockito.mock(HttpClientWithContext.class);
-
-  HttpClientImpl httpClient = Mockito.mock(HttpClientImpl.class);
-
-  HttpClientOptions httpClientOptions = Mockito.mock(HttpClientOptions.class);
-
 
   @Before
   public void setUp() throws Exception {
@@ -83,22 +53,6 @@ public class TestRestTransportClient {
     Assert.assertNotNull(instance);
   }
 
-  @Test
-  public void init(@Mocked Vertx vertx, @Mocked VertxUtils utils) throws Exception {
-    new MockUp<VertxUtils>() {
-      @Mock
-      <VERTICLE extends AbstractVerticle> boolean blockDeploy(Vertx vertx,
-          Class<VERTICLE> cls,
-          DeploymentOptions options) throws InterruptedException {
-        return true;
-      }
-    };
-    RestTransportClient client = new RestTransportClient();
-    client.init(vertx);
-
-    ClientPoolManager<HttpClientWithContext> clientMgr = Deencapsulation.getField(client, "clientMgr");
-    Assert.assertSame(vertx, Deencapsulation.getField(clientMgr, "vertx"));
-  }
 
   @Test
   public void testRestTransportClientException() {
@@ -112,46 +66,4 @@ public class TestRestTransportClient {
     }
     Assert.assertFalse(status);
   }
-
-
-  @Test
-  public void testRestTransportClientHttp2(@Mocked Vertx vertx, @Mocked VertxUtils utils)
-      throws Exception {
-    boolean status = true;
-    Mockito.when(invocation.getEndpoint()).thenReturn(endPoint);
-    Mockito.when(invocation.isSync()).thenReturn(true);
-    Mockito.when(endPoint.getAddress()).thenReturn(uriEndpointObject);
-    Mockito.when(uriEndpointObject.isHttp2Enabled()).thenReturn(true);
-    Mockito.when(invocation.getOperationMeta()).thenReturn(operationMeta);
-    Mockito.when(operationMeta.getExtData(RestConst.SWAGGER_REST_OPERATION)).thenReturn(operationMeta);
-    Mockito.when(httpClientWithContext.getHttpClient()).thenReturn(httpClient);
-    Mockito.when(httpClient.getOptions()).thenReturn(httpClientOptions);
-
-    instance.init(vertx);
-    Field clientMgrHttp2Field = instance.getClass().getDeclaredField("clientMgrHttp2");
-    clientMgrHttp2Field.setAccessible(true);
-
-    ClientPoolManager<HttpClientWithContext> client = new ClientPoolManager<HttpClientWithContext>(vertx, null) {
-      @Mock
-      public HttpClientWithContext findClientPool(boolean sync) {
-        return httpClientWithContext;
-      }
-    };
-
-    clientMgrHttp2Field.set(instance, client);
-
-    try {
-      instance.send(invocation, asyncResp);
-    } catch (Exception e) {
-      status = false;
-    }
-
-    Assert.assertTrue(status);
-  }
-
-  @Test
-  public void testCreateHttpClientOptions() {
-    HttpClientOptions obj = Deencapsulation.invoke(instance, "createHttpClientOptions", false);
-    Assert.assertNotNull(obj);
-  }
 }