有时候,我们发现线上的版本有缺陷、或者需要升级服务,这时候需要利用DUBBO多版本的特性对服务进行升级。下面引用DUBBO官方的 最佳实践-版本部分 的说明,可以详细了解到,当我们面临服务升级时,应该怎么做。
- 每个接口都应定义版本号,为后续不兼容升级提供可能,如:<dubbo:service interface="com.xxx.XxxService" version="1.0" />
- 建议使用两位版本号,因为第三位版本号通常表示兼容升级,只有不兼容时才需要变更服务版本。
- 当不兼容时,先升级一半提供者为新版本,再将消费者全部升为新版本,然后将剩下的一半提供者升为新版本。
OK,下面开始撸码。实例中定义了两个服务提供者,他俩实现了同样的接口,分别是1.0.0和1.0.1,因为只在内部优化了算法,并没有修改接口,所以可以继续兼容。服务消费者则随机访问提供者的版本。
- 服务提供者-1
服务接口:
public interface DemoService {
public String saySomething();
}
服务实现:
public class DemoServiceImpl implements DemoService {
@Override
public String saySomething() {
return "我是服务提供者1";
}
}
dubbo配置:
<!-- 配置Bean -->
<bean id="demoService"
class="com.github.thinwonton.dubbo.sample.multiversion.service.DemoServiceImpl" />
<!-- 指定web服务名字 -->
<dubbo:application name="multi-version-provider" />
<!-- 声明服务注册中心 -->
<!-- 使用zookeeper作为注册中心 -->
<dubbo:registry protocol="zookeeper" address="192.168.88.15:2181" />
<!-- 指定传输层通信协议 -->
<dubbo:protocol name="dubbo" port="20880" />
<!-- 暴露服务地址,该服务的实现类是demoService的引用 -->
<dubbo:service ref="demoService"
interface="com.github.thinwonton.dubbo.sample.multiversion.service.DemoService"
protocol="dubbo" version="1.0.0"/>
- 服务提供者-2
与服务提供者-1相比,只是服务的实现和服务版本的不同。
服务实现:
public class DemoServiceImpl implements DemoService {
@Override
public String saySomething() {
return "我是服务提供者2";
}
}
DUBBO配置:
<!-- 配置Bean -->
<bean id="demoService"
class="com.github.thinwonton.dubbo.sample.multiversion.service.DemoServiceImpl" />
<!-- 指定web服务名字 -->
<dubbo:application name="multi-version-provider" />
<!-- 声明服务注册中心 -->
<!-- 使用zookeeper作为注册中心 -->
<dubbo:registry protocol="zookeeper" address="192.168.88.15:2181" />
<!-- 指定传输层通信协议 -->
<dubbo:protocol name="dubbo" port="20881" />
<!-- 暴露服务地址,该服务的实现类是demoService的引用 -->
<dubbo:service ref="demoService"
interface="com.github.thinwonton.dubbo.sample.multiversion.service.DemoService"
protocol="dubbo" version="1.0.1"/>
当我们启动这两个服务后,通过DUBBO的管理控制平台,可以查询到服务的发布信息:
- 服务消费者 主程序:
public class ConsumerMain {
public static void main(String[] args) throws IOException {
ApplicationContext applicationContext = new ClassPathXmlApplicationContext("classpath:applicationContext.xml");
DemoService demoService = (DemoService) applicationContext.getBean("demoService");
for (int i = 0; i < 10; i++) {
System.out.println("消费者1:" + demoService.saySomething());
}
}
}
DUBBO配置:
<!-- 指定web应用名字 -->
<dubbo:application name="multi-version-consumer" />
<!-- 声明服务注册中心 -->
<dubbo:registry protocol="zookeeper" address="192.168.88.15:2181" />
<!-- 引用服务,demoService仅用于根据接口生成动态代理,默认使用javassist生成代理对象 -->
<dubbo:reference id="demoService"
interface="com.github.thinwonton.dubbo.sample.multiversion.service.DemoService"
protocol="dubbo" version="*"/>
这里消费者配置为可以访问任意版本。当我们运行主程序后,可以看到消费者随机访问服务提供者。如果我们指定了版本号为具体版本,则只会访问某个版本的提供者。