|
28 | 28 | import com.tencent.polaris.factory.api.APIFactory; |
29 | 29 | import com.tencent.trpc.core.common.ConfigManager; |
30 | 30 | import com.tencent.trpc.core.common.config.PluginConfig; |
| 31 | +import com.tencent.trpc.core.constant.proto.HttpConstants; |
31 | 32 | import com.tencent.trpc.core.rpc.Request; |
| 33 | +import com.tencent.trpc.core.rpc.RequestMeta; |
| 34 | +import com.tencent.trpc.core.rpc.RpcClientContext; |
32 | 35 | import com.tencent.trpc.core.selector.ServiceId; |
33 | 36 | import com.tencent.trpc.core.selector.ServiceInstance; |
34 | 37 | import com.tencent.trpc.polaris.common.PolarisTrans; |
35 | 38 | import com.tencent.trpc.selector.polaris.PolarisSelector; |
36 | 39 | import com.tencent.trpc.selector.polaris.common.pojo.PolarisServiceInstances; |
| 40 | +import java.net.InetSocketAddress; |
37 | 41 | import java.util.ArrayList; |
38 | 42 | import java.util.HashMap; |
39 | 43 | import java.util.List; |
|
43 | 47 | import java.util.concurrent.ExecutionException; |
44 | 48 | import java.util.concurrent.atomic.AtomicReference; |
45 | 49 | import java.util.stream.Collectors; |
| 50 | +import javax.servlet.http.HttpServletRequest; |
46 | 51 | import org.junit.After; |
47 | 52 | import org.junit.Assert; |
48 | 53 | import org.junit.Before; |
@@ -103,6 +108,39 @@ public void testEmptyReturn() { |
103 | 108 | }); |
104 | 109 | } |
105 | 110 |
|
| 111 | + @Test |
| 112 | + public void testWarmupWithEmptyInstances() { |
| 113 | + ServiceId serviceId = DataTest.newServiceId(); |
| 114 | + serviceId.setServiceName("service_empty"); |
| 115 | + |
| 116 | + PolarisSelector clusterNaming = new PolarisSelector(); |
| 117 | + clusterNaming.setPluginConfig(selectorConfig); |
| 118 | + clusterNaming.init(); |
| 119 | + |
| 120 | + try { |
| 121 | + clusterNaming.warmup(serviceId); |
| 122 | + } catch (Exception e) { |
| 123 | + Assert.fail("warmup should not throw exception for empty instances: " + e.getMessage()); |
| 124 | + } |
| 125 | + } |
| 126 | + |
| 127 | + @Test |
| 128 | + public void testSelectEmptyInstances() throws Exception { |
| 129 | + ServiceId serviceId = DataTest.newServiceId(); |
| 130 | + serviceId.setServiceName("service_empty"); |
| 131 | + |
| 132 | + PolarisSelector clusterNaming = new PolarisSelector(); |
| 133 | + clusterNaming.setPluginConfig(selectorConfig); |
| 134 | + clusterNaming.init(); |
| 135 | + |
| 136 | + CompletionStage<List<ServiceInstance>> future = clusterNaming.asyncSelectAll(serviceId, DataTest.request); |
| 137 | + List<ServiceInstance> result = future.toCompletableFuture().get(); |
| 138 | + |
| 139 | + Assert.assertNotNull("result should not be null", result); |
| 140 | + Assert.assertTrue("result should be empty list", result.isEmpty()); |
| 141 | + Assert.assertEquals("result size should be 0", 0, result.size()); |
| 142 | + } |
| 143 | + |
106 | 144 | @Test |
107 | 145 | public void testExp() { |
108 | 146 | ServiceId expService = DataTest.getExpService(); |
@@ -250,6 +288,9 @@ private Answer<InstancesFuture> newPolarisAnswer(boolean getOne) { |
250 | 288 | if (service.contains("fallback") && getOne) { |
251 | 289 | size = 0; |
252 | 290 | } |
| 291 | + if (service.contains("fallback_null")) { |
| 292 | + size = 0; |
| 293 | + } |
253 | 294 | CompletableFuture<InstancesResponse> instancesResponseCompletableFuture = CompletableFuture |
254 | 295 | .completedFuture(new InstancesResponse(getServiceInstances(size), null, null)); |
255 | 296 | InstancesFuture instancesFuture = new InstancesFuture(() -> { |
@@ -334,4 +375,203 @@ public void testGetConsumerAPI() { |
334 | 375 | Assert.assertNotNull(polarisSelector.getPolarisAPI()); |
335 | 376 | polarisSelector.destroy(); |
336 | 377 | } |
| 378 | + |
| 379 | + @Test |
| 380 | + public void testAsyncSelectOneWithHashVal() { |
| 381 | + PolarisSelector clusterNaming = new PolarisSelector(); |
| 382 | + clusterNaming.setPluginConfig(selectorConfig); |
| 383 | + clusterNaming.init(); |
| 384 | + |
| 385 | + Request request = DataTest.mockRequest(); |
| 386 | + RequestMeta meta = request.getMeta(); |
| 387 | + meta.setHashVal("test-hash-value"); |
| 388 | + ServiceId serviceId = DataTest.newServiceId(); |
| 389 | + |
| 390 | + CompletionStage<ServiceInstance> future = clusterNaming.asyncSelectOne(serviceId, request); |
| 391 | + AtomicReference<Throwable> errorRef = new AtomicReference<>(); |
| 392 | + AtomicReference<ServiceInstance> resultRef = new AtomicReference<>(); |
| 393 | + CompletionStage<ServiceInstance> stage = future.whenComplete((res, err) -> { |
| 394 | + if (err != null) { |
| 395 | + errorRef.set(err); |
| 396 | + } |
| 397 | + resultRef.set(res); |
| 398 | + }); |
| 399 | + CompletableFuture.allOf(stage.toCompletableFuture()).join(); |
| 400 | + } |
| 401 | + |
| 402 | + @Test |
| 403 | + public void testNullExtMap() { |
| 404 | + Map<String, Object> extMap = new HashMap<>(); |
| 405 | + extMap.put("worker_pool", "selector_pool1"); |
| 406 | + PluginConfig config = new PluginConfig("selector_null_ext", PolarisSelector.class, extMap); |
| 407 | + |
| 408 | + PolarisSelector selector = new PolarisSelector(); |
| 409 | + selector.setPluginConfig(config); |
| 410 | + selector.init(); |
| 411 | + Assert.assertNotNull(selector.getPolarisAPI()); |
| 412 | + selector.destroy(); |
| 413 | + } |
| 414 | + |
| 415 | + @Test |
| 416 | + public void testWarmupException() { |
| 417 | + ServiceId serviceId = DataTest.getExpService(); |
| 418 | + |
| 419 | + PolarisSelector clusterNaming = new PolarisSelector(); |
| 420 | + clusterNaming.setPluginConfig(selectorConfig); |
| 421 | + clusterNaming.init(); |
| 422 | + |
| 423 | + try { |
| 424 | + clusterNaming.warmup(serviceId); |
| 425 | + } catch (Exception e) { |
| 426 | + Assert.assertTrue(e.getMessage().contains("call polaris error") || |
| 427 | + e.getCause() != null && e.getCause().getMessage().contains("test polaris exp")); |
| 428 | + } |
| 429 | + } |
| 430 | + |
| 431 | + @Test |
| 432 | + public void testAsyncSelectAllException() { |
| 433 | + ServiceId serviceId = DataTest.getExpService(); |
| 434 | + |
| 435 | + PolarisSelector clusterNaming = new PolarisSelector(); |
| 436 | + clusterNaming.setPluginConfig(selectorConfig); |
| 437 | + clusterNaming.init(); |
| 438 | + |
| 439 | + try { |
| 440 | + CompletionStage<List<ServiceInstance>> future = clusterNaming.asyncSelectAll(serviceId, DataTest.request); |
| 441 | + future.toCompletableFuture().join(); |
| 442 | + } catch (Exception e) { |
| 443 | + Assert.assertTrue(e.getMessage().contains("call polaris error") || |
| 444 | + (e.getCause() != null && e.getCause().getMessage().contains("test polaris exp"))); |
| 445 | + } |
| 446 | + } |
| 447 | + |
| 448 | + @Test |
| 449 | + public void testSelectOneFallbackReturnsNull() { |
| 450 | + ServiceId serviceId = DataTest.newServiceId(); |
| 451 | + serviceId.setServiceName("fallback_null"); |
| 452 | + |
| 453 | + PolarisSelector clusterNaming = new PolarisSelector(); |
| 454 | + clusterNaming.setPluginConfig(selectorConfig); |
| 455 | + clusterNaming.init(); |
| 456 | + |
| 457 | + CompletionStage<ServiceInstance> future = clusterNaming.asyncSelectOne(serviceId, DataTest.request); |
| 458 | + AtomicReference<ServiceInstance> resultRef = new AtomicReference<>(); |
| 459 | + CompletionStage<ServiceInstance> stage = future.whenComplete((res, err) -> { |
| 460 | + resultRef.set(res); |
| 461 | + }); |
| 462 | + CompletableFuture.allOf(stage.toCompletableFuture()).join(); |
| 463 | + } |
| 464 | + |
| 465 | + @Test |
| 466 | + public void tesSelectAllNamespace() { |
| 467 | + PolarisSelector clusterNaming = new PolarisSelector(); |
| 468 | + clusterNaming.setPluginConfig(selectorConfig); |
| 469 | + clusterNaming.init(); |
| 470 | + |
| 471 | + ServiceId serviceId = DataTest.newServiceId(); |
| 472 | + CompletionStage<List<ServiceInstance>> future = clusterNaming.asyncSelectAll(serviceId, DataTest.request); |
| 473 | + |
| 474 | + AtomicReference<Throwable> errorRef = new AtomicReference<>(); |
| 475 | + CompletionStage<List<ServiceInstance>> stage = future.whenComplete((res, err) -> { |
| 476 | + if (err != null) { |
| 477 | + errorRef.set(err); |
| 478 | + } |
| 479 | + }); |
| 480 | + CompletableFuture.allOf(stage.toCompletableFuture()).join(); |
| 481 | + Assert.assertNull(errorRef.get()); |
| 482 | + } |
| 483 | + |
| 484 | + |
| 485 | + @Test |
| 486 | + public void testSelectOneMetadataContext() { |
| 487 | + PolarisSelector clusterNaming = new PolarisSelector(); |
| 488 | + clusterNaming.setPluginConfig(selectorConfig); |
| 489 | + clusterNaming.init(); |
| 490 | + |
| 491 | + ServiceId serviceId = DataTest.newServiceId(); |
| 492 | + Request request = DataTest.mockRequest(); |
| 493 | + |
| 494 | + CompletionStage<ServiceInstance> future = clusterNaming.asyncSelectOne(serviceId, request); |
| 495 | + AtomicReference<Throwable> errorRef = new AtomicReference<>(); |
| 496 | + CompletionStage<ServiceInstance> stage = future.whenComplete((res, err) -> { |
| 497 | + if (err != null) { |
| 498 | + errorRef.set(err); |
| 499 | + } |
| 500 | + }); |
| 501 | + CompletableFuture.allOf(stage.toCompletableFuture()).join(); |
| 502 | + Assert.assertNull(errorRef.get()); |
| 503 | + } |
| 504 | + |
| 505 | + @Test |
| 506 | + public void testServletRequest() { |
| 507 | + PolarisSelector clusterNaming = new PolarisSelector(); |
| 508 | + clusterNaming.setPluginConfig(selectorConfig); |
| 509 | + clusterNaming.init(); |
| 510 | + |
| 511 | + ServiceId serviceId = DataTest.newServiceId(); |
| 512 | + Request request = DataTest.mockRequest(); |
| 513 | + RpcClientContext context = new RpcClientContext(); |
| 514 | + |
| 515 | + HttpServletRequest servletRequest = Mockito.mock(HttpServletRequest.class); |
| 516 | + Mockito.when(servletRequest.getHeader(Mockito.anyString())).thenReturn("test-value"); |
| 517 | + context.getReqAttachMap().put(HttpConstants.TRPC_ATTACH_SERVLET_REQUEST, servletRequest); |
| 518 | + Mockito.when(request.getContext()).thenReturn(context); |
| 519 | + |
| 520 | + CompletionStage<ServiceInstance> future = clusterNaming.asyncSelectOne(serviceId, request); |
| 521 | + AtomicReference<Throwable> errorRef = new AtomicReference<>(); |
| 522 | + CompletionStage<ServiceInstance> stage = future.whenComplete((res, err) -> { |
| 523 | + if (err != null) { |
| 524 | + errorRef.set(err); |
| 525 | + } |
| 526 | + }); |
| 527 | + CompletableFuture.allOf(stage.toCompletableFuture()).join(); |
| 528 | + Assert.assertNull(errorRef.get()); |
| 529 | + } |
| 530 | + |
| 531 | + @Test |
| 532 | + public void testCustomHeaders() { |
| 533 | + PolarisSelector clusterNaming = new PolarisSelector(); |
| 534 | + clusterNaming.setPluginConfig(selectorConfig); |
| 535 | + clusterNaming.init(); |
| 536 | + |
| 537 | + ServiceId serviceId = DataTest.newServiceId(); |
| 538 | + Request request = DataTest.mockRequest(); |
| 539 | + RpcClientContext context = new RpcClientContext(); |
| 540 | + context.getReqAttachMap().put("custom-header", "custom-value"); |
| 541 | + Mockito.when(request.getContext()).thenReturn(context); |
| 542 | + |
| 543 | + CompletionStage<ServiceInstance> future = clusterNaming.asyncSelectOne(serviceId, request); |
| 544 | + AtomicReference<Throwable> errorRef = new AtomicReference<>(); |
| 545 | + CompletionStage<ServiceInstance> stage = future.whenComplete((res, err) -> { |
| 546 | + if (err != null) { |
| 547 | + errorRef.set(err); |
| 548 | + } |
| 549 | + }); |
| 550 | + CompletableFuture.allOf(stage.toCompletableFuture()).join(); |
| 551 | + Assert.assertNull(errorRef.get()); |
| 552 | + } |
| 553 | + |
| 554 | + @Test |
| 555 | + public void testRemoteAddress() { |
| 556 | + PolarisSelector clusterNaming = new PolarisSelector(); |
| 557 | + clusterNaming.setPluginConfig(selectorConfig); |
| 558 | + clusterNaming.init(); |
| 559 | + |
| 560 | + ServiceId serviceId = DataTest.newServiceId(); |
| 561 | + Request request = DataTest.mockRequest(); |
| 562 | + RequestMeta meta = new RequestMeta(); |
| 563 | + meta.setRemoteAddress(new InetSocketAddress("192.168.1.1", 8080)); |
| 564 | + meta.getCallInfo().setCalleeMethod("testMethod"); |
| 565 | + Mockito.when(request.getMeta()).thenReturn(meta); |
| 566 | + |
| 567 | + CompletionStage<ServiceInstance> future = clusterNaming.asyncSelectOne(serviceId, request); |
| 568 | + AtomicReference<Throwable> errorRef = new AtomicReference<>(); |
| 569 | + CompletionStage<ServiceInstance> stage = future.whenComplete((res, err) -> { |
| 570 | + if (err != null) { |
| 571 | + errorRef.set(err); |
| 572 | + } |
| 573 | + }); |
| 574 | + CompletableFuture.allOf(stage.toCompletableFuture()).join(); |
| 575 | + Assert.assertNull(errorRef.get()); |
| 576 | + } |
337 | 577 | } |
0 commit comments