Search in sources :

Example 6 with PartitionState

use of com.linkedin.d2.balancer.strategies.relative.PartitionState in project rest.li by linkedin.

the class StateUpdaterTest method testInitializePartitionWithMultipleThreads.

@Test
public void testInitializePartitionWithMultipleThreads() throws InterruptedException {
    setup(new D2RelativeStrategyProperties(), new ConcurrentHashMap<>());
    List<TrackerClient> trackerClients = TrackerClientMockHelper.mockTrackerClients(2, Arrays.asList(20, 20), Arrays.asList(10, 10), Arrays.asList(200L, 500L), Arrays.asList(100L, 200L), Arrays.asList(0, 0));
    assertTrue(_stateUpdater.getPointsMap(DEFAULT_PARTITION_ID).isEmpty(), "There should be no state before initialization");
    int numThreads = 50;
    ExecutorService executorService = Executors.newFixedThreadPool(numThreads);
    CountDownLatch countDownLatch = new CountDownLatch(numThreads);
    Runnable runnable = () -> {
        PartitionState lastState = _stateUpdater.getPartitionState(DEFAULT_PARTITION_ID);
        _stateUpdater.updateState(new HashSet<>(trackerClients), DEFAULT_PARTITION_ID, DEFAULT_CLUSTER_GENERATION_ID, false);
        PartitionState currentState = _stateUpdater.getPartitionState(DEFAULT_PARTITION_ID);
        if (lastState != null) {
            assertEquals(currentState, lastState, "The partition state should always be the same object created by the first thread that obtained the lock");
        }
    };
    for (int threadIndex = 0; threadIndex < numThreads; threadIndex++) {
        runIndividualConcurrentTask(executorService, runnable, countDownLatch);
    }
    if (!countDownLatch.await(2, TimeUnit.SECONDS)) {
        fail("Initialization failed to finish within 2 seconds");
    }
    assertEquals(_stateUpdater.getPointsMap(DEFAULT_PARTITION_ID).get(trackerClients.get(0).getUri()).intValue(), HEALTHY_POINTS);
    assertEquals(_stateUpdater.getPointsMap(DEFAULT_PARTITION_ID).get(trackerClients.get(1).getUri()).intValue(), HEALTHY_POINTS);
    executorService.shutdown();
}
Also used : TrackerClient(com.linkedin.d2.balancer.clients.TrackerClient) ScheduledExecutorService(java.util.concurrent.ScheduledExecutorService) ExecutorService(java.util.concurrent.ExecutorService) CountDownLatch(java.util.concurrent.CountDownLatch) D2RelativeStrategyProperties(com.linkedin.d2.D2RelativeStrategyProperties) HashSet(java.util.HashSet) Test(org.testng.annotations.Test)

Example 7 with PartitionState

use of com.linkedin.d2.balancer.strategies.relative.PartitionState in project rest.li by linkedin.

the class StateUpdaterTest method testUpdateMultiplePartitions.

@Test
public void testUpdateMultiplePartitions() {
    /**
     * There are 2 partitions, and 4 tracker clients in total.
     * Partition 0 contains tracker client 1,2,3
     * Partition 1 contains tracker client 3,4
     * TrackerClient 3 will be unhealthy in partition 0, but not in partition 1
     */
    List<TrackerClient> trackerClients1 = TrackerClientMockHelper.mockTrackerClients(3, Arrays.asList(20, 20, 20), Arrays.asList(10, 10, 10), Arrays.asList(200L, 300L, 1000L), Arrays.asList(100L, 200L, 500L), Arrays.asList(0, 0, 0));
    List<TrackerClient> trackerClients2 = TrackerClientMockHelper.mockTrackerClients(1, Arrays.asList(20), Arrays.asList(10), Arrays.asList(1000L), Arrays.asList(600L), Arrays.asList(0));
    trackerClients2.add(trackerClients1.get(2));
    PartitionState state1 = new PartitionStateTestDataBuilder().setClusterGenerationId(DEFAULT_CLUSTER_GENERATION_ID).setTrackerClientStateMap(trackerClients1, Arrays.asList(StateUpdater.MAX_HEALTH_SCORE, StateUpdater.MAX_HEALTH_SCORE, StateUpdater.MAX_HEALTH_SCORE), Arrays.asList(TrackerClientState.HealthState.HEALTHY, TrackerClientState.HealthState.HEALTHY, TrackerClientState.HealthState.HEALTHY), Arrays.asList(30, 30, 30)).build();
    PartitionState state2 = new PartitionStateTestDataBuilder().setClusterGenerationId(DEFAULT_CLUSTER_GENERATION_ID).setTrackerClientStateMap(trackerClients2, Arrays.asList(StateUpdater.MAX_HEALTH_SCORE, StateUpdater.MAX_HEALTH_SCORE), Arrays.asList(TrackerClientState.HealthState.HEALTHY, TrackerClientState.HealthState.HEALTHY), Arrays.asList(30, 30)).build();
    ConcurrentMap<Integer, PartitionState> partitionLoadBalancerStateMap = new ConcurrentHashMap<>();
    partitionLoadBalancerStateMap.put(0, state1);
    partitionLoadBalancerStateMap.put(1, state2);
    setup(new D2RelativeStrategyProperties(), partitionLoadBalancerStateMap);
    _stateUpdater.updateState();
    URI overlapUri = trackerClients1.get(2).getUri();
    assertEquals(partitionLoadBalancerStateMap.get(0).getPointsMap().get(overlapUri).intValue(), (int) (HEALTHY_POINTS - RelativeLoadBalancerStrategyFactory.DEFAULT_DOWN_STEP * RelativeLoadBalancerStrategyFactory.DEFAULT_POINTS_PER_WEIGHT));
    assertEquals(partitionLoadBalancerStateMap.get(1).getPointsMap().get(overlapUri).intValue(), HEALTHY_POINTS);
}
Also used : TrackerClient(com.linkedin.d2.balancer.clients.TrackerClient) ConcurrentHashMap(java.util.concurrent.ConcurrentHashMap) URI(java.net.URI) D2RelativeStrategyProperties(com.linkedin.d2.D2RelativeStrategyProperties) Test(org.testng.annotations.Test)

Example 8 with PartitionState

use of com.linkedin.d2.balancer.strategies.relative.PartitionState in project rest.li by linkedin.

the class StateUpdaterTest method testUpdateOnePartition.

@Test
public void testUpdateOnePartition() {
    List<TrackerClient> trackerClients = TrackerClientMockHelper.mockTrackerClients(3, Arrays.asList(20, 20, 20), Arrays.asList(10, 10, 10), Arrays.asList(200L, 300L, 1000L), Arrays.asList(100L, 200L, 500L), Arrays.asList(0, 0, 0));
    PartitionState state = new PartitionStateTestDataBuilder().setClusterGenerationId(DEFAULT_CLUSTER_GENERATION_ID).setTrackerClientStateMap(trackerClients, Arrays.asList(1.0, 1.0, 1.0), Arrays.asList(TrackerClientState.HealthState.HEALTHY, TrackerClientState.HealthState.HEALTHY, TrackerClientState.HealthState.HEALTHY), Arrays.asList(30, 30, 30)).build();
    ConcurrentMap<Integer, PartitionState> partitionLoadBalancerStateMap = new ConcurrentHashMap<>();
    partitionLoadBalancerStateMap.put(DEFAULT_PARTITION_ID, state);
    setup(new D2RelativeStrategyProperties(), partitionLoadBalancerStateMap);
    _stateUpdater.updateState();
    Map<URI, Integer> pointsMap = _stateUpdater.getPointsMap(DEFAULT_PARTITION_ID);
    assertEquals(pointsMap.get(trackerClients.get(0).getUri()).intValue(), HEALTHY_POINTS);
    assertEquals(pointsMap.get(trackerClients.get(1).getUri()).intValue(), HEALTHY_POINTS);
    assertEquals(pointsMap.get(trackerClients.get(2).getUri()).intValue(), (int) (HEALTHY_POINTS - RelativeLoadBalancerStrategyFactory.DEFAULT_DOWN_STEP * RelativeLoadBalancerStrategyFactory.DEFAULT_POINTS_PER_WEIGHT));
}
Also used : TrackerClient(com.linkedin.d2.balancer.clients.TrackerClient) ConcurrentHashMap(java.util.concurrent.ConcurrentHashMap) URI(java.net.URI) D2RelativeStrategyProperties(com.linkedin.d2.D2RelativeStrategyProperties) Test(org.testng.annotations.Test)

Example 9 with PartitionState

use of com.linkedin.d2.balancer.strategies.relative.PartitionState in project rest.li by linkedin.

the class StateUpdaterTest method testExecutorSchedule.

@Test
public void testExecutorSchedule() throws InterruptedException {
    setup(new D2RelativeStrategyProperties(), new ConcurrentHashMap<>());
    List<TrackerClient> trackerClients = TrackerClientMockHelper.mockTrackerClients(2, Arrays.asList(20, 20), Arrays.asList(10, 10), Arrays.asList(200L, 200L), Arrays.asList(100L, 100L), Arrays.asList(0, 0));
    PartitionState existingState = new PartitionStateTestDataBuilder().setTrackerClientStateMap(trackerClients, Arrays.asList(1.0, 1.0), Arrays.asList(TrackerClientState.HealthState.HEALTHY, TrackerClientState.HealthState.HEALTHY), Arrays.asList(30, 30)).build();
    ConcurrentMap<Integer, PartitionState> stateMap = new ConcurrentHashMap<>();
    stateMap.put(DEFAULT_PARTITION_ID, existingState);
    ScheduledExecutorService executorService = Executors.newSingleThreadScheduledExecutor();
    D2RelativeStrategyProperties relativeStrategyProperties = RelativeLoadBalancerStrategyFactory.putDefaultValues(new D2RelativeStrategyProperties());
    _stateUpdater = new StateUpdater(relativeStrategyProperties, _quarantineManager, executorService, stateMap, Collections.emptyList(), SERVICE_NAME);
    // In 6 seconds, the update should be executed twice
    CountDownLatch countDownLatch = new CountDownLatch(2);
    Mockito.doAnswer(new ExecutionCountDown<>(countDownLatch)).when(_quarantineManager).updateQuarantineState(any(), any(), anyLong());
    if (!countDownLatch.await(6, TimeUnit.SECONDS)) {
        fail("scheduled update failed to finish within 6 seconds");
    }
    Mockito.verify(_quarantineManager, Mockito.atLeast(2)).updateQuarantineState(any(), any(), anyLong());
    assertEquals(_stateUpdater.getPointsMap(DEFAULT_PARTITION_ID).get(trackerClients.get(0).getUri()).intValue(), HEALTHY_POINTS);
    assertEquals(_stateUpdater.getPointsMap(DEFAULT_PARTITION_ID).get(trackerClients.get(1).getUri()).intValue(), HEALTHY_POINTS);
    executorService.shutdown();
}
Also used : ScheduledExecutorService(java.util.concurrent.ScheduledExecutorService) CountDownLatch(java.util.concurrent.CountDownLatch) TrackerClient(com.linkedin.d2.balancer.clients.TrackerClient) ConcurrentHashMap(java.util.concurrent.ConcurrentHashMap) D2RelativeStrategyProperties(com.linkedin.d2.D2RelativeStrategyProperties) Test(org.testng.annotations.Test)

Example 10 with PartitionState

use of com.linkedin.d2.balancer.strategies.relative.PartitionState in project rest.li by linkedin.

the class QuarantineManagerTest method testEnrollOneQuarantineOneRecovery.

@Test
public void testEnrollOneQuarantineOneRecovery() {
    LoadBalancerQuarantine quarantine = Mockito.mock(LoadBalancerQuarantine.class);
    List<TrackerClient> trackerClients = TrackerClientMockHelper.mockTrackerClients(3);
    Map<TrackerClient, LoadBalancerQuarantine> existingQuarantineMap = new HashMap<>();
    existingQuarantineMap.put(trackerClients.get(1), quarantine);
    Mockito.when(quarantine.checkUpdateQuarantineState()).thenReturn(true);
    setup(0.5, true, true);
    _quarantineManager.tryEnableQuarantine();
    PartitionState state = new PartitionStateTestDataBuilder().setTrackerClientStateMap(trackerClients, Arrays.asList(StateUpdater.MIN_HEALTH_SCORE, StateUpdater.MIN_HEALTH_SCORE, QuarantineManager.INITIAL_RECOVERY_HEALTH_SCORE), Arrays.asList(TrackerClientState.HealthState.UNHEALTHY, TrackerClientState.HealthState.NEUTRAL, TrackerClientState.HealthState.UNHEALTHY), Arrays.asList(20, 20, 20)).build();
    _quarantineManager.updateQuarantineState(state, state, DEFAULT_AVG_CLUSTER_LATENCY);
    assertEquals(state.getRecoveryTrackerClients().size(), 1);
    assertTrue(state.getRecoveryTrackerClients().contains(trackerClients.get(1)));
    assertEquals(state.getQuarantineMap().size(), 1);
    assertTrue(state.getQuarantineMap().containsKey(trackerClients.get(0)));
}
Also used : LoadBalancerQuarantine(com.linkedin.d2.balancer.strategies.LoadBalancerQuarantine) TrackerClient(com.linkedin.d2.balancer.clients.TrackerClient) HashMap(java.util.HashMap) Test(org.testng.annotations.Test)

Aggregations

TrackerClient (com.linkedin.d2.balancer.clients.TrackerClient)17 Test (org.testng.annotations.Test)12 D2RelativeStrategyProperties (com.linkedin.d2.D2RelativeStrategyProperties)10 ConcurrentHashMap (java.util.concurrent.ConcurrentHashMap)9 URI (java.net.URI)6 LoadBalancerQuarantine (com.linkedin.d2.balancer.strategies.LoadBalancerQuarantine)5 HashMap (java.util.HashMap)5 ScheduledExecutorService (java.util.concurrent.ScheduledExecutorService)5 CountDownLatch (java.util.concurrent.CountDownLatch)4 CallTracker (com.linkedin.util.degrader.CallTracker)2 ArrayList (java.util.ArrayList)2 HashSet (java.util.HashSet)2 None (com.linkedin.common.util.None)1 DegraderTrackerClient (com.linkedin.d2.balancer.clients.DegraderTrackerClient)1 DelegatingRingFactory (com.linkedin.d2.balancer.strategies.DelegatingRingFactory)1 PartitionStateUpdateListener (com.linkedin.d2.balancer.strategies.PartitionStateUpdateListener)1 PartitionState (com.linkedin.d2.balancer.strategies.relative.PartitionState)1 RelativeLoadBalancerStrategy (com.linkedin.d2.balancer.strategies.relative.RelativeLoadBalancerStrategy)1 TrackerClientState (com.linkedin.d2.balancer.strategies.relative.TrackerClientState)1 Ring (com.linkedin.d2.balancer.util.hashing.Ring)1