1、單體應用與微服務
1.1、單體應用
1.1.1、什麼的單體應用
項目所有的資源都在一個應用中,打包成一個war包,使用一個tomcat去運作,運作在一個程序中
1.1.2、單體應用的問題
- 一個子產品挂了,整個項目都受影響
- 單個tomcat更能處理的并發有限,可以做叢集,但是不友善局部(某一個子產品)擴充
- 維護/開發/更新比較麻煩
- 代碼臃腫,編譯,打包都比較慢
- 技術選型單一
- 資料庫選型單一
1.2、微服務架構
1.2.1、什麼是微服務架構
微服務就是把一個大的系統,拆分成多個小的服務,每個微服務隻專注一個業務 ,每個服務有各自的程序, 微服務之間使用網絡通信協定進行資料互動(通常是基于HTTP的RESTful API)。
1.2.2、微服務的特點
- 資料庫選型多樣化
- 技術選型多樣化
- 每個微服務專注一個業務
- 每個維護有自己的程序
- 微服務之間通過網絡協定進行通信
- 友善做局部拓展
- 開發/維護/更新更友善
1.2.3、微服務缺點
- 成本高
- 技術要求比較高
- 部署麻煩
1.3、spring cloud
1.3.1、簡介
Spring cloud是一個基于Spring Boot實作的服務治理工具包,用于微服務架構中管理和協調服務的。
1.3.2、主要元件
- 服務注冊發現——Netflix Eureka : 幫我們服務的通信位址的
- 客服端負載均衡——Netflix Ribbon\Feign :解決網絡通信的
- 斷路器——Netflix Hystrix :解決微服務故障的
- 服務網關——Netflix Zuul :微服務的大門(安保部門)
- 分布式配置——Spring Cloud Config :統一管理微服務的配置
1.3.3、SpringCloud和Dubbo的差別
- dubbo是rpc架構
- SpringCloud是一系列微服務解決方案
- dubbo基于tcp
- SpringCloud基于http
- dubbo在通信方面的性能高于SpringCloud
1.3.4、Spring Cloud架構特點
- 約定優于配置
- 适用于各種環境,開發、部署在PC Servler 或各種雲環境
- 隐藏了元件的複雜性,并提供聲明式、無xml的配置方式
- 開箱即用,快速啟動
- 輕量級元件。Spring Cloud整合的元件大多比較輕量,例如Eureka,Zuul等等,都是各自領域輕量級的實作
- 元件豐富,功能齊全。
- 選型中立、豐富。支援Eureka,Zookeeper和Consul實作的服務發現。
2、Spring Cloud入門
2.1、注冊中心原理
2.2、搭建注冊中心
2.2.1、建立多子產品工程
2.2.2、springcould-parent管理依賴
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<maven.compiler.source>1.8</maven.compiler.source>
<maven.compiler.target>1.8</maven.compiler.target>
<spring-cloud.version>Finchley.SR1</spring-cloud.version>
<springboot.version>2.0.5.RELEASE</springboot.version>
</properties>
<dependencies>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.12</version>
</dependency>
</dependencies>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>${spring-cloud.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-dependencies</artifactId>
<version>${springboot.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
2.2.3、springcloud-eureka-server-3000導入依賴
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-eureka-server</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
</dependencies>
2.2.4、主配置類EnrekaServerApplication_3000
@SpringBootApplication
//開啟注冊中心
@EnableEurekaServer
public class EnrekaServerApplication_3000 {
public static void main(String[] args) {
SpringApplication.run(EnrekaServerApplication_3000.class);
}
2.2.5、配置檔案application.yml
server:
port: 3000
eureka:
instance:
hostname: localhost
client:
registerWithEureka: false #是否要注冊到eureka
fetchRegistry: false #表示是否從Eureka Server擷取注冊資訊
serviceUrl:
defaultZone: http://${eureka.instance.hostname}:${server.port}/eureka/ #單機配置
2.2.6、啟動
2.3、搭建訂單服務springcloud-produce-user-server-1000
2.3.1、導入依賴
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
</dependencies>
2.3.2、主配置類UserProviderApplication_1000
@SpringBootApplication
public class UserProviderApplication_1000 {
public static void main(String[] args) {
SpringApplication.run(UserProviderApplication_1000.class);
}
}
2.3.3、配置檔案application.yml
eureka:
client:
serviceUrl:
#注冊中心服務端的注冊位址
defaultZone: http://localhost:3000/eureka/
instance:
prefer-ip-address: true#使用ip位址注冊
instance-id: user-server:1000 #服務注冊到注冊中心的id
server:
port: 1000
#應用的名字
spring:
application:
name: user-server
2.3.4、啟動
在注冊中心可以看到啟動的提供者
2.4、搭建消費者服務springcloud-consumer-pay-server-2000
步驟與上面一樣
2.5、訂單服務和使用者服務完成通信
2.5.1 搭建公共的使用者子產品springcloud-user-common
因為使用者在使用者服務和訂單服務中都有,以後可能不僅僅這兩個服務中有使用者,是以将這種多次使用的類型,通過公共的子產品,減少代碼的備援,直接将使用的微服務子產品依賴于公共的子產品。
為了示範,建立一個domain,User類
2.5.2 user-server提供者服務編寫接口
1.依賴公共子產品
<dependency>
<groupId>com.vivi</groupId>
<artifactId>springcloud-user-common</artifactId>
<version>1.0-SNAPSHOT</version>
</dependency>
2.建立web.controller
@RestController
public class UserController {
@GetMapping(value = "/user/{id}")
public User getUser(@PathVariable("id") Long id){
User user = new User();
user.setName("調用成功");
user.setId(id);
user.setSex(1);
return user;
}
}
2.5.3 pay-server提供者服務編寫接口
1.依賴公共子產品
<dependency>
<groupId>com.vivi</groupId>
<artifactId>springcloud-user-common</artifactId>
<version>1.0-SNAPSHOT</version>
</dependency>
2.定義RestTemplate的bean
/**
* SpringMvc提供的一個基于Rest風格的http調用工具
* @return
*/
@Bean
public RestTemplate restTemplate(){
return new RestTemplate();
}
3.建立web.controller
這裡的url,也可以寫String url = “http://localhost:1000/user/”+id;
@RestController
public class PayController {
@Autowired
private RestTemplate restTemplate;
@GetMapping(value = "/pay/user/{id}",produces = "application/json")
@HystrixCommand(fallbackMethod = "payFallback")
public User pay(@PathVariable("id") Long id) {
String url = "http://user-server/user/"+id;
User user = restTemplate.getForObject(url, User.class);
return user;
}
}
結果如下圖: