[
https://issues.apache.org/jira/browse/SCB-1063?page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel&focusedCommentId=16708543#comment-16708543
]
ASF GitHub Bot commented on SCB-1063:
-------------------------------------
liubao68 closed pull request #1021: [SCB-1063]Improve the time cost when first
time loading schema
URL: https://github.com/apache/servicecomb-java-chassis/pull/1021
This is a PR merged from a forked repository.
As GitHub hides the original diff on merge, it is displayed below for
the sake of provenance:
As this is a foreign pull request (from a fork), the diff is supplied
below (as it won't show otherwise due to GitHub magic):
diff --git
a/core/src/main/java/org/apache/servicecomb/core/definition/schema/ConsumerSchemaFactory.java
b/core/src/main/java/org/apache/servicecomb/core/definition/schema/ConsumerSchemaFactory.java
index c9b8ed242..aab39e973 100644
---
a/core/src/main/java/org/apache/servicecomb/core/definition/schema/ConsumerSchemaFactory.java
+++
b/core/src/main/java/org/apache/servicecomb/core/definition/schema/ConsumerSchemaFactory.java
@@ -37,6 +37,7 @@
// 允许consumerIntf与schemaId对应的interface原型不同,用于支持context类型的参数
// consumerIntf为null,表示原型与契约相同
public void createConsumerSchema(MicroserviceMeta microserviceMeta,
Microservice microservice) {
+ long start = System.currentTimeMillis();
for (String schemaId : microservice.getSchemas()) {
ConsumerSchemaContext context = new ConsumerSchemaContext();
context.setMicroserviceMeta(microserviceMeta);
@@ -46,6 +47,9 @@ public void createConsumerSchema(MicroserviceMeta
microserviceMeta, Microservice
getOrCreateSchema(context);
}
+
+ LOGGER.info("Loading schema for service {} token {}",
microservice.getServiceId(),
+ (System.currentTimeMillis() - start));
}
@Override
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 246e8a40d..ba7c8c3c1 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
@@ -92,7 +92,9 @@ public void start(Future<Void> startFuture) {
public void start(Future<Void> startFuture) {
HttpClient client = vertx.createHttpClient();
client.post(port, "127.0.0.1", "/").handler(resp -> {
- startFuture.complete();
+ resp.bodyHandler((buffer) -> {
+ startFuture.complete();
+ });
}).end(body);
}
}
diff --git
a/service-registry/src/main/java/org/apache/servicecomb/serviceregistry/client/http/ServiceRegistryClientImpl.java
b/service-registry/src/main/java/org/apache/servicecomb/serviceregistry/client/http/ServiceRegistryClientImpl.java
index c27ba96fe..3ee0fe818 100644
---
a/service-registry/src/main/java/org/apache/servicecomb/serviceregistry/client/http/ServiceRegistryClientImpl.java
+++
b/service-registry/src/main/java/org/apache/servicecomb/serviceregistry/client/http/ServiceRegistryClientImpl.java
@@ -21,10 +21,13 @@
import java.nio.charset.Charset;
import java.util.ArrayList;
+import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.CountDownLatch;
+import java.util.concurrent.ExecutionException;
+import java.util.concurrent.TimeUnit;
import javax.ws.rs.core.Response.Status;
@@ -60,6 +63,9 @@
import org.slf4j.LoggerFactory;
import com.google.common.annotations.VisibleForTesting;
+import com.google.common.cache.CacheBuilder;
+import com.google.common.cache.CacheLoader;
+import com.google.common.cache.LoadingCache;
import io.netty.handler.codec.http.HttpStatusClass;
import io.vertx.core.Handler;
@@ -79,6 +85,18 @@ public ServiceRegistryClientImpl(IpPortManager
ipPortManager) {
this.ipPortManager = ipPortManager;
}
+ private LoadingCache<String, Map<String, String>> schemaCache =
CacheBuilder.newBuilder()
+ .expireAfterAccess(60, TimeUnit.SECONDS).build(new CacheLoader<String,
Map<String, String>>() {
+ public Map<String, String> load(String key) {
+ Holder<List<GetSchemaResponse>> result = getSchemas(key, true, true);
+ Map<String, String> schemas = new HashMap<>();
+ if (result.getStatusCode() == Status.OK.getStatusCode() ) {
+ result.value.stream().forEach(r -> schemas.put(r.getSchemaId(),
r.getSchema()));
+ }
+ return schemas;
+ }
+ });
+
@Override
public void init() {
}
@@ -350,6 +368,16 @@ public String getSchema(String microserviceId, String
schemaId) {
}
private String doGetSchema(String microserviceId, String schemaId, boolean
global) {
+ try {
+ // avoid query too many times of schema when first time loading
+ String cachedSchema = schemaCache.get(microserviceId).get(schemaId);
+ if (cachedSchema != null) {
+ return cachedSchema;
+ }
+ } catch (ExecutionException e) {
+ // ignore this error.
+ }
+
Holder<GetSchemaResponse> holder = new Holder<>();
IpPort ipPort = ipPortManager.getAvailableAddress();
@@ -383,15 +411,27 @@ public String getAggregatedSchema(String microserviceId,
String schemaId) {
@Override
public Holder<List<GetSchemaResponse>> getSchemas(String microserviceId) {
+ return getSchemas(microserviceId, false, false);
+ }
+
+ private Holder<List<GetSchemaResponse>> getSchemas(String microserviceId,
boolean withSchema, boolean global) {
Holder<GetSchemasResponse> holder = new Holder<>();
IpPort ipPort = ipPortManager.getAvailableAddress();
Holder<List<GetSchemaResponse>> resultHolder = new Holder<>();
CountDownLatch countDownLatch = new CountDownLatch(1);
- // default not return schema content, just return summary!
+ String url = Const.REGISTRY_API.MICROSERVICE_ALL_SCHEMAs;
+ RequestParam requestParam = new RequestParam();
+ if (withSchema) {
+ url = Const.REGISTRY_API.MICROSERVICE_ALL_SCHEMAs + "?withSchema=1";
+ }
+ if (global) {
+ requestParam.addQueryParam("global", "true");
+ }
+
RestUtils.get(ipPort,
- String.format(Const.REGISTRY_API.MICROSERVICE_ALL_SCHEMAs,
microserviceId),
- new RequestParam(),
+ String.format(url, microserviceId),
+ requestParam,
syncHandler(countDownLatch, GetSchemasResponse.class, holder));
try {
countDownLatch.await();
diff --git
a/service-registry/src/test/java/org/apache/servicecomb/serviceregistry/client/http/TestServiceRegistryClientImpl.java
b/service-registry/src/test/java/org/apache/servicecomb/serviceregistry/client/http/TestServiceRegistryClientImpl.java
index cba18e24d..900f534d6 100644
---
a/service-registry/src/test/java/org/apache/servicecomb/serviceregistry/client/http/TestServiceRegistryClientImpl.java
+++
b/service-registry/src/test/java/org/apache/servicecomb/serviceregistry/client/http/TestServiceRegistryClientImpl.java
@@ -20,8 +20,11 @@
import static org.hamcrest.core.Is.is;
import java.util.ArrayList;
+import java.util.HashMap;
import java.util.List;
+import java.util.Map;
import java.util.concurrent.CountDownLatch;
+import java.util.concurrent.TimeUnit;
import javax.ws.rs.core.Response.Status;
@@ -47,6 +50,10 @@
import org.junit.Test;
import org.mockito.Mockito;
+import com.google.common.cache.CacheBuilder;
+import com.google.common.cache.CacheLoader;
+import com.google.common.cache.LoadingCache;
+
import io.vertx.core.Handler;
import io.vertx.core.buffer.Buffer;
import io.vertx.core.http.HttpClientOptions;
@@ -343,8 +350,21 @@ void httpDo(RequestContext requestContext,
Handler<RestResponse> responseHandler
Assert.assertEquals("global=true", requestParam.getQueryParams());
}
};
+
+ LoadingCache<String, Map<String, String>> oldCache =
Deencapsulation.getField(oClient, "schemaCache");
+ LoadingCache<String, Map<String, String>> newCache =
CacheBuilder.newBuilder()
+ .expireAfterAccess(60, TimeUnit.SECONDS).build(new CacheLoader<String,
Map<String, String>>() {
+ public Map<String, String> load(String key) {
+ Map<String, String> schemas = new HashMap<>();
+ return schemas;
+ }
+ });
+ Deencapsulation.setField(oClient, "schemaCache", newCache);
+
String str = oClient.getAggregatedSchema(microserviceId, schemaId);
Assert.assertEquals("schema", str);
+
+ Deencapsulation.setField(oClient, "schemaCache", oldCache);
}
@Test
----------------------------------------------------------------
This is an automated message from the Apache Git Service.
To respond to the message, please log on GitHub and use the
URL above to go to the specific comment.
For queries about this service, please contact Infrastructure at:
[email protected]
> Improve the time cost when first time loading schema
> ----------------------------------------------------
>
> Key: SCB-1063
> URL: https://issues.apache.org/jira/browse/SCB-1063
> Project: Apache ServiceComb
> Issue Type: Improvement
> Components: Java-Chassis
> Reporter: liubao
> Assignee: liubao
> Priority: Major
>
> When first time to invoke a service, will download each schema and compile
> classes. Sometimes users got hundreds of schema, this will taken more than
> 30s and the first time invocation can get easily timeout.
>
> There are some improvements can be done:
> # loading and compile concurrently
> # fetch all schema in one invocation in service center.
>
> Notice:
> for edge, we should not cache all microservice schema, because some deleted
> service will not be used forever.
>
--
This message was sent by Atlassian JIRA
(v7.6.3#76005)