Search in sources :

Example 61 with Ring

use of com.linkedin.d2.balancer.util.hashing.Ring in project rest.li by linkedin.

the class SimpleLoadBalancer method getRings.

public Map<Integer, Ring<URI>> getRings(URI serviceUri) throws ServiceUnavailableException {
    ServiceProperties service = listenToServiceAndCluster(serviceUri);
    String serviceName = service.getServiceName();
    String clusterName = service.getClusterName();
    ClusterProperties cluster = getClusterProperties(serviceName, clusterName);
    LoadBalancerStateItem<UriProperties> uriItem = getUriItem(serviceName, clusterName, cluster);
    UriProperties uris = uriItem.getProperty();
    List<LoadBalancerState.SchemeStrategyPair> orderedStrategies = _state.getStrategiesForService(serviceName, service.getPrioritizedSchemes());
    if (!orderedStrategies.isEmpty()) {
        final PartitionAccessor accessor = getPartitionAccessor(serviceName, clusterName);
        int maxPartitionId = accessor.getMaxPartitionId();
        Map<Integer, Ring<URI>> ringMap = new HashMap<>((maxPartitionId + 1) * 2);
        for (int partitionId = 0; partitionId <= maxPartitionId; partitionId++) {
            for (LoadBalancerState.SchemeStrategyPair pair : orderedStrategies) {
                TrackerClientSubsetItem subsetItem = getPotentialClients(serviceName, service, cluster, uris, pair.getScheme(), partitionId, uriItem.getVersion());
                Ring<URI> ring = pair.getStrategy().getRing(uriItem.getVersion(), partitionId, subsetItem.getWeightedSubset(), subsetItem.shouldForceUpdate());
                // ring will never be null; it can be empty
                ringMap.put(partitionId, ring);
                if (!ring.isEmpty()) {
                    // don't fallback to the next strategy if there are already hosts in the current one
                    break;
                }
            }
        }
        return ringMap;
    } else {
        throw new ServiceUnavailableException(serviceName, "PEGA_1003. Unable to find a load balancer strategy" + "Server Schemes: [" + String.join(", ", service.getPrioritizedSchemes()) + ']');
    }
}
Also used : HashMap(java.util.HashMap) ServiceUnavailableException(com.linkedin.d2.balancer.ServiceUnavailableException) URI(java.net.URI) LoadBalancerState(com.linkedin.d2.balancer.LoadBalancerState) ServiceProperties(com.linkedin.d2.balancer.properties.ServiceProperties) PartitionAccessor(com.linkedin.d2.balancer.util.partitions.PartitionAccessor) UriProperties(com.linkedin.d2.balancer.properties.UriProperties) Ring(com.linkedin.d2.balancer.util.hashing.Ring) ClusterProperties(com.linkedin.d2.balancer.properties.ClusterProperties)

Example 62 with Ring

use of com.linkedin.d2.balancer.util.hashing.Ring in project rest.li by linkedin.

the class DeterministicSubsettingStrategy method getWeightedSubset.

@Override
public Map<T, Double> getWeightedSubset(Map<T, Double> weightMap, DeterministicSubsettingMetadata metadata) {
    if (metadata != null) {
        List<T> points = new ArrayList<>(weightMap.keySet());
        Collections.sort(points);
        Collections.shuffle(points, new Random(_randomSeed));
        List<Double> weights = points.stream().map(weightMap::get).collect(Collectors.toList());
        double totalWeight = weights.stream().mapToDouble(Double::doubleValue).sum();
        if (totalWeight == 0) {
            return null;
        }
        Ring ring = new Ring(weights, totalWeight);
        double offset = metadata.getInstanceId() / (double) metadata.getTotalInstanceCount();
        double subsetSliceWidth = getSubsetSliceWidth(metadata.getTotalInstanceCount(), points.size());
        List<Integer> indices = ring.getIndices(offset, subsetSliceWidth);
        return indices.stream().collect(Collectors.toMap(points::get, i -> round(ring.getWeight(i, offset, subsetSliceWidth), WEIGHT_DECIMAL_PLACE)));
    } else {
        _log.warn("Cannot retrieve metadata required for D2 subsetting. Revert to use all available hosts.");
        return null;
    }
}
Also used : BigDecimal(java.math.BigDecimal) List(java.util.List) Logger(org.slf4j.Logger) MD5Hash(com.linkedin.d2.balancer.util.hashing.MD5Hash) LoadBalancerState(com.linkedin.d2.balancer.LoadBalancerState) Map(java.util.Map) LoggerFactory(org.slf4j.LoggerFactory) Random(java.util.Random) Collections(java.util.Collections) Collectors(java.util.stream.Collectors) RoundingMode(java.math.RoundingMode) ArrayList(java.util.ArrayList) Random(java.util.Random) ArrayList(java.util.ArrayList)

Aggregations

URI (java.net.URI)45 HashMap (java.util.HashMap)28 TrackerClient (com.linkedin.d2.balancer.clients.TrackerClient)26 ArrayList (java.util.ArrayList)25 Test (org.testng.annotations.Test)23 Map (java.util.Map)18 URIRequest (com.linkedin.d2.balancer.util.URIRequest)15 HashSet (java.util.HashSet)15 DegraderTrackerClient (com.linkedin.d2.balancer.clients.DegraderTrackerClient)13 List (java.util.List)12 RequestContext (com.linkedin.r2.message.RequestContext)11 ServiceUnavailableException (com.linkedin.d2.balancer.ServiceUnavailableException)10 PartitionAccessor (com.linkedin.d2.balancer.util.partitions.PartitionAccessor)10 LoadBalancerState (com.linkedin.d2.balancer.LoadBalancerState)9 Request (com.linkedin.r2.message.Request)9 DegraderControl (com.linkedin.util.degrader.DegraderControl)9 Set (java.util.Set)9 AtomicLong (java.util.concurrent.atomic.AtomicLong)9 DegraderTrackerClientTest (com.linkedin.d2.balancer.clients.DegraderTrackerClientTest)8 Ring (com.linkedin.d2.balancer.util.hashing.Ring)8