五:Spring Cloud 之服務發現與調用-Feign

1. 簡介

Feign is a declarative web service client. It makes writing web service clients easier. To use Feign create an interface and annotate it. It has pluggable annotation support including Feign annotations and JAX-RS annotations. Feign also supports pluggable encoders and decoders. Spring Cloud adds support for Spring MVC annotations and for using the same HttpMessageConverters used by default in Spring Web. Spring Cloud integrates Ribbon and Eureka to provide a load balanced http client when using Feign.

  • Feign 是一個聲明式調用HTTP協議服務的客戶端
  • 支持註解形式發現與調用服務
  • 支持編碼與解碼
  • 與Ribbon、Eureka結合使用可實現負載均衡功能

2. 代碼實現

2.1涉及的模塊

  • eureka-server-singleton:服務註冊中心,端口8761
  • eureka-service: 服務提供者,通過profile指定不同端口模擬一組微服務,端口8762、8763
  • eureka-service-feign:通過Feign調用服務提供者提供的服務

2.2 源代碼

2.2.1 Github地址

https://github.com/andyChenHuaYing/spring-cloud-demo

2.2.2 切換

通過tag切換git tag -d v1.0,若想修改,可根據此tag創建新的分支。

2.3 eureka-server-singleton

Spring Cloud 之服務發現與調用-Ribbon#2.3 eureka-server-singleton 沒有任何區別

2.4 eureka-service

Spring Cloud 之服務發現與調用-Ribbon#2.4 eureka-service 沒有任何區別

2.5 eureka-service-feign

2.5.1整體實現步驟

  1. pom.xml中引入spring-cloud-starter-netflix-eureka-serverspring-cloud-starter-openfeign依賴
  2. application.yml中指定配置項,端口、application.name、eureka-server地址
  3. SpringBoot 啓動類添加啓用Fegin的註解@EnableFeignClients
  4. 在當前項目Service接口類名上使用FeignClient註解指定服務提供者的服務名@FeignClient("eureka-service")
  5. 在需要調用服務提供者的接口方法之上使用註解指定調用服務提供者提供的方法@RequestMapping("/print")
  6. 在需要使用服務提供者提供的方法之處,使用第4步與第5步實例化好的服務提供者的方法

2.5.2 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">
    <parent>
        <artifactId>spring-cloud-finchley-demo</artifactId>
        <groupId>org.oscar.scd</groupId>
        <version>1.0.0</version>
    </parent>
    <modelVersion>4.0.0</modelVersion>

    <artifactId>eureka-service-feign</artifactId>


    <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>
        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-openfeign</artifactId>        </dependency>
    </dependencies>

</project>

2.5.2 application.yml

eureka:
  client:
    serviceUrl:
      defaultZone: http://localhost:8761/eureka/

server:
  port: 8765

spring:
  application:
    name: eureka-serivce-feign

2.5.3 EurekaServiceFeignApplication

package org.oscar.scd.eureka.service.feign;

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.client.discovery.EnableDiscoveryClient;
import org.springframework.cloud.netflix.eureka.EnableEurekaClient;
import org.springframework.cloud.openfeign.EnableFeignClients;

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

2.5.4 FeignHelloController、FeignHelloService

  • FeignHelloService:
package org.oscar.scd.eureka.service.feign.service;

import org.springframework.cloud.openfeign.FeignClient;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;

@FeignClient("eureka-service")
public interface FeignHelloService {

    @RequestMapping("/print")
    String printPort(@RequestParam("name") String name);
}
  • FeignHelloController
package org.oscar.scd.eureka.service.feign.controller;

import org.oscar.scd.eureka.service.feign.service.FeignHelloService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;

@RestController
@RequestMapping("/feign")
public class FeignHelloController {

    @Autowired
    private FeignHelloService service;

    @RequestMapping("/print")
    public String print(@RequestParam("name") String name) {
        return this.service.printPort(name);
    }
}

3. 驗證

3.1 創建SpringBoot啓動類

3.1.1 EurekaServerSingletonApplication

四:Spring Cloud 之服務發現與調用-Ribbon#3.1.1 EurekaServerSingletonApplication 完全一致

3.1.2 EurekaServiceApplication-8762

四:Spring Cloud 之服務發現與調用-Ribbon#3.1.2 EurekaServiceApplication-8762 完全一致

3.1.3 EurekaServiceApplication-8763

四:Spring Cloud 之服務發現與調用-Ribbon#3.1.3 EurekaServiceApplication-8763完全一致

3.1.4 EurekaServiceFeignApplication

最簡單的方式添加一個SpringBoot啓動類型的啓動類就行。

3.2 啓動

依次啓動EurekaServerSingletonApplicationEurekaServiceApplication-8762EurekaServiceApplication-8763EurekaServiceFeignApplication,啓動完成後Run Dashboard界面:
這裏寫圖片描述

3.3 訪問服務信息界面

可直接點擊上圖中Run Dashboard中的8761端口直接訪問,也可訪問http://localhost:8761/查看,可看到三個eureka服務都註冊到註冊中心了。

這裏寫圖片描述

3.4 調用服務

訪問eureka-service-ribbon 提供的服務:http://localhost:8764/ribbon/print?name=oscar,多請求兩次,返回結果在一下兩種中切換,說明負載均衡起作用了。

  • 第一次:
    這裏寫圖片描述
  • 第二次
    這裏寫圖片描述

4. 思考

  • 如何與Ribbon集成的
  • 如何指定負載均衡算法
  • 默認負載均衡算法是如何的
  • 內部使用HttpClient訪問的服務提供者提供的REST接口嗎
  • 如何根據註解以及本地接口定義實例化調用遠程接口的代理實例的
  • 一次完整的調用過程內部需要經過哪些步驟
  • 數據如何序列化與反序列化的

5. 補充

5.1 資料

http://cloud.spring.io/spring-cloud-static/Finchley.SR1/multi/multi_spring-cloud-feign.html

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章