假如某个电商系统,订单服务需要调用用户服务获取某个用户的所有地址,
所以现在需要创建两个服务模块:
- 订单服务web模块 用来创建订单
- 用户服务service模块 查询用户地址
这里的订单服务 web 模块一般指的是对外 HTTP 服务,用户服务 service 模块一般指的是对外提供 RPC 服务,订单服务也可称为服务消费者,用户服务也可以称为服务提供者
预期结果:
订单服务 web 模块在 A 服务器,用户服务模块在 B 服务器,A 可以远程调用 B 功能
一 创建服务提供者
- 使用 idea 创建一个新的 Maven Project

- 设置 GroupId 和 ArtifactId,GroupId 一般为反转域名来定义,ArtifactId 则是项目的具体名称

-
直接 finish
4.在 gmall 下常见 module,创建 maven 项目 next

5.GroupId 是创建 project 时加过的,ArtifactId 是当前项目 module 的名称,点击next

- Module name 尽量和第二步 ArtifactId 加的一样,没问题后 Finsh,Module 就创建成功了,在提供者的目录下创建具体接口实现

目录结构

- user-service-provider用户模块:用户服务接口的实现
- UserServiceImpl:服务方提供实现接口(UserService)
- provider.xml:用 Spring 配置声明暴露服务
- MainApplication:加载 Spring 配置
代码
// UserServiceImpl:服务方提供实现接口(UserService)
public class UserServiceImpl implements UserService {
@Override
public List<UserAddress> getUserAddressList(String userId){
UserAddress address1 = new UserAddress(1,"北京","1","beijing","1234567891","Y");
UserAddress address2 = new UserAddress(1,"上海","2","shanghai","1234567892","N");
return Arrays.asList(address2,address1);
}
}
// MainApplication:加载 Spring 配置
public class MainApplication {
public static void main(String[] args) throws IOException {
ClassPathXmlApplicationContext ioc = new ClassPathXmlApplicationContext("provider.xml");
ioc.start();
System.in.read();
}
}
// pom.xml
// 引入dubbo依赖
// 因为注册中心使用的是zookeeper,所以引入zookeeper依赖
// 引入gmall-interface依赖(使用bean和接口)
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<parent>
<artifactId>gmall-test-test</artifactId>
<groupId>com.sangyu</groupId>
<version>1.0-SNAPSHOT</version>
</parent>
<modelVersion>4.0.0</modelVersion>
<groupId>com.sangyu</groupId>
<artifactId>user-service-provider</artifactId>
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<configuration>
<source>1.6</source>
<target>1.6</target>
</configuration>
</plugin>
</plugins>
</build>
<dependencies>
<dependency>
<groupId>com.sangyu</groupId>
<artifactId>gmall-interface</artifactId>
<version>1.0-SNAPSHOT</version>
</dependency>
<!-- 引入dubbo -->
<!-- https://mvnrepository.com/artifact/com.alibaba/dubbo -->
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>dubbo</artifactId>
<version>2.6.2</version>
</dependency>
<!-- 注册中心使用的是zookeeper,引入操作zookeeper的客户端-->
<dependency>
<groupId>org.apache.curator</groupId>
<artifactId>curator-framework</artifactId>
<version>2.12.0</version>
</dependency>
</dependencies>
</project>
// provider.xml
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:dubbo="http://dubbo.apache.org/schema/dubbo"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-4.3.xsd http://dubbo.apache.org/schema/dubbo http://dubbo.apache.org/schema/dubbo/dubbo.xsd">
<!-- 提供方应用信息,用于计算依赖关系 -->
<dubbo:application name="user-service-provider" />
<!-- 使用multicast广播注册中心暴露服务地址 -->
<dubbo:registry address="zookeeper://127.0.0.1:2181" />
<!-- 用dubbo协议在20880端口暴露服务 -->
<dubbo:protocol name="dubbo" port="20880" />
<!-- 声明需要暴露的服务接口 -->
<dubbo:service interface="com.sangyu.gmall.service.UserService" ref="UserServiceImpl" />
<!-- 和本地bean一样实现服务 -->
<bean id="UserServiceImpl" class="com.sangyu.gmall.service.impl.UserServiceImpl" />
</beans>
二 创建服务消费者
创建 module 过程和服务提供者相同,在 gmall 项目下创建 module,并 ArtifactId 设置为 order-service-consumer
目录结构

- order-service-consumer订单模块:调用用户模块
- OrderServiceImpl:服务方提供实现接口(UserService)
- consumer.xml:用 Spring 配置声明暴露服务
- MainApplication:加载 Spring 配置
代码
// OrderServiceImpl:服务方提供实现接口(UserService)
@Service // 使用spring的注解将OrderServiceImpl注入到容器中
public class OrderServiceImpl implements OrderService {
@Autowired //使用Autowired将UserService注入进来,UserService已经在consumer.xml配置后已经在容器中了
UserService userService;
@Override
public void initOrder(String userId) {
System.out.println("用户id:" + userId);
List<UserAddress> addressList = userService.getUserAddressList(userId);
for (UserAddress userAddress : addressList) {
System.out.println(userAddress.getUserAddress());
}
}
}
// MainApplication:加载 Spring 配置
public class MainApplication {
@SuppressWarnings("resource")
public static void main(String[] args) throws IOException {
ClassPathXmlApplicationContext applicationContext =new ClassPathXmlApplicationContext("consumer.xml");
OrderService orderService = applicationContext.getBean(OrderService.class);
orderService.initOrder("1");
System.out.println("调用完成");
System.in.read();
}
}
// consumer.xml:用 Spring 配置声明暴露服务
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:dubbo="http://dubbo.apache.org/schema/dubbo"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.3.xsd
http://dubbo.apache.org/schema/dubbo http://dubbo.apache.org/schema/dubbo/dubbo.xsd
http://code.alibabatech.com/schema/dubbo http://code.alibabatech.com/schema/dubbo/dubbo.xsd">
<context:component-scan base-package="com.sangyu.gmall.service.impl"></context:component-scan>
<!-- 消费方应用名,用于计算依赖关系,不是匹配条件,不要与提供方一样 -->
<dubbo:application name="order-service-consumer" />
<!-- 使用zookeeper广播注册中心暴露发现服务地址 -->
<dubbo:registry address="zookeeper://127.0.0.1:2181" />
<!--声明需要调用的远程服务的接口;生成远程服务代理 -->
<dubbo:reference id="UserService" interface="com.sangyu.gmall.service.UserService" />
</beans>
// pom.xml
// 引入dubbo依赖
// 因为注册中心使用的是zookeeper,所以引入zookeeper依赖
// 引入gmall-interface依赖(使用bean和接口)
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<parent>
<artifactId>gmall-test-test</artifactId>
<groupId>com.sangyu</groupId>
<version>1.0-SNAPSHOT</version>
</parent>
<modelVersion>4.0.0</modelVersion>
<groupId>com.sangyu</groupId>
<artifactId>order-service-consumer</artifactId>
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<configuration>
<source>1.6</source>
<target>1.6</target>
</configuration>
</plugin>
</plugins>
</build>
<dependencies>
<dependency>
<groupId>com.sangyu</groupId>
<artifactId>gmall-interface</artifactId>
<version>1.0-SNAPSHOT</version>
</dependency>
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>dubbo</artifactId>
<version>2.6.2</version>
</dependency>
<dependency>
<groupId>org.apache.curator</groupId>
<artifactId>curator-framework</artifactId>
<version>2.12.0</version>
</dependency>
</dependencies>
</project>
三 创建公共接口层
创建 module 过程和服务提供者不同,在 gmall 项目下创建 module ,并ArtifactId 设置为 gmall-interface,提供 javabean 和服务接口
作用:定义公共接口,也可以导入公共依赖
目录结构

代码
// UserAddress类(javabean)
public class UserAddress {
private Integer id;
private String userAddress; // 用户地址
private String userId; // 用户id
private String consignee; // 收货人
private String phoneNum; // 电话号码
private String isDefault; // 是否为默认地址 Y-是 N-否
public UserAddress() {
super();
}
public UserAddress(Integer id, String userAddress, String userId, String consignee,
String phoneNum, String isDefault) {
this.id = id;
this.userAddress = userAddress;
this.userId = userId;
this.consignee = consignee;
this.phoneNum = phoneNum;
this.isDefault = isDefault;
}
public Integer getId() {
return id;
}
public void setId(Integer id) {
this.id = id;
}
public String getUserAddress() {
return userAddress;
}
public void setUserAddress(String userAddress) {
this.userAddress = userAddress;
}
public String getUserId() {
return userId;
}
public void setUserId(String userId) {
this.userId = userId;
}
public String getConsignee() {
return consignee;
}
public void setConsignee(String consignee) {
this.consignee = consignee;
}
public String getPhoneNum() {
return phoneNum;
}
public void setPhoneNum(String phoneNum) {
this.phoneNum = phoneNum;
}
public String getIsDefault() {
return isDefault;
}
public void setIsDefault(String isDefault) {
this.isDefault = isDefault;
}
}
// 用户服务接口
public interface UserService {
/**
* 按照用户id返回所有的收获地址
* @param userId
* @return
*/
public List<UserAddress> getUserAddressList(String userId);
}
// OrderService接口初始化订单
public interface OrderService {
/**
* 初始化订单
* @param userId
*/
public void initOrder(String userId);
}
四 测试运行
先运行服务提供者 user-service-provider,再运行服务调用者 order-service-provider,两者运行前要的保证 zookeeper 是运行状态
// 运行结果
用户id:1
上海
北京
调用完成
