上篇博文<一路踩坑构建Dubbo源码>谈论了如何本地构建dubbo源码,最近溪源也在努力的学习dubbo相关知识和机制,学习过程也可以称之苦不堪言吧。dubbo官网是入门学习资源重要之一;故溪源先分享中文官网:dubbo中文手册。
上网文章中也清晰地带着大家成功运行dubbo-demo
;对于像溪源这样的新手接触dubbo,学习源码估计都很难找到入手的方法,溪源也是走了不少冤枉路,所以特此写了一篇入手dubbo源码的文章,希望能够帮助伙伴们降低时间浪费,少走弯路。溪源这篇带着大家在dubbo-demo中创建自己的跟踪源码的单测用例。对于官网给与的demo用例,大家可以大胆的修改,溪源就是把demo改的面目全非。
借助官网的快速启动手册,以及源码包路径;
分别在dubbo-demo-interface
module中建立实体类和接口:
public class User implements Serializable {
private String userId;
private String userName;
private String userLevel;
private String userAddress;
//省略get/set方法
}
注意:实体类对象要实现Serializable接口,涉及后面远程调用传输;
public interface UserService {
List<User> getUserAddressList();
}
public interface OrderService {
void getUserAddressList();
}
在dubbo-demo-xml
模块中分别处理服务提供者逻辑、服务消费者逻辑;
首先贴出代码目录结构:
这个模块下东西比较多,目前只要是溪源学习SPI,Adaptive相关知识用到,大家可以暂时忽略,可以参考溪源分享的代码和目录结构创建,或者根据大家的实际情况建立,溪源仅仅提供一种入门的方式。
具体配置如下:
注册中心zookeeper地址换成自己本地IP或者阿里云服务器公网IP。
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:dubbo="http://dubbo.apache.org/schema/dubbo"
xmlns="http://www.springframework.org/schema/beans"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-4.3.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.0.xsd
http://dubbo.apache.org/schema/dubbo http://dubbo.apache.org/schema/dubbo/dubbo.xsd">
<dubbo:application metadata-type="remote" name="user-provider"/>
<!-- <dubbo:metadata-report address="zookeeper://****:2181"/>-->
<!--定义包扫描路径-->
<context:component-scan base-package="org.apache.dubbo.demo.provider"/>
<dubbo:registry address="zookeeper://*****:2181" timeout="10000"/>
<dubbo:protocol name="dubbo"/>
<!--暴露服务接口,ref:指接口真正的实现类bean,实现类后面会分享-->
<dubbo:service interface="org.apache.dubbo.demo.UserService" ref="memberServiceImpl"/>
</beans>
注意:此处与官网提供的xml配置存在区别,溪源这里引入包路径扫描
机制,否则接口实现类无法使用注解@Service
等注入spring容器中,或者大家可以按照官网使用
标签注入实现类对象,如下:
<bean id="memberServiceImpl" class="org.apache.dubbo.demo.provider.impl.MemberServiceImpl"/>
@Service
public class MemberServiceImpl implements UserService, Serializable {
@Override
public List<User> getUserAddressList() {
List<User> userList = new LinkedList<>();
for (int i = 0; i < 2; i++) {
User user = new User();
user.setUserLevel("member");
user.setUserAddress("杭州拱墅 " + i);
userList.add(user);
}
return userList;
}
}
溪源目的是通过实例学习dubbo相关机制和实现,所以此处直接代码创建user对象,实际应用业务场景再仔细考虑;
为了能够区分业务功能启动类,溪源直接将官网提供的类名改成ProviderApplication。
public class ProviderApplication {
public static void main(String[] args) throws Exception {
ClassPathXmlApplicationContext context = new ClassPathXmlApplicationContext("spring/dubbo-provider.xml");
context.start();
System.in.read();
}
}
服务提供者相关业务结束,下面开始实现服务消费者。
代码目录如下:
consumer模块的目录结构就比较简单明了。
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:dubbo="http://dubbo.apache.org/schema/dubbo"
xmlns="http://www.springframework.org/schema/beans"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-4.3.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.0.xsd
http://dubbo.apache.org/schema/dubbo http://dubbo.apache.org/schema/dubbo/dubbo.xsd">
<context:component-scan base-package="org.apache.dubbo.demo.consumer"/>
<dubbo:application name="order-consumer"/>
<dubbo:registry address="zookeeper://****:2181" timeout="80000"/>
<!--引用暴露的接口-->
<dubbo:reference id="userService" check="false" interface="org.apache.dubbo.demo.UserService"/>
</beans>
@Service
public class OrderServiceImpl implements OrderService {
@Autowired
private UserService userService;
@Override
public void getUserAddressList() {
List<User> userAddressList = userService.getUserAddressList();
for (User user : userAddressList) {
System.out.println(user.getUserAddress());
}
}
}
获取用户地址,并打印出来。
同理,溪源将原启动类重命名为ConsumerApplication。
public class ConsumerApplication {
public static void main(String[] args) throws Exception {
ClassPathXmlApplicationContext context = new ClassPathXmlApplicationContext("spring/dubbo-consumer.xml");
OrderService orderService = context.getBean(OrderService.class);
orderService.getUserAddressList();
System.in.read();
}
}
运行程序之前,溪源再着重强调几点,也是溪源学习过程中遇到的异常或者错误问题,避免大家踩坑,再说一下:
1.实体类,服务接口实现类实现Serializable接口;
2.确保自己zookeeper注册中心正常启动;
3.检查自己是否开启包扫描机制或者是否使用xml配置文件注入bean方式;
4.溪源并没有设置启动检查选项,所以默认值为true,如果服务提供类未启动,则服务消费者先启动,会报错;
大家运行之前,再仔细核查一遍,然后先启动ProviderApplication,再启动ConsumerApplication。
运行结果如图:
溪源写的demo源码传送门。
虽然公司项目业务暂时用不dubbo,但是不代表我们就停滞不前,程序员最重要的是技能。大家如果存在好的学习资源可以私信或者评论区留言能够分享给溪源一下哈~~。溪源也是第一次接触dubbo的相关机制,如果中间存在错误之处,希望大家能够及时指正,便于改正。最后,希望能够得到大家的肯定和支持。