Dubbo官方網站: dubbo.apache.org/zh-cn/php
我將會用一個小demo來介紹如何與Spring Boot整合;html
若是看我文章的朋友沒有用過Spring Boot,Dubbo,那麼我推薦你仍是先去熟悉一下,由於本篇文章沒有介紹如何安裝。java
此次的demo是獲取用戶訂單信息的小demogit
目前這個demo正在個人github上: github.com/aaaTao66/du…github
我這裏叫作:gmall-interfaceweb
根據 Dubbo的官方文檔的 服務最佳化實踐 裏面說的:spring
建議將服務接口、服務模型、服務異常等均放在 API 包中,由於服務模型和異常也是 API 的一部分,這樣作也符合分包原則:重用發佈等價原則(REP),共同重用原則(CRP)。apache
這就是咱們創建 gmall-interface 的緣由,也就是咱們要把Java Bean 和 接口放在這個項目裏面,讓每個微服務的項目依賴於它。json
提供者項目名:boot-user-service-provider;(用戶,能夠什麼都不勾選)服務器
消費者項目名:boot-order-service-consumer;(訂單,記得初始化的時候要勾選web)
package com.carson.gmall.bean;
import java.io.Serializable;
public class UserAddress implements Serializable {
private Integer id;
private String userAddress; // 用戶地址
private String userId; // 用戶id
private String consignee; // 收貨人
private String phoneNum; // 電話號碼
private String isDefault; // 是否爲默認地址 yes / no
// 省略get set toString 等方法
複製代碼
記得要實現序列化
打個比方,若是咱們的 A 客戶端 想要調用 B客戶端的一個方法,這個時候 A 服務器要與B服務器創建起鏈接,並且A服務器調用方法的時候要還要傳入參數,而這個參數要在網絡間傳遞,咱們須要序列化。
而後B服務器發現有外界的服務器想要調用個人方法,同時還給我傳了參數,因爲是序列化傳過來的,因此B服務器要把參數反序列化。
而後方法調用完以後,還有一個返回值,這個時候基本與剛纔同樣,先是序列化,而後A再把它反序列化,這樣就能夠獲得返回結果了。
OrderService:
import com.carson.gmall.bean.UserAddress;
import java.util.List;
/** * 用戶服務接口 * */
public interface UserService {
/* 按照用戶id返回全部收穫地址 * */
List<UserAddress> getUserAddressList(String userId);
}
複製代碼
UserService:
import com.carson.gmall.bean.UserAddress;
import java.util.List;
/** * 用戶服務接口 * */
public interface UserService {
/* 按照用戶id返回全部收穫地址 * */
List<UserAddress> getUserAddressList(String userId);
}
複製代碼
<?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">
<modelVersion>4.0.0</modelVersion>
<groupId>com.carson.gmall</groupId>
<artifactId>gmall-interface</artifactId>
<version>1.0-SNAPSHOT</version>
<dependencies>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>1.18.8</version>
</dependency>
<dependency>
<groupId>org.apache.curator</groupId>
<artifactId>curator-framework</artifactId>
<version>2.8.0</version>
</dependency>
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>dubbo</artifactId>
<version>2.6.2</version>
</dependency>
</dependencies>
</project>
複製代碼
除了Spring Boot自帶的,還須要添加這兩個,dubbo的 0.2.0 版本是給Spring Boot 2.x用的。
若是Spring Boot是 1.x版本,那麼dubbo應該用 0.1.0.
與 gmall-interface 進行關聯。
<dependency>
<groupId>com.carson.gmall</groupId>
<artifactId>gmall-interface</artifactId>
<version>1.0-SNAPSHOT</version>
</dependency>
dubbo依賴
<dependency>
<groupId>com.alibaba.boot</groupId>
<artifactId>dubbo-spring-boot-starter</artifactId>
<version>0.2.0</version>
</dependency>
複製代碼
而後就是Spring Boot的配置文件:
dubbo:
application:
name: boot-order-service-consumer
registry:
address: zookeeper://127.0.0.1:2181
monitor:
protocol: registry
server:
port: 8081
複製代碼
沒有用過可能看不懂這一段配置,其實對應的就是dubbo官方文檔的那一段 provider.xml :
具體網址 :dubbo.apache.org/zh-cn/docs/…
可是個人配置裏面沒有 聲明須要暴露的服務接口 ,這個等一下會說爲何。
import com.alibaba.dubbo.config.annotation.Service;
import com.carson.gmall.bean.UserAddress;
import com.carson.gmall.bootuserserviceprovider.service.UserService;
import org.springframework.stereotype.Component;
import java.util.Arrays;
import java.util.List;
@Service // 暴露服務
@Component
public class UserServiceImpl implements UserService {
public List<UserAddress> getUserAddressList(String userId) {
UserAddress address1 = new UserAddress(1, "河北省衡水市", "1", "carson","12345678911","Y");
UserAddress address2 = new UserAddress(1, "山東省德州市", "2", "eason", "4562144", "Y");
return Arrays.asList(address1,address2);
}
}
複製代碼
注意個人註解 @Service,這個註解不是Spring的,而是dubbo的:
import com.alibaba.dubbo.config.annotation.Service;
這個註解的意思就是:聲明須要暴露的服務接口;
這個方法咱們能夠看到我設置了兩個收穫地址,而且把它以list方式返回。
import com.alibaba.dubbo.config.spring.context.annotation.EnableDubbo;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
@EnableDubbo // 開啓基於註解的dubbo功能
@SpringBootApplication
public class BootUserServiceProviderApplication {
public static void main(String[] args) {
SpringApplication.run(BootUserServiceProviderApplication.class, args);
}
}
複製代碼
pom 文件與剛纔的提供者同樣。
dubbo:
application:
name: boot-order-service-consumer
registry:
address: zookeeper://127.0.0.1:2181
monitor:
protocol: registry
server:
port: 8081
複製代碼
具體配的什麼,能夠參考duboo官方文檔的快速啓動,也就是剛纔上面的網址:
package com.carson.gmall.bootorderserviceconsumer.service.impl;
import com.alibaba.dubbo.config.annotation.Reference;
import com.carson.gmall.bean.UserAddress;
import com.carson.gmall.bootuserserviceprovider.service.OrderService;
import com.carson.gmall.bootuserserviceprovider.service.UserService;
import com.sun.org.apache.bcel.internal.generic.RETURN;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import java.util.List;
/** * 1. 將服務提供者註冊到註冊中心(暴漏服務) * 1) 導入 dubbo 依賴 * 2) 配置服務提供者 * * 2. 讓服務消費者去註冊中心訂閱服務提供者的服務地址 * */
@Service
public class OrderServiceImpl implements OrderService {
@Reference
UserService userService;
public List<UserAddress> initOrder(String userId) {
System.out.println("用戶id:"+userId);
// 1. 查詢用戶的收貨地址
List<UserAddress> userAddressList = userService.getUserAddressList(userId);
return userAddressList;
}
}
複製代碼
注意 @Reference: 遠程調用UserService, 本身會去註冊中心去發現
@Controller
public class OrderController {
@Autowired
private OrderService orderService;
@ResponseBody
@RequestMapping("/initOrder")
public List<UserAddress> initOrder(@RequestParam("uid") String userId) {
return orderService.initOrder(userId);
}
}
複製代碼
@ResponseBody: 把獲取到的結果以 json方式響應
@EnableDubbo // 開啓基於註解的dubbo功能
@SpringBootApplication
public class BootOrderServiceConsumerApplication {
public static void main(String[] args) {
SpringApplication.run(BootOrderServiceConsumerApplication.class, args);
}
}
複製代碼
和提供者同樣
啓動zookeeper和dubbo和這兩個項目,能夠在dubbo控制檯看到,已經有了消費者和提供者
而後,咱們剛纔啓動的Spring Boot,有一個是web項目,而且設置了端口 8081,讓咱們試着訪問這個 8081端口,而且帶上參數:
成功獲取到了訂單信息;