美文网首页
微架构 springcloud-13. Ribbon 负载均衡机

微架构 springcloud-13. Ribbon 负载均衡机

作者: 程序员_超 | 来源:发表于2018-03-27 21:45 被阅读0次

    Ribbon 负载均衡机制分析

    这一小结分析Ribbon的机制

    默认规则获取服务器

    1. 定义Ribbon负载均衡器对象 ILoadBalancer
    //负载均衡器对象
    ILoadBalancer loadBalancer = new BaseLoadBalancer();
    
    1. 定义服务器列表,是要将哪些服务器交与Ribbon以实现负载均衡
    //准备服务器列表
    List<Server> serverList = new ArrayList<Server>();
    serverList.add(new Server("localhost", 8080));
    serverList.add(new Server("localhost", 8081));
    
    1. 将服务器列表交与Ribbon
    //将服务器列表加载到负载均衡器
    loadBalancer.addServers(serverList);
    
    1. 从Ribbon负载均衡器中获取服务器对象
    for (int i = 0; i < 10; i++) {
        Server server = loadBalancer.chooseServer(null);
        System.out.println(server);
    }
    
    1. 完整代码如下:
    package person.jack.ribbon.client;
    
    import com.netflix.loadbalancer.BaseLoadBalancer;
    import com.netflix.loadbalancer.ILoadBalancer;
    import com.netflix.loadbalancer.LoadBalancerBuilder;
    import com.netflix.loadbalancer.Server;
    
    import java.util.ArrayList;
    import java.util.List;
    
    public class LBTest {
        @Test
        public void testBalancer() {
            //负载均衡器对象
            ILoadBalancer loadBalancer = new BaseLoadBalancer();
    
            //准备服务器列表
            List<Server> serverList = new ArrayList<Server>();
            serverList.add(new Server("localhost", 8080));
            serverList.add(new Server("localhost", 8081));
    
            //将服务器列表加载到负载均衡器
            loadBalancer.addServers(serverList);
            for (int i = 0; i < 10; i++) {
                Server server = loadBalancer.chooseServer(null);
                System.out.println(server);
            }
        }
    }
    
    
    1. 运行main 函数,控制台打印如下:
    SLF4J: Failed to load class "org.slf4j.impl.StaticLoggerBinder".
    SLF4J: Defaulting to no-operation (NOP) logger implementation
    SLF4J: See http://www.slf4j.org/codes.html#StaticLoggerBinder for further details.
    localhost:8081
    localhost:8080
    localhost:8081
    localhost:8080
    localhost:8081
    localhost:8080
    localhost:8081
    localhost:8080
    localhost:8081
    localhost:8080
    

    可知,负载均衡器选择服务器是以轮询的方式!

    自定义规则获取服务器

    1. 定义类实现 com.netflix.loadbalancer.IRule 接口,让8080调用的概率只有10%,完整代码如下:
    package person.jack.ribbon.rule;
    
    import com.netflix.loadbalancer.ILoadBalancer;
    import com.netflix.loadbalancer.IRule;
    import com.netflix.loadbalancer.Server;
    
    import java.util.List;
    import java.util.Random;
    
    public class MyRule implements IRule {
        private ILoadBalancer lb;
        //负载均衡器选择服务器
        @Override
        public Server choose(Object key) {
            int n = new Random().nextInt(10) + 1;
            if(n<2){
                return getServerByPort(8080);
            }
            return getServerByPort(8081);
        }
        //工具方法,根据端口获取服务器
        private Server getServerByPort(int port){
            List<Server> serverList = lb.getAllServers();
            for (Server server : serverList) {
                if(server.getPort()==port){
                    return server;
                }
            }
            return null;
        }
        //设置负载均衡器
        @Override
        public void setLoadBalancer(ILoadBalancer lb) {
            this.lb=lb;
        }
        //获取负载均衡器
        @Override
        public ILoadBalancer getLoadBalancer() {
            return this.lb;
        }
    }
    
    
    1. 测试方法

    Rule对象要运行需要 ILoadBalancer 对象以获取服务器:

    MyRule rule=new MyRule();
    rule.setLoadBalancer(lb);
    

    将rule对象交与ILoadBalancer:

    lb.setRule(rule);
    

    方法完整代码如下:

    @Test
    public void testRule() {
        //负载均衡器对象
        BaseLoadBalancer lb = new BaseLoadBalancer();
        MyRule rule=new MyRule();
        rule.setLoadBalancer(lb);
        lb.setRule(rule);
    
        //准备服务器列表
        List<Server> serverList = new ArrayList<Server>();
        serverList.add(new Server("localhost", 8080));
        serverList.add(new Server("localhost", 8081));
    
        //将服务器列表加载到负载均衡器
        lb.addServers(serverList);
        for (int i = 0; i < 10; i++) {
            Server server = lb.chooseServer("key");
            System.out.println(server);
        }
    }
    
    1. 运行测试方法,控制台运行如下:
    SLF4J: Failed to load class "org.slf4j.impl.StaticLoggerBinder".
    SLF4J: Defaulting to no-operation (NOP) logger implementation
    SLF4J: See http://www.slf4j.org/codes.html#StaticLoggerBinder for further details.
    localhost:8080
    localhost:8081
    localhost:8081
    localhost:8081
    localhost:8081
    localhost:8081
    localhost:8081
    localhost:8081
    localhost:8081
    localhost:8081
    
    # 8080 被调用的概率明显降低,测试成功
    

    以上就是对负载均衡器的使用与测试

    使用自定义规则

    1. 了解了负载均衡器的调用逻辑,接下来就是如何将自定义的规则应用到Ribbon客户端调用,需配置:NFLoadBalancerRuleClassName,指定规则的类名实现:
    ConfigurationManager.getConfigInstance().setProperty("myClient.ribbon.NFLoadBalancerRuleClassName",MyRule==.class.getName());
    

    完整代码如下:

    @Test
    public void testMyRuleBalancer() throws Exception {
        ConfigurationManager.getConfigInstance().setProperty(
                "myClient.ribbon.listOfServers", "localhost:8080,localhost:8081");
        ConfigurationManager.getConfigInstance().setProperty(
                "myClient.ribbon.NFLoadBalancerRuleClassName",
                MyRule.class.getName());
        RestClient client = (RestClient) ClientFactory.getNamedClient("myClient");
        HttpRequest request = HttpRequest.newBuilder().uri("/info").build();
        for (int i = 0; i < 10; i++) {
            HttpResponse response = client.executeWithLoadBalancer(request);
            String json = response.getEntity(String.class);
            System.out.println(json);
        }
    }
    
    1. 运行以上测试方法,控制台打印如下:
    SLF4J: Failed to load class "org.slf4j.impl.StaticLoggerBinder".
    SLF4J: Defaulting to no-operation (NOP) logger implementation
    SLF4J: See http://www.slf4j.org/codes.html#StaticLoggerBinder for further details.
    springBoot 是javaWEB开发最优美的姿势!http://localhost:8081/info
    springBoot 是javaWEB开发最优美的姿势!http://localhost:8081/info
    springBoot 是javaWEB开发最优美的姿势!http://localhost:8081/info
    springBoot 是javaWEB开发最优美的姿势!http://localhost:8080/info
    springBoot 是javaWEB开发最优美的姿势!http://localhost:8081/info
    springBoot 是javaWEB开发最优美的姿势!http://localhost:8081/info
    springBoot 是javaWEB开发最优美的姿势!http://localhost:8081/info
    springBoot 是javaWEB开发最优美的姿势!http://localhost:8081/info
    springBoot 是javaWEB开发最优美的姿势!http://localhost:8081/info
    springBoot 是javaWEB开发最优美的姿势!http://localhost:8081/info
    
    # 已经未采用轮询规则来调用服务器,使用的是我们自定义的规则
    

    Ribbon 内置的几种规则 Common rules:

    1. RoundRobinRule(默认)
    轮询
    
    1. AvailabilityFilteringRule
    过滤掉那些因为一直连接失败的被标记为circuit tripped的后端server,并过滤掉那些高并发的的后端server(active connections 超过配置的阈值)
    
    1. WeightedResponseTimeRule
    根据相应时间分配一个weight,相应时间越长,weight越小,被选中的可能性越低。
    
    1. ZoneAvoidanceRule
    复合判断server所在区域的性能和server的可用性选择server
    
    1. BestAvailableRule
    选择一个最小的并发请求的server
    
    1. RandomRule
    随机选择一个server
    
    1. RetryRule
    对选定的负载均衡策略机上重试机制。
    

    相关文章

      网友评论

          本文标题:微架构 springcloud-13. Ribbon 负载均衡机

          本文链接:https://www.haomeiwen.com/subject/qlhecftx.html