點擊上方“芋道源碼”,選擇“設爲星標”
管她前浪,還是後浪?
能浪的浪,纔是好浪!
每天 8:55 更新文章,每天掉億點點頭髮...
源碼精品專欄
摘要: 原創出處 http://www.iocoder.cn/Soul/install/ 「芋道源碼」歡迎轉載,保留摘要,謝謝!
1. 概述
2. 單機部署
3. 接入 Dubbo 應用
4. 接入 Spring Boot 應用
5. 接入 Spring Cloud 應用
6. rateLimiter 插件
7. hystrix 插件
666. 彩蛋
1. 概述
Soul 是基於 WebFlux 實現的響應式的 API 網關,具有異步、高性能、跨語言等特點。
作者:我希望能夠有一樣東西像靈魂一樣,保護您的微服務。在參考了 Kong、Spring Cloud Gateway 等優秀的網關後,站在巨人的肩膀上,Soul 由此誕生!
作者是艿艿的大表弟,胖友信麼?!
目前 Soul 功能列表如下:
支持各種語言,無縫集成到 Dubbo、Spring Cloud、Spring Boot 中。
Soul 是極其少支持 Dubbo 的 API 網關,通過 Dubbo 泛化調用 實現。
豐富的插件支持,鑑權,限流,熔斷,防火牆等等。
網關多種規則動態配置,支持各種策略配置。
插件熱插拔,易擴展。
支持集羣部署,支持 A/B Test。
整體架構如下圖所示:
是不是看着就賊酷炫,實際一臉懵逼。不要慌~我們先來搭建 Soul 網關。
2. 單機部署
本小節,我們來單機部署一個 Soul 服務,適合測試環境。如下圖所示:
2.1 MySQL 安裝
相信大家都會,艿艿就不瞎嗶嗶了。嘿嘿~注意,目前最好安裝 5.X 版本,艿艿一開始用 8.X 存在報錯的情況。
安裝完成後,創建 soul
數據庫。
2.2 Soul Admin 安裝
Soul Admin 控制檯,負責維護網關的元數據、配置等等,並提供給 Soul Bootstrap 網關服務讀取。
友情提示:後續推薦胖友閱讀如下兩篇文章,搞懂 Soul Admin 和 Soul Bootstrap 的同步的原理:
《Soul 文檔 —— 數據配置流程》
《Soul 文檔 —— 數據同步原理》
① 從 https://yu199195.github.io/jar/soul-admin.jar 下載啓動 jar 包。
# 創建目錄
$ mkdir -p /Users/yunai/Soul
$ cd /Users/yunai/Soul
# 下載
$ wget https://yu199195.github.io/jar/soul-admin.jar
② 通過 java -jar soul-admin.jar
命令啓動 Soul Admin 控制檯。完整命令如下:
$ java -jar soul-admin.jar --spring.datasource.url="jdbc:mysql://s1.iocoder.cn:3306/soul?useUnicode=true&characterEncoding=utf-8&zeroDateTimeBehavior=CONVERT_TO_NULL&failOverReadOnly=false&autoReconnect=true&useSSL=false" --spring.datasource.username='root' --spring.datasource.password='3WLiVUBEwTbvAfsh'
--spring.datasource.url
配置項,修改成胖友的數據庫地址。--spring.datasource.username
配置項,修改成胖友的數據庫賬號。--spring.datasource.password
配置項,修改成胖友的數據庫密碼。
Soul Admin 會自動創建數據庫,以及表結構,並初始化默認數據。如下圖所示:
soul
數據庫友情提示:具體的數據庫設計,後續可以看看《Soul 文檔 —— 數據庫設計》。
③ 啓動完成後,我們可以通過日誌看到 Soul Admin 啓動在 9095 端口。使用瀏覽器,訪問 http://127.0.0.1:9095/ 地址,進入登錄頁。
默認內置管理員賬號「admin/123456」。輸入賬號密碼,進入首頁。
胖友可以自己隨便點點,簡單瞭解下有哪些功能。
2.3 Soul Bootstrap 安裝
Soul Bootstrap 網關服務,負責啓動網關,並轉發請求到後端服務。
① 從 https://yu199195.github.io/jar/soul-bootstrap.jar 下載啓動 jar 包。
$ wget https://yu199195.github.io/jar/soul-bootstrap.jar
② 直接通過 java -jar soul-bootstrap.jar
命令啓動 Soul Bootstrap 網關服務。完整命令如下:
$ java -jar soul-bootstrap.jar --soul.sync.websocket.url="ws://localhost:9095/websocket"
--spring.datasource.url
配置項,修改成胖友的 Soul Admin 地址。
同時,我們在 Soul Admin 的日誌輸出如下日誌,說明 Soul Bootstrap 成功連接上。
2020-05-22 20:32:48.005 INFO 48891 --- [0.0-9095-exec-1] o.d.s.a.l.websocket.WebsocketCollector : websocket on open successful....
③ 啓動完成後,我們可以通過日誌看到 Soul Bootstrap 啓動在 9195 端口。使用瀏覽器,訪問 http://127.0.0.1:9195/ 地址,返回如下結果,說明啓動成功。
{
"code": -100,
"message": "您的參數錯誤,請檢查相關文檔!",
"data": null
}
2.4 下一步
至此,我們已經完成了 Soul 服務的單機部署,是不是挺簡單的。下面,胖友可以根據自己的需要,閱讀如下小節:
「3. 接入 Dubbo 應用」
「4. 接入 Spring Boot 應用」
「5. 接入 Spring Cloud 應用」
3. 接入 Dubbo 應用
示例代碼對應倉庫:
lab-60-soul-dubbo-demo-user-service
本小節,我們參考《Soul 文檔 —— Dubbo 用戶接入》文章,接入 Soul 服務網關。整個示例架構如下圖所示:
下面,我們來開始正式接入 Dubbo 應用。
3.1 設置 dubbo 插件
先需要設置 dubbo 插件 的註冊中心,因爲 Soul Bootstrap 服務網關需要從註冊中心獲取到 Dubbo 服務的實例列表。
① 使用瀏覽器,訪問 http://127.0.0.1:9095/#/system/plugin 地址,進入「系統管理 -> 插件管理」菜單,可以看到 dubbo 插件。如下圖所示:
② 點擊 dubbo 插件的「編輯」按鈕,設置註冊中心的配置。如下圖所示:
因爲我們將使用 Nacos 作爲 Dubbo 服務的註冊中心,所以這裏設置爲
{"register":"nacos://localhost:8848"}
。如果胖友使用 Zookeeper 作爲 Dubbo 服務的註冊中心,所以這裏設置爲
{"register":"zookeeper://localhost:2181"}
。
友情提示:註冊中心的地址,記得要填寫正確哈~
③ 因爲 Soul Bootstrap 和 Soul Admin 暫時不支持插件修改的自動加載,所以我們此時需要手動重啓下。
3.2 搭建 Dubbo 示例項目
先快速搭建一個 Dubbo 示例項目,暫未接入 Soul 網關。如下圖所示:
lab-60-soul-dubbo-demo-user-service-api
lab-60-soul-dubbo-demo-user-service
友情提示:如果胖友對 Dubbo + Nacos 不瞭解的胖友,可以閱讀《芋道 Spring Boot Dubbo 入門》文章。
下面,我們來將它改造接入 Soul 網關。
3.2.1 引入依賴
修改 pom.xml
文件,引入 soul-client-apache-dubbo
依賴,它是 Soul 對 Apache Dubbo 2.7.X 的集成支持。
<!-- 引入 Soul 針對 Dubbo 的集成的依賴 -->
<dependency>
<groupId>org.dromara</groupId>
<artifactId>soul-client-apache-dubbo</artifactId>
<version>2.1.2-RELEASE</version>
</dependency>
友情提示:如果胖友使用 Alibaba Dubbo 2.6.X 的話,引入
soul-client-alibaba-dubbo
依賴。
3.2.2 配置文件
修改 application.yaml
配置文件,添加 Soul 配置項如下:
soul:
# Soul 針對 Dubbo 的配置項,對應 DubboConfig 配置類
dubbo:
admin-url: http://127.0.0.1:9095 # Soul Admin 地址
context-path: /user-api # 設置在 Soul 網關的路由前綴,例如說 /order、/product 等等。
# 後續,網關會根據該 context-path 來進行路由
app-name: user-service # 應用名。未配置情況下,默認使用 Dubbo 的應用名
soul.dubbo
配置項,Soul 對 Dubbo 的配置項,對應 DubboConfig 配置類。具體每個配置項的作用,胖友自己看配置項後的註釋。
3.2.3 UserServiceImpl
需要在 Dubbo Service 實現類的方法上,添加 @SoulClient
註解,用於設置每個 Dubbo 方法對應的請求路徑。這裏,我們修改 UserServiceImpl 類,添加該註解。代碼如下:
@org.apache.dubbo.config.annotation.Service(version = "1.0.0")
public class UserServiceImpl implements UserService {
private Logger logger = LoggerFactory.getLogger(getClass());
@Override
@SoulClient(path = "/user/get", desc = "獲得用戶詳細")
public String getUser(Integer id) {
return "User:" + id;
}
@Override
@SoulClient(path = "/user/create", desc = "創建用戶")
public Integer createUser(UserCreateDTO createDTO) {
logger.info("[createUser][username({}) password({})]", createDTO.getNickname(), createDTO.getGender());
return 1;
}
}
@SoulClient
註解一共有三個屬性:
path
:映射的 HTTP 接口的請求路徑。desc
:接口的描述,便於知道其用途。enable
:是否開啓,默認爲true
開啓。
後續,在 Dubbo 服務啓動時,Soul Client 會自動解析 @SoulClient
註解的 Dubbo 方法,寫入方法的元數據到 Soul Admin 控制檯,最終通知到 Soul Bootstrap 服務網關上。
3.3 簡單測試
① 執行 UserServiceApplication 啓動 Dubbo 服務。在 IDEA 控制檯可以看到如下日誌,看到寫入 Dubbo 方法的元數據到 Soul Admin 控制檯。
2020-05-23 01:27:56.682 INFO 54370 --- [pool-2-thread-1] .d.s.c.d.s.DubboServiceBeanPostProcessor : dubbo client register success :{} {"appName":"user-service","path":"/user-api/user/get","pathDesc":"獲得用戶詳細","rpcType":"dubbo","serviceName":"cn.iocoder.springboot.lab60.userservice.api.UserService","methodName":"getUser","parameterTypes":"java.lang.Integer","rpcExt":"{\"version\":\"1.0.0\"}","enabled":true}
2020-05-23 01:27:56.944 INFO 54370 --- [pool-2-thread-1] .d.s.c.d.s.DubboServiceBeanPostProcessor : dubbo client register success :{} {"appName":"user-service","path":"/user-api/user/create","pathDesc":"創建用戶","rpcType":"dubbo","serviceName":"cn.iocoder.springboot.lab60.userservice.api.UserService","methodName":"createUser","parameterTypes":"cn.iocoder.springboot.lab60.userservice.api.dto.UserCreateDTO","rpcExt":"{\"version\":\"1.0.0\"}","enabled":true}
② 使用瀏覽器,訪問 http://127.0.0.1:9095/#/system/metadata 地址,進入「系統管理 -> 元數據」菜單,可以看到上述註冊的元數據。如下圖所示:
③ 使用瀏覽器,訪問 http://127.0.0.1:9095/#/plug/dubbo 地址,進入「插件列表 -> Dubbo」菜單,看到選擇器和規則。如下圖所示:
點擊選擇器 /user-api
的「編輯」按鈕,查看該選擇器的具體信息。如下圖所示:
點擊規則 /user-api/user/get
的「編輯」按鈕,查看該規則的具體信息。如下圖所示:
④ 使用 Postman 模擬請求 http://127.0.0.1:9195/user-api/user/get 地址,調用 UserServiceImpl#getUser(Integer id)
方法。如下圖所示:
使用 Request Method 爲
POST
。請求內容類型爲
application/json
。因爲
UserServiceImpl#getUser(Integer id)
方法是非 Bean 參數類型,所以直接在 Request Body 輸入具體值即可。
⑤ 使用 Postman 模擬請求 http://127.0.0.1:9195/user-api/user/create 地址,調用 UserServiceImpl#createUser(UserCreateDTO createDTO)
方法。如下圖所示:
使用 Request Method 爲
POST
。請求內容類型爲
application/json
。因爲
UserServiceImpl#createUser(UserCreateDTO createDTO)
方法是 Bean 參數類型,所以直接在 Request Body 輸入 JSON 數據格式。
至此,我們已經完成了 Soul 網關接入 Dubbo 應用,並進行相應的而測試。
友情提示:實際上,我們也可以參考《Soul 文檔 —— dubbo 插件》,手動在 Soul Admin 控制檯配置 Dubbo 接口方法的元數據,以及進行 dubbo 插件的選擇器和規則的設置,實現 Soul Bootstrap 服務網關轉發請求到 Dubbo 服務,無需在 Dubbo 項目中引入
soul-client-apache-dubbo
依賴。也就是說,引入
soul-client-apache-dubbo
依賴的目的,是爲了實現自動化,畢竟手工配置比較麻煩,並且容易出錯。
4. 接入 Spring Boot 應用
示例代碼對應倉庫:
lab-60-soul-spring-boot-demo
本小節,我們參考《Soul 文檔 —— http 用戶接入》文章,接入 Soul 服務網關。整個示例架構如下圖所示:
下面,我們來開始正式接入 Spring Boot 應用。
4.1 設置 divide 插件
需要設置 divide 插件 爲開啓。該插件實現 HTTP 正向代理的功能,所有 HTTP 類型的請求你,都由它進行負載均衡的調用。
使用瀏覽器,訪問 http://127.0.0.1:9095/#/system/plugin 地址,進入「系統管理 -> 插件管理」菜單,可以看到 divide 插件。如下圖所示:
默認情況下,divide 插件已經是開啓狀態,所以無需開啓。
4.2 安裝 Zookeeper
因爲 Soul 網關需要知道後端 Spring Boot 應用的 host + port 地址,所以 Soul Client 實現使用 Zookeeper 作爲註冊中心,讓 Spring Boot 應用註冊到其上,從而使得 Soul 網關能夠知道具體轉發的地址。
① 參考《芋道 Zookeeper 極簡入門》文章,先來搭建一個 Zookeeper 服務。
② 重啓 Soul Admin 控制檯,設置 --soul.http.zookeeper-url
配置項爲 Zookeeper 地址。完整命令如下:
java -jar soul-admin.jar --spring.datasource.url="jdbc:mysql://s1.iocoder.cn:3306/soul?useUnicode=true&characterEncoding=utf-8&zeroDateTimeBehavior=CONVERT_TO_NULL&failOverReadOnly=false&autoReconnect=true&useSSL=false" --spring.datasource.username='root' --spring.datasource.password='3WLiVUBEwTbvAfsh' --soul.http.register=true --soul.http.zookeeper-url=127.0.0.1:2181
4.3 搭建 Spring Boot 示例項目
先快速搭建一個 Spring Boot 示例項目,暫未接入 Soul 網關。如下圖所示:
lab-60-soul-spring-boot-demo
4.3.1 引入依賴
修改 pom.xml
文件,引入 soul-client-springmvc
依賴,它是 Soul 對 SpringMVC 的集成支持。
<!-- 引入 Soul 針對 SpringMVC 的集成的依賴 -->
<dependency>
<groupId>org.dromara</groupId>
<artifactId>soul-client-springmvc</artifactId>
<version>2.1.2-RELEASE</version>
</dependency>
4.3.2 配置文件
修改 application.yaml
配置文件,添加 Soul 配置項如下:
soul:
# Soul 針對 SpringMVC 的配置項,對應 SoulHttpConfig 配置類
http:
admin-url: http://127.0.0.1:9095 # Soul Admin 地址
context-path: /sb-demo-api # 設置在 Soul 網關的路由前綴,例如說 /order、/product 等等。
# 後續,網關會根據該 context-path 來進行路由
app-name: sb-demo-service # 應用名。未配置情況下,默認使用 `spring.application.name` 配置項
zookeeper-url: 127.0.0.1:2181 # 使用 Zookeeper 作爲註冊中心的地址
soul.http
配置項,Soul 對 SpringMVC 的配置項,對應 SoulHttpConfig 配置類。具體每個配置項的作用,胖友自己看配置項後的註釋。
4.3.3 UserController
需要在 Controller 的 HTTP API 方法上,添加 @SoulClient
註解,用於設置每個 API 方法對應的請求路徑。這裏,我們修改 UserController 類,添加該註解。代碼如下:
@RestController
@RequestMapping("/user")
public class UserController {
private Logger logger = LoggerFactory.getLogger(getClass());
@GetMapping("/get")
@SoulClient(path = "/user/get", desc = "獲得用戶詳細")
public String getUser(@RequestParam("id") Integer id) {
return "DEMO:" + id;
}
@PostMapping("/create")
@SoulClient(path = "/user/create", desc = "創建用戶")
public Integer createUser(@RequestBody UserCreateDTO createDTO) {
logger.info("[createUser][username({}) password({})]", createDTO.getNickname(), createDTO.getGender());
return 1;
}
}
@SoulClient
註解一共有三個屬性:
path
:映射的 HTTP 接口的請求路徑。desc
:接口的描述,便於知道其用途。enable
:是否開啓,默認爲true
開啓。
後續,在 Spring Boot 應用啓動時,Soul Client 會自動解析 @SoulClient
註解的 API 方法,寫入方法的元數據到 Soul Admin 控制檯,最終通知到 Soul Bootstrap 服務網關上。
4.4 簡單測試
① 執行 DemoApplication 啓動 Spring Boot 應用。在 IDEA 控制檯可以看到如下日誌,看到寫入 HTTP API 方法的元數據到 Soul Admin 控制檯。
// 註冊到 Zookeeper
2020-05-23 10:50:39.587 INFO 62682 --- [ main] o.d.s.c.s.s.ApplicationStartListener : soul-http-client服務註冊成功,context-path:/sb-demo-api, ip:port:10.171.1.115:8080
// 寫入元數據
2020-05-23 10:50:39.911 INFO 62682 --- [pool-1-thread-1] o.d.s.c.s.s.SoulClientBeanPostProcessor : springMvc client register success :{} {"appName":"sb-demo-service","path":"/sb-demo-api/user/get","pathDesc":"獲得用戶詳細","rpcType":"http","serviceName":"UserController","methodName":"getUser","parameterTypes":"java.lang.Integer","rpcExt":"","enabled":true}
2020-05-23 10:50:40.212 INFO 62682 --- [pool-1-thread-1] o.d.s.c.s.s.SoulClientBeanPostProcessor : springMvc client register success :{} {"appName":"sb-demo-service","path":"/sb-demo-api/user/create","pathDesc":"創建用戶","rpcType":"http","serviceName":"UserController","methodName":"createUser","parameterTypes":"cn.iocoder.springboot.lab60.dto.UserCreateDTO","rpcExt":"","enabled":true}
② 使用瀏覽器,訪問 http://127.0.0.1:9095/#/system/metadata 地址,進入「系統管理 -> 元數據」菜單,可以看到上述註冊的元數據。如下圖所示:
③ 使用瀏覽器,訪問 http://127.0.0.1:9095/#/plug/divide 地址,進入「插件列表 -> Divide」菜單,看到選擇器和規則。如下圖所示:
點擊選擇器 /sb-demo-api
的「編輯」按鈕,查看該選擇器的具體信息。如下圖所示:
點擊規則 /sb-demo-api/user/get
的「編輯」按鈕,查看該規則的具體信息。如下圖所示:
④ 使用 Postman 模擬請求 http://127.0.0.1:9195/sb-demo-api/user/get?id=1 地址,轉發到 GET /user/get
接口上。如下圖所示:
使用 Request Method 爲
GET
。請求參數,直接帶在 URL 後面。
⑤ 使用 Postman 模擬請求 http://127.0.0.1:9195/sb-demo-api/user/create 地址,轉發到 POST /user/create
接口上。如下圖所示:
使用 Request Method 爲
POST
。請求內容類型爲
application/json
。因爲
POST /user/create
使用 JSON 接參,所以直接在 Request Body 輸入 JSON 數據格式。
至此,我們已經完成了 Soul 網關接入 Spring Boot 應用,並進行相應的而測試。
友情提示:實際上,我們也可以參考《Soul 文檔 —— divide 插件》,手動在 Soul Admin 控制檯配置 API 接口方法的元數據,以及進行 divide 插件的選擇器和規則的設置,實現 Soul Bootstrap 服務網關轉發請求到 Spring Boot 應用,無需在 Spring Boot 應用中引入
soul-client-springmvc
依賴。也就是說,引入
soul-client-springmvc
依賴的目的,是爲了實現自動化,畢竟手工配置比較麻煩,並且容易出錯。當然,這樣也就無法使用 Zookeeper 作爲註冊中心,需要在 Soul Admin 中手動維護應用的實例列表,會比較麻煩~
5. 接入 Spring Cloud 應用
示例代碼對應倉庫:
lab-60-soul-spring-cloud-demo
本小節,我們參考《Soul 文檔 —— springcloud 用戶接入》文章,接入 Soul 服務網關。整個示例架構如下圖所示:
下面,我們來開始正式接入 Spring Cloud 應用。
5.1 設置 springcloud 插件
需要設置 springcloud 插件 爲開啓。該插件實現從 Spring Cloud 註冊中心獲取服務的示例列表,後續使用 Ribbon 實現負載均衡的調用。
使用瀏覽器,訪問 http://127.0.0.1:9095/#/system/plugin 地址,進入「系統管理 -> 插件管理」菜單,可以看到 springcloud 插件。如下圖所示:
默認情況下,springcloud 插件已經是開啓狀態,所以無需開啓。
5.2 安裝 Nacos
我們使用 Nacos 作爲 Spring Cloud 應用的註冊中心,所有胖友可以參照《Nacos 極簡入門》文章,搭建一個 Nacos 註冊中心。
友情提示:如果想要 Eureka 作爲 Spring Cloud 應用註冊中心的胖友,可以參照《芋道 Spring Cloud Netflix 註冊中心 Eureka 入門》文章,搭建一個 Eureka 註冊中心。
5.3 修改 Soul Bootstrap 接入 Nacos
因爲 Soul Bootstrap 需要從註冊中心獲取 Spring Cloud 應用的實例列表,所以需要集成 Spring Cloud 註冊中心。目前,默認情況下 Soul Bootstrap 網關服務提供的 soul-bootstrap.jar
包,並未引入相關依賴,所以我們需要自己修改源碼,並進行打包。
① 使用 IDEA 從 https://gitee.com/shuaiqiyu/soul 倉庫中,下載最新的源碼。如下圖所示:
② 修改 application.yml
配置文件,添加 spring.cloud.nacos.discovery.server-addr
配置項爲 Nacos 註冊中心的地址。如下圖所示:
application.yml
配置文件③ 修改 pom.xml
文件,引入 spring-cloud-starter-alibaba-nacos-discovery
依賴,集成 Nacos 作爲 Spring Cloud 的註冊中心。如下圖所示:
pom.xml
文件友情提示:如果想要 Eureka 作爲 Spring Cloud 應用註冊中心的胖友,也是修改配置文件,和引入依賴。
④ 關閉 soul-bootstrap.jar
啓動的服務網關,在 IDEA 中執行 SoulBootstrapApplication 啓動服務網關。美滋滋~
友情提示:啓動時,會報
Connection refused: localhost/127.0.0.1:6379
錯誤,這是 Soul 限流功能需要使用到 Redis,可以暫時忽略。
5.4 搭建 Spring Cloud 示例項目
先快速搭建一個 Spring Cloud 示例項目,暫未接入 Soul 網關。如下圖所示:
lab-60-soul-spring-cloud-demo
5.4.1 引入依賴
修改 pom.xml
文件,引入 soul-client-springcloud
依賴,它是 Soul 對 Spring Cloud 的集成支持。
<!-- 引入 Soul 針對 Spring Cloud 的集成的依賴 -->
<dependency>
<groupId>org.dromara</groupId>
<artifactId>soul-client-springcloud</artifactId>
<version>2.1.2-RELEASE</version>
</dependency>
5.4.2 配置文件
修改 application.yaml
配置文件,添加 Soul 配置項如下:
soul:
# Soul 針對 SpringMVC 的配置項,對應 SoulSpringCloudConfig 配置類
springcloud:
admin-url: http://127.0.0.1:9095 # Soul Admin 地址
context-path: /sc-user-service-api # 設置在 Soul 網關的路由前綴,例如說 /order、/product 等等。
# 後續,網關會根據該 context-path 來進行路由
app-name: sc-user-service # 應用名。未配置情況下,默認使用 `spring.application.name` 配置項
soul.springcloud
配置項,Soul 對 Spring Cloud 的配置項,對應 SoulSpringCloudConfig 配置類。具體每個配置項的作用,胖友自己看配置項後的註釋。
5.4.3 UserController
需要在 Controller 的 HTTP API 方法上,添加 @SoulClient
註解,用於設置每個 API 方法對應的請求路徑。這裏,我們修改 UserController 類,添加該註解。代碼如下:
@RestController
@RequestMapping("/user")
public class UserController {
private Logger logger = LoggerFactory.getLogger(getClass());
@GetMapping("/get")
@SoulClient(path = "/user/get", desc = "獲得用戶詳細")
public String getUser(@RequestParam("id") Integer id) {
return "DEMO:" + id;
}
@PostMapping("/create")
@SoulClient(path = "/user/create", desc = "創建用戶")
public Integer createUser(@RequestBody UserCreateDTO createDTO) {
logger.info("[createUser][username({}) password({})]", createDTO.getNickname(), createDTO.getGender());
return 1;
}
}
@SoulClient
註解一共有三個屬性:
path
:映射的 HTTP 接口的請求路徑。desc
:接口的描述,便於知道其用途。enable
:是否開啓,默認爲true
開啓。
後續,在 Spring Cloud 應用啓動時,Soul Client 會自動解析 @SoulClient
註解的 API 方法,寫入方法的元數據到 Soul Admin 控制檯,最終通知到 Soul Bootstrap 服務網關上。
5.5 簡單測試
① 執行 DemoApplication 啓動 Spring Boot 應用。在 IDEA 控制檯可以看到如下日誌,看到寫入 HTTP API 方法的元數據到 Soul Admin 控制檯。
2020-05-23 17:00:26.711 INFO 67422 --- [pool-1-thread-1] s.SoulSpringCloudClientBeanPostProcessor : springCloud client register success :{} {"appName":"sc-user-service","path":"/sc-user-service-api/user/get","pathDesc":"獲得用戶詳細","rpcType":"springCloud","serviceName":"UserController","methodName":"getUser","parameterTypes":"java.lang.Integer","rpcExt":"","enabled":true}
2020-05-23 17:00:27.110 INFO 67422 --- [pool-1-thread-1] s.SoulSpringCloudClientBeanPostProcessor : springCloud client register success :{} {"appName":"sc-user-service","path":"/sc-user-service-api/user/create","pathDesc":"創建用戶","rpcType":"springCloud","serviceName":"UserController","methodName":"createUser","parameterTypes":"cn.iocoder.springcloud.lab60.dto.UserCreateDTO","rpcExt":"","enabled":true}
② 使用瀏覽器,訪問 http://127.0.0.1:9095/#/system/metadata 地址,進入「系統管理 -> 元數據」菜單,可以看到上述註冊的元數據。如下圖所示:
③ 使用瀏覽器,訪問 http://127.0.0.1:9095/#/plug/divide 地址,進入「插件列表 -> Divide」菜單,看到選擇器和規則。如下圖所示:
點擊選擇器 /sc-user-service-api
的「編輯」按鈕,查看該選擇器的具體信息。如下圖所示:
點擊規則 /sc-user-service-api/user/get
的「編輯」按鈕,查看該規則的具體信息。如下圖所示:
④ 使用 Postman 模擬請求 http://127.0.0.1:9195/sc-user-service-api/user/get?id=1 地址,轉發到 GET /user/get
接口上。如下圖所示:
使用 Request Method 爲
GET
。請求參數,直接帶在 URL 後面。
⑤ 使用 Postman 模擬請求 http://127.0.0.1:9195/sb-demo-api/user/create 地址,轉發到 POST /user/create
接口上。如下圖所示:
使用 Request Method 爲
POST
。請求內容類型爲
application/json
。因爲
POST /user/create
使用 JSON 接參,所以直接在 Request Body 輸入 JSON 數據格式。
至此,我們已經完成了 Soul 網關接入 Spring Cloud 應用,並進行相應的而測試。
友情提示:實際上,我們也可以參考《Soul 文檔 —— springcloud 插件》,手動在 Soul Admin 控制檯配置 API 接口方法的元數據,以及進行 springcloud 插件的選擇器和規則的設置,實現 Soul Bootstrap 服務網關轉發請求到 Spring Cloud 應用,無需在 Spring Cloud 應用中引入
soul-client-springcloud
依賴。也就是說,引入
soul-client-springcloud
依賴的目的,是爲了實現自動化,畢竟手工配置比較麻煩,並且容易出錯。
6. rateLimiter 插件
本小節,我們參考《Soul 文檔 —— rateLimiter 插件》文章,使用 rateLimiter 插件,實現 Soul 網關的限流功能。該插件是基於令牌桶算法 + Redis 存儲計數,實現分佈式限流。整體設計如下圖:
下面,我們在「3. 接入 Dubbo 應用」小節的基礎上,對 user-api/user/get
實現限流的功能。
6.1 安裝 Redis
相信大家都會,艿艿就不瞎嗶嗶了。嘿嘿~
6.2 設置 rateLimiter 插件
先需要設置 rateLimiter 插件 的 Redis 配置,目前支持單機、哨兵、集羣模式。
① 使用瀏覽器,訪問 http://127.0.0.1:9095/#/system/plugin 地址,進入「系統管理 -> 插件管理」菜單,可以看到 rateLimiter 插件。如下圖所示:
② 點擊 rateLimiter 插件的「編輯」按鈕,設置 Redis 的配置,並設置該插件爲開啓。如下圖所示:
友情提示:Redis 的地址,記得要填寫正確哈~
③ 因爲 Soul Bootstrap 和 Soul Admin 暫時不支持插件修改的自動加載,所以我們此時需要手動重啓下。
6.3 設置 rateLimiter 限流規則
① 使用瀏覽器,訪問 http://127.0.0.1:9095/#/plug/rate_limiter 地址,進入「插件列表 -> rate_limiter」菜單,進行限流規則的配置。如下圖所示:
② 點擊「添加選擇器」按鈕,添加一個選擇器。如下圖所示:
③ 點擊「添加規則」按鈕,給該選擇器添加一個規則。如下圖所示:
對請求地址
/user-api/user/get
進行限流,對應 UserService 的#getUser(Integer id)
方法。速率:是你允許用戶每秒執行多少請求,而丟棄任何請求。這是令牌桶的填充速率。
容量:是允許用戶在一秒鐘內執行的最大請求數。這是令牌桶可以保存的令牌數。
友情提示:可能胖友對 Soul 定義的選擇器與規則的概念有點不瞭解,可以看看《Soul 文檔 —— 選擇器規則詳解》文章。
6.4 簡單測試
執行 UserServiceApplication 啓動 Dubbo 服務。
快速且多次使用 Postman 模擬請求 http://127.0.0.1:9195/user-api/user/get 地址,調用 UserServiceImpl#getUser(Integer id)
方法,最終被限流。如下圖所示:
7. hystrix 插件
本小節,我們參考《Soul 文檔 —— hystrix 插件》文章,使用 hystrix 插件,使用 Hystrix 框架,實現 Soul 網關的熔斷器功能。
友情提示:對 Hystrix 不瞭解的胖友,可以後續閱讀《芋道 Spring Boot 服務容錯 Hystrix 入門》文章進行學習。
下面,我們在「3. 接入 Dubbo 應用」小節的基礎上,對 user-api/user/get
實現熔斷器的功能。
7.1 設置 hystrix 插件
需要設置 hystrix 插件 爲開啓。
使用瀏覽器,訪問 http://127.0.0.1:9095/#/system/plugin 地址,進入「系統管理 -> 插件管理」菜單,可以看到 hystrix 插件。如下圖所示:
默認情況下,hystrix 插件已經是開啓狀態,所以無需開啓。
7.2 設置 rateLimiter 限流規則
① 使用瀏覽器,訪問 http://127.0.0.1:9095/#/plug/hystrix 地址,進入「插件列表 -> hystrix」菜單,進行熔斷器規則的配置。如下圖所示:
② 點擊「添加選擇器」按鈕,添加一個選擇器。如下圖所示:
③ 點擊「添加規則」按鈕,給該選擇器添加一個規則。如下圖所示:
對請求地址
/user-api/user/get
進行熔斷保護,對應 UserService 的#getUser(Integer id)
方法。
友情提示:可能胖友對 Soul 定義的選擇器與規則的概念有點不瞭解,可以看看《Soul 文檔 —— 選擇器規則詳解》文章。
7.3 簡單測試
不要執行 UserServiceApplication 啓動 Dubbo 服務,模擬其故障。
快速且多次使用 Postman 模擬請求 http://127.0.0.1:9195/user-api/user/get 地址,調用 UserServiceImpl#getUser(Integer id)
方法,最終被熔斷。如下圖所示:
此時,我們在 Soul Bootstrap 網關的日誌可以看到,Hystrix 熔斷器已經打開。日誌內容如下:
2020-05-23 20:52:28.786 ERROR 69264 --- [work-threads-20] o.d.s.web.plugin.hystrix.HystrixPlugin : hystrix execute have circuitBreaker is Open! groupKey:user-service,commandKey:cn.iocoder.springboot.lab60.userservice.api.UserService
666. 彩蛋
至此,我們已經完成了 Soul 網關的學習,後續胖友可以閱讀《Soul 文檔》,瞭解本文暫時並未寫到的內容。
例如插件相關:
monitor 插件:實現監控數據的收集,後續可以使用 Grafana 實現監控儀表盤。
waf 插件:實現黑名單功能,禁止惡意 IP 的訪問。
sign 插件:實現請求籤名功能,保證接口的安全性。
rewrite 插件:對請求 URI 進行重寫。
websocket 插件:實現對 Websocket 進行代理轉發。
自定義插件:自己實現插件,進一步拓展自己的插件。
例如功能相關:
自定義 filter:自定義 Filter,可以拓展安全認證等等功能。
文件上傳下載:提供的文件上傳和下載功能。
友情提示:建議文件上傳不要經過 API 網關,而是先上傳到文件服務器,然後提交 URL 到 API 網關。
自定義 host 與 ip:考慮到 API 網關的前面都有 Nginx,所以需要拓展保證解析到正確的用戶 IP。
自定義返回結果:每個公司的統一返回格式可能有差異,最好自己拓展下。
歡迎加入我的知識星球,一起探討架構,交流源碼。加入方式,長按下方二維碼噢:
已在知識星球更新源碼解析如下:
最近更新《芋道 SpringBoot 2.X 入門》系列,已經 20 餘篇,覆蓋了 MyBatis、Redis、MongoDB、ES、分庫分表、讀寫分離、SpringMVC、Webflux、權限、WebSocket、Dubbo、RabbitMQ、RocketMQ、Kafka、性能測試等等內容。
提供近 3W 行代碼的 SpringBoot 示例,以及超 4W 行代碼的電商微服務項目。
獲取方式:點“在看”,關注公衆號並回復 666 領取,更多內容陸續奉上。
兄弟,艿一口,點個贊!????