Spring Cloud1

Spring Cloud

代碼地址:https://github.com/jedyang/springCloud

springcloud中文社區(qū)給的定義是微服務架構(gòu)集大成者亚斋,云計算最佳業(yè)務實踐咏瑟。
我的理解是分布式服務全家桶酪捡。
如果你有dubbo或其他分布式框架的使用經(jīng)驗,那么對springcloud提供的特性是很好理解的恩静。
springcloud提供了如下特性:

  • 分布式配置
  • 服務注冊和發(fā)現(xiàn)
  • 路由
  • 遠程服務調(diào)用
  • 負載均衡
  • 斷路器
  • 全局鎖
  • 主從選舉和集群狀態(tài)
  • 分布式消息

主要項目

spring cloud config

springcloud的配置管理項目焕毫,使用git管理∈磺可根據(jù)不同環(huán)境管理不同參數(shù)。也可用于非spring應用循签。

Spring Cloud Netflix

Spring Cloud包含了非常多的子框架级乐,其中,Spring Cloud Netflix是其中一套框架县匠,由Netflix開發(fā)后來又并入Spring Cloud大家庭风科,它主要提供的模塊包括:服務發(fā)現(xiàn)(Eureka),斷路器(Hystrix)乞旦,智能路由(Zuul)和客戶端負載平衡(Ribbon)贼穆。

Spring Cloud Bus

事件總線。使用分布式消息將服務和服務實例聯(lián)系起來兰粉。在集群的狀態(tài)變化傳播中作用很大故痊。

Spring Cloud for Cloud Foundry

讓你的應用同Cloudfoundry進行整合。(Cloudfoundry是最近很熱的開源PaaS云平臺)玖姑。讓你很容易實現(xiàn)SSO(單點登錄)愕秫、OAuth2(一個關(guān)于授權(quán)的開放網(wǎng)絡標準)功能,以及Cloudfoundry的服務分發(fā)器焰络。

Spring Cloud Cloud Foundry Service Broker

提供了一個擴展點戴甩,以便于開發(fā)基于 Cloud Foundry管理的服務分發(fā)器。

Spring Cloud Cluster

主從選舉闪彼√鸸拢基于zookeeper,redis,hazelcast(hazelcast是一個開放源碼集群和高度可擴展的數(shù)據(jù)分發(fā)平臺)缴川,consul(支持多數(shù)據(jù)中心下茉稠,分布式高可用的,服務發(fā)現(xiàn)和配置共享)的抽象和實現(xiàn)二跋。

Spring Cloud Consul

基于Consul實現(xiàn)的服務發(fā)現(xiàn)和配置管理

Spring Cloud Security

提供了對OAuth2 負載均衡的客戶端战惊,以及基于Zuul代理的頭部校驗。

Spring Cloud Sleuth

對spring cloud分布式應用的服務鏈路追蹤

Spring Cloud Data Flow

一個建立數(shù)據(jù)集成和實時處理管道的工具集扎即。
簡化了應用程序的開發(fā)和部署 將精力集中到數(shù)據(jù)處理的用例上吞获。

Spring Cloud Stream

一個輕量級的事件驅(qū)動的微服務框架⊙璞桑可以快速構(gòu)建應用和外部系統(tǒng)對接各拷。可以在springboot應用之間通過簡單的聲明模型闷营,基于kafka或rabbitMq交互消息烤黍。

Spring Cloud Stream App Starters

一個基于springboot的同外部系統(tǒng)的集成應用

Spring Cloud Task

短時任務處理框架。如定時任務傻盟。

Spring Cloud Task App Starters

對應的具體應用速蕊。

Spring Cloud for Amazon Web Services

方便同AWS服務集成

Spring Cloud Connectors

使各種PaaS平臺應用連接基礎(chǔ)后端服務(如數(shù)據(jù)庫服務、消息中間件)更容易娘赴。

Spring Cloud Starters

用于使基于springcloud的依賴管理更方便

Spring Cloud CLI

是一個插件规哲,可以用groovy語言快速創(chuàng)建spring cloud應用

Spring Cloud Contract

是一個消費者驅(qū)動的、面向Java的契約框架诽表。

Spring Cloud Netflix

Netflix是spring cloud的核心框架唉锌,必學必用。

微服務架構(gòu)

首先竿奏,我們來看看一般的微服務架構(gòu)需要的功能或使用場景:

  1. 我們把整個系統(tǒng)根據(jù)業(yè)務拆分成幾個子系統(tǒng)袄简。

  2. 每個子系統(tǒng)可以部署多個應用,多個應用之間使用負載均衡泛啸。

  3. 需要一個服務注冊中心绿语,所有的服務都在注冊中心注冊,負載均衡也是通過在注冊中心注冊的服務來使用一定策略來實現(xiàn)平痰。

  4. 所有的客戶端都通過同一個網(wǎng)關(guān)地址訪問后臺的服務汞舱,通過路由配置,網(wǎng)關(guān)來判斷一個URL請求由哪個服務處理宗雇。請求轉(zhuǎn)發(fā)到服務上的時候也使用負載均衡昂芜。

  5. 服務之間有時候也需要相互訪問。例如有一個用戶模塊赔蒲,其他服務在處理一些業(yè)務的時候泌神,要獲取用戶服務的用戶數(shù)據(jù)良漱。

  6. 需要一個斷路器,及時處理服務調(diào)用時的超時和錯誤欢际,防止由于其中一個服務的問題而導致整體系統(tǒng)的癱瘓母市。

  7. 還需要一個監(jiān)控功能,監(jiān)控每個服務調(diào)用花費的時間等损趋。

Netflix

Spring Cloud Netflix框架剛好就滿足了上面所有的需求患久,而且最重要的是,使用起來非常的簡單浑槽。Spring Cloud Netflix包含的組件及其主要功能大致如下:

  1. Eureka蒋失,服務注冊和發(fā)現(xiàn),它提供了一個服務注冊中心桐玻、服務發(fā)現(xiàn)的客戶端篙挽,還有一個方便的查看所有注冊的服務的界面。 所有的服務使用Eureka的服務發(fā)現(xiàn)客戶端來將自己注冊到Eureka的服務器上镊靴。

  2. Zuul铣卡,網(wǎng)關(guān),所有的客戶端請求通過這個網(wǎng)關(guān)訪問后臺的服務偏竟。他可以使用一定的路由配置來判斷某一個URL由哪個服務來處理煮落。并從Eureka獲取注冊的服務來轉(zhuǎn)發(fā)請求。

  3. Ribbon踊谋,即負載均衡州邢,Zuul網(wǎng)關(guān)將一個請求發(fā)送給某一個服務的應用的時候,如果一個服務啟動了多個實例褪子,就會通過Ribbon來通過一定的負載均衡策略來發(fā)送給某一個服務實例。

  4. Feign骗村,服務客戶端嫌褪,服務之間如果需要相互訪問,可以使用RestTemplate胚股,也可以使用Feign客戶端訪問笼痛。它默認會使用Ribbon來實現(xiàn)負載均衡。

  5. Hystrix琅拌,監(jiān)控和斷路器缨伊。我們只需要在服務接口上添加Hystrix標簽,就可以實現(xiàn)對這個接口的監(jiān)控和斷路器功能进宝。

  6. Hystrix Dashboard刻坊,監(jiān)控面板,他提供了一個界面党晋,可以監(jiān)控各個服務上的服務調(diào)用所消耗的時間等谭胚。

  7. Turbine徐块,監(jiān)控聚合,使用Hystrix監(jiān)控灾而,我們需要打開每一個服務實例的監(jiān)控信息來查看胡控。而Turbine可以幫助我們把所有的服務實例的監(jiān)控信息聚合到一個地方統(tǒng)一查看。這樣就不需要挨個打開一個個的頁面一個個查看旁趟。

接下來一個一個看昼激。

Eureka

作為服務注冊與發(fā)現(xiàn)的中心。我們的demo分為兩部分锡搜,一個server橙困,一個client。 這里的server是指注冊中心余爆。client是指向注冊中心注冊或者訂閱服務的消費者纷宇。

  1. 創(chuàng)建一個maven主工程

  2. 建一個server模塊。
    右鍵-->new module -->Spring Initializr -->next
    -->填寫相關(guān)信息-->next
    -->dependencies 選Cloud Discovery-->Eureka Server
    -->finish

  3. 第一個server

     // 服務注冊中心注解
     @EnableEurekaServer
     @SpringBootApplication
     public class ServerApplication {
     
         public static void main(String[] args) {
             SpringApplication.run(ServerApplication.class, args);
         }
     }
    

    代碼非常簡單蛾方,就是在原來springboot的啟動類上加了一個注解像捶。
    @EnableEurekaServer
    將該實例注冊為一個Eureka的server角色。

  4. 配置文件
    在resources下建一個appication.yml
    配置如下:
    server:
    port: 8761

     eureka:
       instance:
         hostname: localhost
       client:
         registerWithEureka: false
         fetchRegistry: false
         serviceUrl:
           defaultZone: http://${eureka.instance.hostname}:${server.port}/eureka/
    

(注意桩砰,yml對于格式要求非常嚴格拓春,縮進不要搞錯)

  1. 啟動工程
    訪問http://localhost:8761⊙怯纾可以看到注冊中心的界面硼莽。
    此時還沒有服務提供者注冊過來。
1.png
  1. 同創(chuàng)建server一樣的步驟煮纵,建一個client

  2. 代碼如下

     @SpringBootApplication
     @EnableEurekaClient
     @RestController
     public class ClientApplication {
     
         @Value("${server.port}")
         String port;
         @RequestMapping("/hi")
         public String home(@RequestParam String name) {
             return "hi "+name+",i am from port:" +port;
         }
     
         public static void main(String[] args) {
             SpringApplication.run(ClientApplication.class, args);
         }
     }
    

    @EnableEurekaClient表明這是一個client

  3. 配置文件

     eureka:
       client:
         serviceUrl:
           defaultZone: http://localhost:8761/eureka/
     server:
       port: 8762
     spring:
       application:
         name: service-hi
    
  4. 啟動工程
    查看http://localhost:8761已經(jīng)注冊進來

2.png

配置文件中spring.application.name指定的name就是注冊的服務名懂鸵。
其他應用調(diào)用也是根據(jù)這個name來找。

ribbon+restTemplate

微服務架構(gòu)中行疏,業(yè)務被拆分成單獨的服務匆光,服務之間通過rest相互調(diào)用。在springcloud中有兩種調(diào)用方式:ribbon+restTemplate和feign酿联。
ribbon是一個負載均衡客戶端终息,可以很好的控制http和tcp之上的行為,feign也是使用ribbon的贞让。

  1. 再啟動一個進程
    為了嘗試負載均衡周崭,基于上面的工程。改一下client的配置端口喳张,將8762改為8763再啟動一個服務提供方client续镇。
    tips:idea默認run 是單實例的,所以再次run main會讓你停掉之前的服務蹲姐。其實在run configration中配置一下磨取,把Single instance only選項勾掉就可以了人柿。

  2. 查看注冊中心
    測試應該看到

3.png

已經(jīng)有兩個服務注冊進來了。

  1. 建一個服務消費者
    新建一個springboot工程:service-consumer
    在dependency時勾選web忙厌、ribbon凫岖、eureka discovery

  2. 在resources下新建application.yml
    配置:

     eureka:
       client:
         serviceUrl:
           defaultZone: http://localhost:8761/eureka/
     server:
       port: 8764
     spring:
       application:
         name: service-consumer
    
  3. 修改啟動類

     @SpringBootApplication
     @EnableDiscoveryClient
     public class ServicveConsumerApplication {
     
         public static void main(String[] args) {
             SpringApplication.run(ServicveConsumerApplication.class, args);
         }
     
         @Bean
         @LoadBalanced
         RestTemplate restTemplate() {
             return new RestTemplate();
         }
     }
    

    注解@EnableDiscoveryClient作用是向注冊中心注冊自己為消費者。

    @LoadBalanced表明開啟負載均衡功能逢净。
    @Bean注解聲明一個RestTemplate bean

  4. 建一個服務類

         @Service
     public class HelloService {
     
         @Autowired
         RestTemplate restTemplate;
     
         public String sayHello(String name) {
             return restTemplate.getForObject("http://SERVICE-HI/hi?name=" + name, String.class);
         }
     }
    
  5. 建一個對應的測試用例

     @RunWith(SpringRunner.class)
     @SpringBootTest(classes=ServicveConsumerApplication.class)
     public class HelloServiceTest {
     
         @Autowired
         HelloService helloService;
     
         @Test
         public void sayHello() throws Exception {
             for (int i = 0; i < 10; i++){
                 System.out.println(helloService.sayHello("yunsheng"));
             }
     
         }
     
     }
    

跑十次看一下結(jié)果哥放。

    hi yunsheng,i am from port:8763
    hi yunsheng,i am from port:8762
    hi yunsheng,i am from port:8763
    hi yunsheng,i am from port:8762
    hi yunsheng,i am from port:8763
    hi yunsheng,i am from port:8762
    hi yunsheng,i am from port:8763
    hi yunsheng,i am from port:8762
    hi yunsheng,i am from port:8763
    hi yunsheng,i am from port:8762

很明顯看到了負載均衡的效果。

當前我們的應用架構(gòu)是:

4.png

feign

Feign是一個聲明試的web服務客戶端爹土∩瘢可以讓你寫web service client更簡單。Feign默認集成了Ribbon胀茵。
還是使用上面的工程社露,知識需要加一個Feign的依賴。

    <dependency>
        <groupId>org.springframework.cloud</groupId>
        <artifactId>spring-cloud-starter-feign</artifactId>
    </dependency>
  1. 新建一個啟動類

     @SpringBootApplication
     @EnableDiscoveryClient
     @EnableFeignClients
     public class FeignConsumerApplication {
     
         public static void main(String[] args) {
             SpringApplication.run(FeignConsumerApplication.class, args);
         }
     
     }
    

    新增一個@EnableFeignClients注解開啟Feign功能

  2. 新建一個feign服務類

     @FeignClient(value = "service-hi")
     public interface FeignConsumeService {
     
         @RequestMapping(value = "/hi",method = RequestMethod.GET)
         String sayHiFromClientOne(@RequestParam(value = "name") String name);
     }
    

這里的功能就是一個服務代理的接口琼娘,只是內(nèi)部默認實現(xiàn)了負載均衡峭弟。
這里的requestMapping必須是服務提供者的RequestMapping保持一致。

  1. controller層對外暴露一個服務調(diào)用

     @RestController
     public class HiController {
         @Autowired
         FeignConsumeService feignConsumeService;
     
         @RequestMapping(value = "/feignHi", method = RequestMethod.GET)
         public String sayHi(@RequestParam(value = "name") String name){
             return feignConsumeService.sayHiFromFeign(name);
         }
     
     
     }
    

這里的requestMapping隨便寫脱拼。

  1. 啟動瞒瘸。
5.png
可以看到消費者已經(jīng)注冊。  
  1. 消費
    因為我們開放的是rest服務熄浓,所以直接瀏覽器測試情臭。
    瀏覽器多次訪問
    http://localhost:8764/feignHi?name=yunsheng
    可以看到負載均衡的效果,間隔調(diào)用8762和8763的服務赌蔑。

Hystrix斷路器

在微服務架構(gòu)中俯在,各個服務模塊獨立部署。但是由于各種原因娃惯,并不能保證服務100%成功朝巫。如果某個服務發(fā)送異常,產(chǎn)生線程阻塞石景。測試有大量請求進入,會導致servlet線程被耗盡拙吉。由于服務之間的依賴潮孽,導致耽擱服務的異常被傳播擴大,產(chǎn)生災難性后果筷黔。為了避免這種情況往史,業(yè)界采用斷路器模式,當服務不可用情況達到一定閾值后佛舱,斷路器打開椎例,避免故障傳播挨决。

  1. 添加依賴
    基于service-consumer工程添加依賴

     <dependency>
         <groupId>org.springframework.cloud</groupId>
         <artifactId>spring-cloud-starter-hystrix</artifactId>
     </dependency>
    
  2. 改造啟動類

     @SpringBootApplication
     @EnableDiscoveryClient
     @EnableHystrix
     public class ServicveConsumerApplication {
     
         public static void main(String[] args) {
             SpringApplication.run(ServicveConsumerApplication.class, args);
         }
     
         @Bean
         @LoadBalanced
         RestTemplate restTemplate() {
             return new RestTemplate();
         }
     }
    

    添加@EnableHystrix注解,開啟斷路器功能

  3. 改造HelloService

     @Service
     public class HelloService {
     
         @Autowired
         RestTemplate restTemplate;
     
         @HystrixCommand(fallbackMethod = "sayErr")
         public String sayHello(String name) {
             return restTemplate.getForObject("http://SERVICE-HI/hi?name=" + name, String.class);
         }
     
         public String sayErr(String name) {
             return "hi,"+name+",sorry,error!";
         }
     }
    

給之前的sayHello方法添加@HystrixCommand注解订歪,并指定失敗時調(diào)用的方法脖祈。

  1. 測試
    先將8762和8763兩個服務提供者關(guān)掉。
    先將 @HystrixCommand(fallbackMethod = "sayErr")注釋掉刷晋,關(guān)閉斷路器盖高。
    為了方便看出效果。也給ribbon方式新建一個rest的controller眼虱。

     @RestController
     public class HiController {
         @Autowired
         HelloService helloService;
     
         @RequestMapping(value = "/ribbonHi", method = RequestMethod.GET)
         public String sayHi(@RequestParam(value = "name") String name) {
             return helloService.sayHello("yys");
         }
     
     
     }
    

瀏覽器訪問http://localhost:8764/ribbonHi?name=yys
需要等到響應超時才能得到錯誤頁面喻奥。
但是開啟了斷路器之后,
再次嘗試捏悬,可以看到很快輸出hi,yys,sorry,error!撞蚕。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市过牙,隨后出現(xiàn)的幾起案子甥厦,更是在濱河造成了極大的恐慌,老刑警劉巖抒和,帶你破解...
    沈念sama閱讀 218,858評論 6 508
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件矫渔,死亡現(xiàn)場離奇詭異,居然都是意外死亡摧莽,警方通過查閱死者的電腦和手機庙洼,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,372評論 3 395
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來镊辕,“玉大人油够,你說我怎么就攤上這事≌餍福” “怎么了石咬?”我有些...
    開封第一講書人閱讀 165,282評論 0 356
  • 文/不壞的土叔 我叫張陵,是天一觀的道長卖哎。 經(jīng)常有香客問我鬼悠,道長,這世上最難降的妖魔是什么亏娜? 我笑而不...
    開封第一講書人閱讀 58,842評論 1 295
  • 正文 為了忘掉前任焕窝,我火速辦了婚禮,結(jié)果婚禮上维贺,老公的妹妹穿的比我還像新娘它掂。我一直安慰自己,他們只是感情好溯泣,可當我...
    茶點故事閱讀 67,857評論 6 392
  • 文/花漫 我一把揭開白布虐秋。 她就那樣靜靜地躺著榕茧,像睡著了一般。 火紅的嫁衣襯著肌膚如雪客给。 梳的紋絲不亂的頭發(fā)上用押,一...
    開封第一講書人閱讀 51,679評論 1 305
  • 那天,我揣著相機與錄音起愈,去河邊找鬼只恨。 笑死,一個胖子當著我的面吹牛抬虽,可吹牛的內(nèi)容都是我干的官觅。 我是一名探鬼主播,決...
    沈念sama閱讀 40,406評論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼阐污,長吁一口氣:“原來是場噩夢啊……” “哼休涤!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起笛辟,我...
    開封第一講書人閱讀 39,311評論 0 276
  • 序言:老撾萬榮一對情侶失蹤功氨,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后手幢,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體捷凄,經(jīng)...
    沈念sama閱讀 45,767評論 1 315
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 37,945評論 3 336
  • 正文 我和宋清朗相戀三年围来,在試婚紗的時候發(fā)現(xiàn)自己被綠了跺涤。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 40,090評論 1 350
  • 序言:一個原本活蹦亂跳的男人離奇死亡监透,死狀恐怖桶错,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情胀蛮,我是刑警寧澤院刁,帶...
    沈念sama閱讀 35,785評論 5 346
  • 正文 年R本政府宣布,位于F島的核電站,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點故事閱讀 41,420評論 3 331
  • 文/蒙蒙 一俐东、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧,春花似錦、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,988評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽购城。三九已至,卻和暖如春虐译,著一層夾襖步出監(jiān)牢的瞬間瘪板,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 33,101評論 1 271
  • 我被黑心中介騙來泰國打工漆诽, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留侮攀,地道東北人。 一個月前我還...
    沈念sama閱讀 48,298評論 3 372
  • 正文 我出身青樓厢拭,卻偏偏與公主長得像兰英,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子供鸠,可洞房花燭夜當晚...
    茶點故事閱讀 45,033評論 2 355

推薦閱讀更多精彩內(nèi)容