Eureka是Netflix开发的服务发现框架,SpringCloud将它集成在自己的子项目spring-cloud-netflix中,实现SpringCloud的服务发现功能。 
为什么要使用Eureka,因为在一个完整的系统架构中,任何单点的服务都不能保证不会中断,因此我们需要服务发现机制,在某个节点中断后,其它的节点能够继续提供服务,从而保证整个系统是高可用的。 
服务发现有两种模式:一种是客户端发现模式,一种是服务端发现模式。Erueka采用的是客户端发现模式。

 feign:Feign是一个声明式的Web服务客户端,使用Feign可使得Web服务客户端的写入更加方便。 它具有可插拔注释支持,包括Feign注解和JAX-RS注解、Feign还支持可插拔编码器和解码器、Spring Cloud增加了对Spring MVC注释的支持,并HttpMessageConverters在Spring Web中使用了默认使用的相同方式。Spring Cloud集成了Ribbon和Eureka,在使用Feign时提供负载平衡的http客户端。

方式一:使用eureka实现服务治理

一、eureka-service 服务搭建

1、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.rainbow.eureka</groupId>
<artifactId>sikl-road-eureka</artifactId>
<version>0.0.1-SNAPSHOT</version>
<packaging>jar</packaging>

<name>sikl-road-eureka</name>
<description>Demo project for Spring Boot</description>

<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>1.5.9.RELEASE</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>

<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
<java.version>1.8</java.version>
<spring-cloud.version>Edgware.RELEASE</spring-cloud.version>
</properties>

<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-eureka-server</artifactId>
</dependency>

<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</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>
</dependencies>
</dependencyManagement>

<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>


</project>

 

 

 

 

 

2、启动类加注解:@EnableEurekaServer

 

@EnableEurekaServer
@SpringBootApplication
public class EurekaDomeServiceApplication {

public static void main(String[] args) {
SpringApplication.run(EurekaDomeServiceApplication.class, args);
}
}

 

 

 

3、application.yml配置:

 

spring:  
application:
name: eureka-service

server:
port: 1111 # 注册服务的端口号

eureka:
instance:
hostname: localhost # 指定主机名 (域名) 值=spring。profiles
server:
enable-self-preservation: false #关闭保护机制 可以将不可用的服务剔除
client:
register-with-eureka: false #不向注册中心注册资金
fetch-registry: false #关闭服务检索
serviceUrl:
defaultZone: http://${eureka.instance.hostname}:${server.port}/eureka/ # 将自己注册到peer2这个Eureka上面去

 

启动app 访问 http://localhost:1111/  能显示下图服务就搭建成功了:

SpringCloud—— eureka+feign实现声明式服务治理_maven


      

-------------------------------------------------------------------------------------------------------------------------------

二、provider-service搭建

1、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.rainbow.eureka</groupId>
<artifactId>eureka-dome-service</artifactId>
<version>0.0.1-SNAPSHOT</version>
<packaging>jar</packaging>
<name>eureka-dome-service</name>
<description>service</description>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>1.5.9.RELEASE</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
<java.version>1.8</java.version>
<spring-cloud.version>Edgware.RELEASE</spring-cloud.version>
</properties>

<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-eureka</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</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>
</dependencies>
</dependencyManagement>

<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>


</project>

spring-cloud-starter-eureka 依赖就可以了

 

2、启动类加 @EnableEurekaClient 或者 @EnableDiscoveryClient

 

 

@EnableDiscoveryClient
@SpringBootApplication
public class EurekaDomeServiceApplication {

public static void main(String[] args) {
SpringApplication.run(EurekaDomeServiceApplication.class, args);
}
}

也可以使用@EnableEurekaClient 代替@EnableDiscoveryClient注解
 

 

 

3、application.yml 配置:

 

spring:
application:
name: test-service #服务名称

server:
port: 8083

eureka:
client:
serviceUrl:
defaultZone: http://localhost:1111/eureka #注册中心

 

 

 4、具体服务的代码和普通的controller相同:

 

 

@RestController
public class HelloController {

@RequestMapping("/hello")
public String index() {

return "hello word!";
}
}

 

5、运行app 访问http://localhost:1111/,能看到如下内容就算成功了:

SpringCloud—— eureka+feign实现声明式服务治理_spring_02

---------------------------------------------------------------------------------------------------------------------------------

三、consumer-service 配置

方法一:

使用 RestTemplate 和 Ribbon相结合的方式,这里简单介绍一下Ribbon:

 

Ribbon是Netflix公司开源的一个负载均衡的项目,是一个客户端负载均衡器,运行在客户端上。它是一个经过了云端测试的IPC库,可以很好地控制HTTP和TCP客户端的一些行为。 Feign已经默认使用了Ribbon。

Ribbon能做负载均衡、容错、多协议(HTTP, TCP, UDP)支持异步和反应模型、缓存和批处理。

 

1、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.rainbow.eureka</groupId>
<artifactId>eureka-dome-clean</artifactId>
<version>0.0.1-SNAPSHOT</version>
<packaging>jar</packaging>

<name>eureka-dome-clean</name>
<description>Demo project for Spring Boot</description>

<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>1.5.9.RELEASE</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>

<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
<java.version>1.8</java.version>
<spring-cloud.version>Edgware.SR1</spring-cloud.version>
</properties>
<dependency>
<groupId>io.sr</groupId>
<artifactId>sr-dh-biz-api</artifactId>
<version>0.0.1-SNAPSHOT</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-eureka</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-ribbon</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</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>
</dependencies>
</dependencyManagement>

<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>


</project>

只需在pom中添加 spring-cloud-starter-eureka 和 spring-cloud-starter-ribbon 依赖

 

2、启动类添加: @EnableEurekaClient 和 负载均衡配置:

 

@EnableEurekaClient
@SpringBootApplication
public class EurekaDomeCleanApplication {

//开启客户端负载均衡
@Bean
@LoadBalanced
public RestTemplate restTemplate() {
return new RestTemplate();
}

public static void main(String[] args) {
SpringApplication.run(EurekaDomeCleanApplication.class, args);

}

 

3、application.ym 配置 eureka服务地址:

 

server:
port: 7777
eureka:
client:
register-with-eureka: false
serviceUrl:
defaultZone: http://localhost:1111/eureka

 

4、调用服务:

public String test() {
return service.getForObject("http://test-service:8080/hello", String.class);
}

注意test-service是你的服务名,不能是IP地址

 

 

方式二: 声明式服务调用: 使用eureka+feign框架

Spring Cloud Feign 是基于Netflix Feign 实现的,整理Spring Cloud Ribbon 与 Spring Cloud Hystrix,并且实现了声明式的Web服务客户端定义方式。

  在spring cloud feign 的实现下,我们只需创建一个接口并用注解的方式来配置它,即可完成对服务提供方的接口绑定,简化了在使用spring cloud ribbon时自行封装的开发量。简单的说方式二封装了方式一使开发变得更简单。

 

1、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.dome</groupId>
<artifactId>eureka-clean</artifactId>
<version>0.0.1-SNAPSHOT</version>
<packaging>jar</packaging>

<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>1.5.9.RELEASE</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>

<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
<java.version>1.8</java.version>
<spring-cloud.version>Dalston.SR1</spring-cloud.version>
</properties>

<dependencies>

<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-eureka</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-feign</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>

<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</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>
</dependencies>
</dependencyManagement>

<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>


</project>

pom文件中要引入eureka依赖和feign依赖

 

2、在启动类中添加@EnableFeignClients 和 @EnableEurekaClient:

 

@EnableFeignClients
@EnableEurekaClient
@SpringBootApplication
public class EurekaDomeCleanApplication {

public static void main(String[] args) {
SpringApplication.run(EurekaDomeCleanApplication.class, args);

}

 

3、application.yml  配置: 

server:
port: 7777

eureka:
client:
register-with-eureka: false
serviceUrl:
defaultZone: http://localhost:1111/eureka

 

4、创建接口:

@FeignClient("test-service")
public interface FeignService {
@RequestMapping("/hello")
String hello() ;
}

5、使用接口调用服务:

@Autowired
private FeignService fs;

public String test() {
return fs.hello();
}

这种方法开发是开发中最常用的方式,开发时provider会提供一个 provider-service-api 里面提供feign接口供consumer依赖使用

 

---------------------------------------------------------------------------------------------------------------------------------问题总结:

 

SpringCLoud中的“Discovery Service”有多种实现,比如:eureka, consul, zookeeper。

1,​​@EnableDiscoveryClient​​​注解是基于​​spring-cloud-commons​​​依赖,并且在classpath中实现; 
2,​​​@EnableEurekaClient​​​注解是基于​​spring-cloud-netflix​​依赖,只能为eureka作用;

其实用更简单的话来说,就是如果选用的注册中心是eureka,那么就推荐@EnableEurekaClient,如果是其他的注册中心,那么推荐使用@EnableDiscoveryClient。

 

开发时,consumer 启动类的位置最好和 provider启动类的位置相同,以免发生错误

 

使用eureka+feign方式时,建议使用三个模块: 服务提供者, 服务提供者提供的接口,服务消费者 

feign为了方便开发人员使用所以提供的注解名城与springMVC的名称一致,只是名称一样所以使用时要多加小心不要犯错