1、了解微服務
1.1 什么是微服務
- 微服務是一種架構風格
- 一個應用拆分為一組小型服務
- 每個服務運行在自己的進程內,也就是可獨立部署和升級
- 服務之間使用輕量級HTTP交互
- 服務圍繞業務功能拆分
- 可以由全自動部署機制獨立部署
- 去中心化,服務自治。服務可以使用不同的語言、不同的存儲技術
1.2 微服務架構
- 服務調用
- 服務降級
- 服務注冊與發先
- 服務熔斷
- 負載均衡
- 服務消息隊列
- 服務網關
- 配置中心管理
- 自動化構建部署
- 服務監控
- 全鏈路追蹤
- 服務定時任務
- 調度操作
2、了解SpringCloud
2.1 SpringCloud是什么
SpringCloud是分布式微服務架構的站式解決方案,是多種微服務架構落地技術的集合體,俗稱微服務全家桶。
官方文檔:https://spring.io/projects/spring-cloud
Spring Cloud provides tools for developers to quickly build some of the common patterns in distributed systems (e.g. configuration management, service discovery, circuit breakers, intelligent routing, micro-proxy, control bus, one-time tokens, global locks, leadership election, distributed sessions, cluster state). ---摘自官網
根據官方對SpringCloud的描述,SpringCloud提供了一系列工具,能夠讓開發者快速的構建分布式系統。所以SpringCloud並不是一個新技術,只是整合了一些常用的技術進行封裝,然后結合SpringBoot,我們就可以快速構建分布式項目。
SpringCloud包含了很多的技術,看官網的目錄就知道了,一個屏幕都截不全。往往一個技術還沒學會就告訴我已經不用了,特喵的。
2.2 SpringCloud停更組件和替換
SpringCloud的Hoxton版本,和之前的版本相比,用新的組件替換掉了原來大部分的組件,老的組件現在處於 停更不停用 的狀況。
詳情見下圖(× 的表示之前的組件,現在停更了的;√ 的表示新的替換后的組件):
服務注冊中心
Eureka:官方停止更新,並且已經有更好的替代產品了,可以使用,但是官方已經不建議使用了。
Zookeeper:某些老系統,以前是用的Zookeeper + Dubbo,后來做技術升級,結果發現SpringCloud的Eureka停更了,然后就用了最少的技術切換,那么就用了Zookeeper做注冊中心。
Consul:go語言開發的,也是一個優秀的服務注冊框架,但是使用量較少,風頭都被Nacos搶了。
Nacos:來自於SpringCloudAlibaba,在企業中經過了百萬級注冊考驗的,不但可以完美替換Eureka,還能做其他組件的替換,所以強烈建議使用,是學習的重點。
服務調用
Ribbon:也進入了維護狀態,停止更新了,但是Spring官方還在使用。
LoadBalancer:Spring官方推出的一個新的組件,打算逐漸取代掉Ribbon,但是現在還處於萌芽狀態。
服務調用2
Feign:Netflix 公司產品,也停止更新了。
OpenFeign:Spring社區等不了Netflix更新了,然后就自己做了一個組件,不用Feign了。
服務降級
Hystrix:官網不推薦使用,但是中國企業中還在大規模使用。
Resilience4J:官網推薦使用,但是國內很少用這個。
Sentienl:來自於SpringCloudAlibaba,在中國企業替換Hystrix的組件,國內強烈建議使用。
服務網關
Zuul:Netflix 公司產品,公司內部產生分歧,有的人想自己出一個Zuul2。
Zuul2:也是Netflix 公司准備出的產品,但是由於內部分歧,所以Zuul2已經胎死腹中了。
gateway:Spring社區自己出的網關組件,官方隆重介紹和極度推薦的網關服務組件。
服務配置
Config:目前也在使用,風頭被Nacos搶了。
Nacos:來自於SpringCloudAlibaba,后來居上,把Config給替換了。
服務總線
Bus:SpringCloud原生的服務總線組件,現在風頭也被Nacos搶了。
Nacos:來自於SpringCloudAlibaba,后來居上,把Bus給替換了。
綜上可以看出,Nacos 是重中之重,一個組件就替換掉了原來的幾個組件。
3、創建分布式項目
分布式項目和單體項目不一樣,一般都會分為多個模塊,構成父工程子工程的關系。一般單個SpringBoot項目,pom文件總是有這么一段
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.1.2.RELEASE</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
父項目指定為SringBoot某個版本,后續使用相關的jar包都繼承父項目指定的版本信息。
下面來新建一個分布式項目的父工程
3.1 創建父工程
創建微服務cloud整體聚合父工程Project,有8個關鍵步驟:
(1)New Project - maven工程
(2)聚合總父工程名字
(3)Maven選版本
(4)工程名字
(5)字符編碼 - Settings - File encoding
(6)注解生效激活 - Settings - Annotation Processors
(7)Java編譯版本選8
(8)File Type過濾 - Settings - File Type
創建完后,可以把src目錄刪除,因為父工程不需要,刪除后變成了下面這樣
然后需要修改pom.xml文件,注意看注釋
<?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.codeliu</groupId>
<artifactId>springcloud-test</artifactId>
<version>1.0-SNAPSHOT</version>
<!--父工程的打包方式必須為pom-->
<packaging>pom</packaging>
<!--統一管理jar包版本號-->
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<maven.compiler.source>8</maven.compiler.source>
<maven.compiler.target>8</maven.compiler.target>
<junit.version>4.12</junit.version>
<log4j.version>1.2.17</log4j.version>
<lombok.version>1.16.18</lombok.version>
<mysql.version>8.0.11</mysql.version>
<druid.version>1.1.16</druid.version>
<mybatis.spring.boot.version>1.3.0</mybatis.spring.boot.version>
</properties>
<!--聲明依賴jar包和指定版本,並不實現引入,由子項目進行引入,子項目如果不指定版本則使用父項目申明的版本,也可以指定版本進行覆蓋-->
<dependencyManagement>
<dependencies>
<!--spring boot 2.2.2-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-dependencies</artifactId>
<version>2.2.2.RELEASE</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<!--spring cloud Hoxton.SR1-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>Hoxton.SR1</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<!--spring cloud alibaba 2.1.0.RELEASE-->
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-alibaba-dependencies</artifactId>
<version>2.1.0.RELEASE</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>${mysql.version}</version>
</dependency>
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>druid</artifactId>
<version>${druid.version}</version>
</dependency>
<dependency>
<groupId>org.mybatis.spring.boot</groupId>
<artifactId>mybatis-spring-boot-starter</artifactId>
<version>${mybatis.spring.boot.version}</version>
</dependency>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>${junit.version}</version>
</dependency>
<dependency>
<groupId>log4j</groupId>
<artifactId>log4j</artifactId>
<version>${log4j.version}</version>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>${lombok.version}</version>
<optional>true</optional>
</dependency>
</dependencies>
</dependencyManagement>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<configuration>
<fork>true</fork>
<addResources>true</addResources>
</configuration>
</plugin>
</plugins>
</build>
</project>
關於dependencyManagement
和dependencies
,Maven使用dependencyManagement元素來管理依賴版本號。通常會在一個組織或者項目的最頂層的父POM中看到dependencyManagement元素。
使用pom.xml中的dependencyManagement元素能讓所有子項目中引用依賴而不用顯式的列出版本號。
Maven會沿着父子層次向上走,直到找到一個擁有dependencyManagement元素的項目,然后它就會使用這個
dependencyManagement元素中指定的版本號。
比如在父項目中聲明了數據庫驅動的jar
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>8.0.11</version>
</dependency>
那么在子項目中,就不需要指定版本號了
<dependency>
<groupId>mysq1</groupId>
<artifactId>mysql-connector-java</artifactId>
</dependency>
這樣做的好處就是:如果有多個子項目都引用同一樣依賴,則可以避免在每個使用的子項目里都聲明一個版本號,這樣當想升級或切換到另一個版本時,只需要在頂層父容器里更新,而不需要一個一個子項目的修改;另外如果某個子項目需要另外的一個版本,只需要聲明version即可。
dependencyManagement里只是聲明依賴,並不實現引入,因此子項目需要顯示的聲明需要用的依賴。如果不在子項目中聲明依賴,是不會從父項目中繼承下來的;只有在子項目中寫了該依賴項,並且沒有指定具體版本,才會從父項目中繼承該項,並且version和scope都讀取自父pom。
如果子項目中指定了版本號,那么會使用子項目中指定的jar版本。
另外關於springcloud
的版本號,指定的是Hoxton.SR1
,這也是有說法的。具體可以參考:https://juejin.cn/post/6844903922511904776
3.2 創建子項目
在父工程上右鍵新建
我們的子項目是什么類型的就建什么類型的,這里新建一個SpringBoot項目,填寫相關信息
創建完成后的目錄結構如下
然后我們需要修改父項目和子項目的pom文件進行關聯
創建其他的子項目都是一樣的步驟。
對於一些不需要服務啟動的子模塊,比如common模塊,那么在新建后,可以刪除啟動類及相關的測試文件夾。
在子項目中如果要互相引用,比如某個子模塊要引入cloud-provider-payment
模塊,直接在pom文件中進行指定即可
<dependency>
<groupId>com.codeliu</groupId>
<artifactId>cloud-provider-payment</artifactId>
<version>1.0-SNAPSHOT</version>
</dependency>
參考:
- SpringCloud停更組件和替換:https://www.cnblogs.com/y3blogs/p/13276504.html
- https://blog.csdn.net/u011863024/article/details/114298270
- SpringCloud版本說明:https://juejin.cn/post/6844903922511904776