从零开始学Dubbo-基础篇-过滤器和负载均衡

1,007 阅读3分钟

过滤器

与很多框架一样,Dubbo也存在拦截(过滤)机制,可以通过该机制在执行目标程序前后执行我们指定的代码。 Dubbo的Filter机制,是专门为服务提供方和服务消费方调用过程进行拦截设计的,每次远程方法执行,该拦截都会被执行。这样就为开发者提供了非常方便的扩展性,比如为dubbo接口实现ip白名单功能、监控功能、日志记录等。

1.创建过滤模块

实现org.apache.dubbo.rpc.Filter接口 实现一个简易过滤器来监控调用时间。 这边用的是2.7.1版本,所用是Constants.CONSUMER这样的常量,注意一下2.7.5的时候就已经改成CommonConstants.CONSUMER)了。

//设置需要过滤的服务
@Activate(group = {Constants.CONSUMER,Constants.PROVIDER})
public class DubboInvokeFilter implements Filter {
    @Override
    public Result invoke(Invoker<?> invoker, Invocation invocation) throws RpcException {
        long startTime=System.currentTimeMillis();
        try{
            return invoker.invoke(invocation);
        }
        finally {
            long endTime=System.currentTimeMillis();
            System.out.println("执行时间:"+(endTime-startTime));
        }
    }
}

2.创建配置文件

在resources目录下创建META-INF/dubbo目录,这里注意生成的时候不要用META-INF.dubbo,虽然在java中有效,但是在resources可能会失效,导致dubbo无法识别目录。

image.png

timer=com.study.filter.DubboInvokeFilter

3.引入依赖

从零开始学Dubbo-基础篇-远程调用使用 juejin.cn/post/694942…

在远程调用时写的消费者以及生产者引入过滤模块

4.测试

然后启动生产消费者查看结果。 消费者:

image.png

生产者:

image.png

如果自定义过滤器,可以不进行全局配置也就是@Activate不配置,在项目中通过k-v进行配置就可以实现过滤器的特定调用

负载均衡

使用负载均衡有两种形式。1.在服务消费方设置。2.在服务提供方设置

使用

//在服务消费者一方配置负载均衡策略 
@Reference(loadbalance = "roundrobin")
private HelloDubbo helloDubbo;
//在服务提供者一方配置负载均衡 
@Service(loadbalance = "random") 
public class public class HellowDubboImpl implements HelloDubbo {
    @Override
    public String sayHello(String name) {
        return "provider3 ack:"+name;
    }
}

这边我只有一个消费者所以在消费房配置比较方便。一共模拟了三个生产者分别是provider provider1 provider3.

1.配置random(随机)请求六次 结果如下:

image.png

可以看到访问是随机的

2.配置roundrobin(轮询)请求六次 结果如下:

image.png

可以看到访问是轮询的

3.配置leastactive(最小活跃数)

4.配置consistenthash(一致性hash)请求六次 结果如下:

image.png

一致性hash是使用hash环实现的,dubbo默认支持120个虚拟节点(可配置)。

自定义负载均衡(loadBalance)

自定义负载均衡器和自定义过滤器实现差不多

1.创建模块实现LoadBalance接口

我这自定义负载均衡器的策略是选择ip端口最小的,逻辑如下

public class MyloadBalance implements LoadBalance {
    @Override
    public <T> Invoker<T> select(List<Invoker<T>> list, URL url, Invocation invocation) throws RpcException {
        //list 就是服务器列表
        //此处按照ip以及端口号排序然后返回第一个值
        final Invoker<T> tInvoker = list.stream().sorted((i1, i2) -> {
            //先比较ip
            final int i = i1.getUrl().getIp().compareTo(i2.getUrl().getIp());
            if (i == 0) {
                //再比较端口
                return Integer.compare(i1.getUrl().getPort(), i2.getUrl().getPort());
            }
            return i;
        }).findFirst().get();
        return tInvoker;
    }
}

2.创建配置文件

在resources目录下创建META-INF/dubbo目录,然后以org.apache.dubbo.rpc.cluster.LoadBalance为名创建文件。 在文件中配置好刚刚自定义的负载均衡器 first=com.study.spi.loadbalance.MyloadBalance

3.使用

可以配置在提供者也可以配置在消费者。我这边配置在消费者。消费者引入依赖,通过key配置负载均衡策略

image.png 然后运行查看结果:

image.png

三次请求结果都在ip最小端口最小的服务器上。