SpingCloud(H版&alibaba)框架开发教程-23 Ribbion负载轮询算法原理及手写轮询算法

2020最新版SpringCloud(H版&alibaba)框架开发教程-周阳

负载均衡算法原理:rest接口第几次请求数%服务器集群总数量=实际调用服务器位置下标,每次服务重启后rest接口计数从1开始

手写轮询算法

cloud-consumer-order80模块

注释掉com.antherd.springcloud.config.ApplicationContextConfig中代码

//  @LoadBalanced // 使RestTemplate具有负载均衡能力

注释掉com.antherd.springcloud.OrderMain80中注释

// @RibbonClient(name = "CLOUD-PAYMENT-SERVICE", configuration = MyRule.class)

新建类:com.antherd.springcloud.lb.LoadBalancer

package com.antherd.springcloud.lb;

import java.util.List;
import org.springframework.cloud.client.ServiceInstance;

public interface LoadBalancer {
     

  ServiceInstance instances(List<ServiceInstance> serviceInstances);

}

新建类:com.antherd.springcloud.lb.LoadBalancer.MyLB

package com.antherd.springcloud.lb;

import java.util.List;
import java.util.concurrent.atomic.AtomicInteger;
import org.springframework.cloud.client.ServiceInstance;
import org.springframework.stereotype.Component;

@Component
public class MyLB implements LoadBalancer {
     

  private AtomicInteger atomicInteger = new AtomicInteger(0);

  public final int getAndIncrement() {
     
    int current;
    int next;
    do {
     
      current = this.atomicInteger.get();
      next = current >= 2147483647 ? 0 : current + 1;
    } while (!this.atomicInteger.compareAndSet(current, next));
    System.out.println("*****第几次访问, 次数next*****: " + next);
    return next;
  }

  @Override
  public ServiceInstance instances(List<ServiceInstance> serviceInstances) {
     
    int index = getAndIncrement() % serviceInstances.size();
    return serviceInstances.get(index);
  }
}

修改com.antherd.springcloud.contorller.OrderController

package com.antherd.springcloud.contorller;

import com.antherd.springcloud.entities.CommonResult;
import com.antherd.springcloud.entities.Payment;
import com.antherd.springcloud.lb.MyLB;
import java.net.URI;
import java.util.List;
import javax.annotation.Resource;
import lombok.extern.slf4j.Slf4j;
import org.springframework.cloud.client.ServiceInstance;
import org.springframework.cloud.client.discovery.DiscoveryClient;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.client.RestTemplate;

@RestController
@Slf4j
public class OrderController {
     

  //private  static final String PAYMENT_URL = "http://localhost:8001";
  private  static final String PAYMENT_URL = "http://CLOUD-PAYMENT-SERVICE";

  @Resource
  private RestTemplate restTemplate;

  @Resource
  private MyLB loadBalancer;

  @Resource
  private DiscoveryClient discoveryClient;

  @PostMapping("/consumer/payment")
  public CommonResult<Payment> create(Payment payment) {
     
    return restTemplate.postForObject(PAYMENT_URL + "/payment", payment, CommonResult.class);
  }

  @GetMapping("/consumer/payment/{id}")
  public CommonResult<Payment> getPayment(@PathVariable Long id) {
     
    return restTemplate.getForObject(PAYMENT_URL + "/payment/" + id, CommonResult.class);
  }

  @GetMapping("/consumer/payment2/{id}")
  public CommonResult<Payment> getPayment2(@PathVariable Long id) {
     
    ResponseEntity<CommonResult> entity = restTemplate.getForEntity(PAYMENT_URL + "/payment/" + id, CommonResult.class);
    if (entity.getStatusCode().is2xxSuccessful()) {
     
      return entity.getBody();
    } else {
     
      return new CommonResult<>(444, "操作失败");
    }
  }

  @GetMapping(value = "/consumer/payment/lb")
  public String getPaymentLB() {
     

    List<ServiceInstance> instances = discoveryClient.getInstances("CLOUD-PAYMENT-SERVICE");
    if (instances == null || instances.size() == 0) {
     
      return null;
    }
    ServiceInstance serviceInstance = loadBalancer.instances(instances);
    URI uri = serviceInstance.getUri();
    return restTemplate.getForObject(uri + "/payment/lb", String.class);
  }
}

新建接口:com.antherd.springcloud.lb.LoadBalancer

cloud-provider-payment8001、cloud-provider-payment8002模块

在com.antherd.springcloud.controller.PaymentController中添加新接口:

@GetMapping(value = "/payment/lb")
public String getPaymentLB() {
     
  return serverPort;
}

测试

启动:cloud-eureka-server7001,cloud-eureka-server7002,cloud-provider-payment8001,cloud-provider-payment8002,cloud-consumer-order80五个模块

访问:http://localhost/consumer/payment/lb

你可能感兴趣的:(spring,boot,spring,cloud,spring,cloud,alibaba,ribbon,轮询算法)