SpringCloud --- 从零开始,项目搭建
1.介绍
Spring Cloud是一系列框架的有序集合。它利用Spring Boot的开发便利性巧妙地简化了分布式系统基础设施的开发,如服务发现注册、配置中心、消息总线、负载均衡、断路器、数据监控等,都可以用Spring Boot的开发风格做到一键启动和部署。
Module | Desc |
---|---|
Spring Cloud Netflix | 是对Netflix开发的一套分布式服务框架的封装,包括服务的发现和注册,负载均衡、断路器、REST客户端、请求路由等。 |
Spring Cloud Config | 将配置信息中央化保存, 配置Spring Cloud Bus可以实现动态修改配置文件 |
Spring Cloud Stream | 分布式消息队列,是对Kafka, MQ的封装 |
Spring Cloud Security | 对Spring Security的封装,并能配合Netflix使用 |
Spring Cloud Zookeeper | 对Zookeeper的封装,使之能配置其它Spring Cloud的子项目使用 |
1.1 版本
https://spring.io/projects/spring-cloud.
Angel 和Brixton已于2017年7月终止不再进行维护
SpringCloud版本 | SpringBoot版本 |
---|---|
Hoxton(霍斯顿) | 2.2.x, 2.3.x (Starting with SR5) |
Greenwich(格林威治) | 2.1.x |
Finchley(芬奇利) | 2.0.x |
Edgware(埃奇韦尔) | 1.5.x |
Dalston(多尔斯顿) | 1.5.x |
Camden(卡姆登) | 1.4.x |
Brixton(布里克斯顿) | 1.3.x |
Angel(天使) | 1.0.x |
2.创建父工程-Parent Project
1.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 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.nolan</groupId>
<artifactId>spring-cloud-micro-service</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>spring-cloud-micro-service</name>
<packaging>pom</packaging>
<description>Demo project for Spring Boot</description>
<properties>
<java.version>1.8</java.version>
</properties>
<modules>
<module>eureka-service</module>
</modules>
</project>
1.2 删除其它目录
父目录是没有代码的,所以都删掉,保持界面整洁
3.创建子工程-Eureka Service
- 注册中心Eureka类似于中介
- 我们就相当于微服务中的 Consumer ,而那些房东就相当于微服务中的 Provider 。消费者 Consumer 需要调用提供者 Provider 提供的一些服务,就像我们现在需要租他们的房子一样
发生了一点小插曲
报警initialization failed for ‘https://start.spring.io‘.
3.1 pom.xml
spring-cloud-starter-eureka-server 这个依赖在2.0版本已经弃用
<?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 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.1.14.RELEASE</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<groupId>com.nolan</groupId>
<artifactId>eureka-service</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>eureka-service</name>
<description>Demo project for Spring Boot</description>
<properties>
<java.version>1.8</java.version>
<spring.cloud-version>Greenwich.SR5</spring.cloud-version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-eureka-server</artifactId>
</dependency>
<!-- 热部署 -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-devtools</artifactId>
<scope>runtime</scope>
<optional>true</optional>
</dependency>
</dependencies>
<!-- SpringCloud版本依赖管理 -->
<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>
3.2 application.yml
server:
port: 8082
eureka:
instance:
hostname: localhost
client:
fetch-registry: false #false表示自己端就是注册中心,我的职责就是维护服务实
register-with-eureka: false #false表示不向注册中心注册自己。
3.3 启动类
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.netflix.eureka.server.EnableEurekaServer;
@EnableEurekaServer
@SpringBootApplication
public class EurekaServiceApplication {
public static void main(String[] args) {
SpringApplication.run(EurekaServiceApplication.class, args);
}
}
4.创建子工程-User Service(Provider)
4.1 依赖
<?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 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.1.14.RELEASE</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<groupId>com.example</groupId>
<artifactId>user-service</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>user-service</name>
<description>Demo project for Spring Boot</description>
<properties>
<spring.cloud-version>Greenwich.SR5</spring.cloud-version>
<java.version>1.8</java.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<!-- 启动依赖 -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<!-- 热部署 -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-devtools</artifactId>
<scope>runtime</scope>
<optional>true</optional>
</dependency>
<!-- 测试依赖 -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<!-- Eureka 注册中心-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
</dependency>
</dependencies>
<!-- SpringCloud版本依赖管理 -->
<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>
4.2 application.yml
server:
port: 8083
eureka:
client:
serviceUrl:
#eureka 注册中心地址
defaultZone: http://localhost:8082/eureka
instance:
instance-id: spring-consumer-8083 #ip名称
prefer-ip-address: true
spring:
application:
name: user-service-01
4.3 启动类
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.netflix.eureka.EnableEurekaClient;
@EnableEurekaClient
@SpringBootApplication
public class UserServiceApplication {
public static void main(String[] args) {
SpringApplication.run(UserServiceApplication.class, args);
}
}
4.4 Controller和Entity
@RestController
public class UserController {
@RequestMapping(value = "user")
public UserEntity getUser(){
UserEntity user = new UserEntity();
user.setUserId(1);
user.setName("UserMan01");
user.setDesc("he is a hero");
user.setFav(" Heal the world");
return user;
}
}
@Data
public class UserEntity {
private int userId;
private String name;
private String desc;
private String fav;
}
5.创建子工程-User Service2(Provider)
5.1 applicaiton.yml
- 修改端口,测试负载均衡
- spring.application.name要保持一致
server:
port: 8084
eureka:
client:
serviceUrl:
#eureka 注册中心地址
defaultZone: http://localhost:8082/eureka
instance:
instance-id: spring-consumer-8084 #ip名称
prefer-ip-address: true
spring:
application:
name: user-service
5.2 controller
@RestController
public class UserController {
@RequestMapping(value = "user")
public UserEntity getUser(){
UserEntity user = new UserEntity();
user.setUserId(1);
user.setName("UserMan02");
user.setDesc("he is a hero");
user.setFav(" Heal the world");
return user;
}
}
6.创建子工程-Ribbon Service (Consumer)
- Ribbon 是一个基于 HTTP 和 TCP 客户端的负载均衡器
- SpringCloud整合ribbon是RibbonEnrekaAutoConfiguration这个类
- 使用Ribbon只需要在RestTemplate上添加@LoadBalanced,即可负载均衡
6.1 依赖
注意:
- spring-cloud-starter-netflix-eureka-client里面就包含了ribbon
- 下面就是eureka client的依赖
<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 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix</artifactId>
<version>2.1.5.RELEASE</version>
</parent>
<artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
<name>Spring Cloud Starter Netflix Eureka Client</name>
<description>Spring Cloud Starter Netflix Eureka Client</description>
<url>https://projects.spring.io/spring-cloud</url>
<organization>
<name>Pivotal Software, Inc.</name>
<url>https://www.spring.io</url>
</organization>
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-netflix-hystrix</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-netflix-eureka-client</artifactId>
</dependency>
<dependency>
<groupId>com.netflix.eureka</groupId>
<artifactId>eureka-client</artifactId>
</dependency>
<dependency>
<groupId>com.netflix.eureka</groupId>
<artifactId>eureka-core</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-archaius</artifactId>
</dependency>
<--看这里,看这里-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-ribbon</artifactId>
</dependency>
<dependency>
<groupId>com.netflix.ribbon</groupId>
<artifactId>ribbon-eureka</artifactId>
</dependency>
<dependency>
<groupId>com.thoughtworks.xstream</groupId>
<artifactId>xstream</artifactId>
</dependency>
</dependencies>
</project>
依赖如下:
<?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 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.1.14.RELEASE</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<groupId>com.nolan</groupId>
<artifactId>ribbon-consumer</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>ribbon-consumer</name>
<description>Demo project for Spring Boot</description>
<properties>
<java.version>1.8</java.version>
<spring.cloud-version>Greenwich.SR5</spring.cloud-version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<optional>true</optional>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<!-- 热部署 -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-devtools</artifactId>
<scope>runtime</scope>
<optional>true</optional>
</dependency>
<!-- Eureka 注册中心-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-hystrix</artifactId>
</dependency>
</dependencies>
<!-- SpringCloud版本依赖管理 -->
<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>
<version>2.1.14.RELEASE</version>
</plugin>
</plugins>
</build>
</project>
6.2 application.yml
server:
port: 8085
eureka:
client:
serviceUrl:
defaultZone: http://localhost:8082/eureka
instance:
instance-id: spring-consumer-ribbon-8085 #ip名称
prefer-ip-address: true
spring:
application:
name: ribbon-consmer-service
6.3 启动类
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.client.loadbalancer.LoadBalanced;
import org.springframework.cloud.netflix.eureka.EnableEurekaClient;
import org.springframework.context.annotation.Bean;
import org.springframework.web.client.RestTemplate;
@EnableEurekaClient
@SpringBootApplication
public class RibbonConsumerApplication {
@Bean
@LoadBalanced
public RestTemplate restTemplate(){
return new RestTemplate();
}
public static void main(String[] args) {
SpringApplication.run(RibbonConsumerApplication.class, args);
}
}
6.4 Controller
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.cloud.client.ServiceInstance;
import org.springframework.cloud.client.loadbalancer.LoadBalancerClient;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.client.RestTemplate;
@RestController
public class ConsumerController {
@Autowired
private RestTemplate restTemplate;
@RequestMapping(value = "/ribbon",method = RequestMethod.GET)
public UserEntity helloConsumer(){
return restTemplate.getForEntity("http://user-service/user",UserEntity.class).getBody();
}
}
6.5 测试
连续测试 => http://localhost:8085/ribbon
7.创建子工程-Hystrix Service
在Ribbon Service上进行操作
7.1 添加Hystrix依赖
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-hystrix</artifactId>
</dependency>
7.2 启动类
添加@EnableCircuitBreaker
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.client.circuitbreaker.EnableCircuitBreaker;
import org.springframework.cloud.client.loadbalancer.LoadBalanced;
import org.springframework.cloud.netflix.eureka.EnableEurekaClient;
import org.springframework.context.annotation.Bean;
import org.springframework.web.client.RestTemplate;
@EnableCircuitBreaker
@EnableEurekaClient
@SpringBootApplication
public class RibbonConsumerApplication {
@Bean
@LoadBalanced
public RestTemplate restTemplate(){
return new RestTemplate();
}
public static void main(String[] args) {
SpringApplication.run(RibbonConsumerApplication.class, args);
}
}
7.3 修改controller
@RestController
public class ConsumerController {
@Autowired
private ConsumerService consumerService;
@RequestMapping(value = "/ribbon",method = RequestMethod.GET)
public UserEntity getUser(){
return consumerService.helloConsumer2();
}
}
7.4 修改service
import com.netflix.hystrix.contrib.javanica.annotation.HystrixCommand;
import com.nolan.ribbon_consumer.entity.UserEntity;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.web.client.RestTemplate;
@Service
public class ConsumerService {
@Autowired
private RestTemplate restTemplate;
@HystrixCommand(fallbackMethod = "helloFallback")
public UserEntity helloConsumer2(){
return restTemplate.getForEntity("http://user-service/user",UserEntity.class).getBody();
}
public UserEntity helloFallback(){
UserEntity user = new UserEntity();
user.setUserId(1);
user.setName("UserMan03");
user.setDesc("he is a hero");
user.setFav(" Heal the world");
return user;
}
}
7.5 测试
- 连续测试 => http://localhost:8085/ribbon
- 过程中关闭某一个user service
8.创建子工程-Feign Service(Consumer)
- Spring Cloud Feign基于Netfix Feign实现
- Feign整合了Spring Cloud Ribbon和Spring Cloud Hystrix,它是在 Ribbon的基础上进行了一次改进,是一个使用起来更加方便的 HTTP 客户端。
8.1依赖
springcloud F 及F版本以上 springboot 2.0 以上基本上使用openfeign,openfeign 如果从框架结构上看就是2019年feign停更后出现版本,也可以说大多数新项目都用openfeign ,2018年以前的项目在使用feign
<?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 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.1.14.RELEASE</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<groupId>com.nolan</groupId>
<artifactId>Feign-consumer</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>Feign-consumer</name>
<description>Demo project for Spring Boot</description>
<properties>
<java.version>1.8</java.version>
<spring.cloud-version>Greenwich.SR5</spring.cloud-version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<optional>true</optional>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<!-- 热部署 -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-devtools</artifactId>
<scope>runtime</scope>
<optional>true</optional>
</dependency>
<!-- Eureka 注册中心-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-openfeign</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-hystrix</artifactId>
</dependency>
</dependencies>
<!-- SpringCloud版本依赖管理 -->
<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>
8.2 application.yml
server:
port: 8086
# 注册到Eureka服务端的微服务名称
spring:
application:
name: feign-consumer-service
eureka:
client:
serviceUrl:
defaultZone: http://localhost:8082/eureka
instance:
instance-id: spring-consumer-feign-8086 #ip名称
prefer-ip-address: true
8.3 启动类
@SpringBootApplication
@EnableFeignClients
@EnableDiscoveryClient
public class FeignConsumerApplication {
public static void main(String[] args) {
SpringApplication.run(FeignConsumerApplication.class, args);
}
}
8.4 Controller 和Interface
@RestController
public class FeignController {
@Autowired
private FeignInterface feignInterface;
@RequestMapping(value = "/feign",method = RequestMethod.GET)
public UserEntity feignHttp(){
return feignInterface.testFeign();
}
}
@Service
@FeignClient(name = "user-service")
public interface FeignInterface {
@RequestMapping("/user")
UserEntity testFeign();
}
8.5 测试
多次呼叫 => http://localhost:8086/feign,完美负载均衡
8.6 Feign使用hystrix
添加配置,开启hystrix
feign:
hystrix:
enabled: true
接口添加配置@FeignClient(name = “user-service”,fallback = UserFallback.class)
@Repository
@FeignClient(name = "user-service",fallback = UserFallback.class)
public interface FeignInterface {
@RequestMapping("/user")
UserEntity testFeign();
}
UserFallback去实现接口
import com.nolan.feign_consumer.entity.UserEntity;
import com.nolan.feign_consumer.service.FeignInterface;
import org.springframework.stereotype.Component;
@Component
public class UserFallback implements FeignInterface {
@Override
public UserEntity testFeign() {
UserEntity user = new UserEntity();
user.setUserId(1);
user.setName("UserMan04");
user.setDesc("he is a hero");
user.setFav(" Heal the world");
return user;
}
}
测试
9.创建子工程-Zuul Service
9.1 依赖
<?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 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.1.14.RELEASE</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<groupId>com.nolan</groupId>
<artifactId>zuul-service</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>zuul-service</name>
<description>Demo project for Spring Boot</description>
<properties>
<java.version>1.8</java.version>
<spring.cloud-version>Greenwich.SR5</spring.cloud-version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<!-- 热部署 -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-devtools</artifactId>
<scope>runtime</scope>
<optional>true</optional>
</dependency>
<!-- Eureka 注册中心-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-zuul</artifactId>
</dependency>
</dependencies>
<!-- SpringCloud版本依赖管理 -->
<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>
9.2 配置
server:
port: 8087
spring:
application:
name: api-gateway
eureka:
client:
serviceUrl:
#eureka 注册中心地址
defaultZone: http://localhost:8082/eureka
instance:
instance-id: spring-zuul-service-8087 #ip名称
prefer-ip-address: true
zuul:
routes:
userServer.path: /user/**
userServer.serviceId: user-service
9.3 启动类
@EnableZuulProxy
@SpringBootApplication
public class ZuulServiceApplication {
@Bean
public AccessFilter accessFilter(){
return new AccessFilter();
}
public static void main(String[] args) {
SpringApplication.run(ZuulServiceApplication.class, args);
}
}
自定义过滤器,过滤url携带token
package com.example.zuul_service.service;
import com.netflix.zuul.ZuulFilter;
import com.netflix.zuul.context.RequestContext;
import com.netflix.zuul.exception.ZuulException;
import org.apache.juli.logging.LogFactory;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import javax.servlet.http.HttpServletRequest;
public class AccessFilter extends ZuulFilter {
private static final Logger logger = LoggerFactory.getLogger(AccessFilter.class);
/**
* 过滤器的类型 这里用pre,代表会再请求被路由之前执行
*/
@Override
public String filterType() {
return "pre";
}
/**
* 过滤器的执行顺序
*/
@Override
public int filterOrder() {
return 0;
}
/**
* 判断该过滤器是否被执行
* @return
*/
@Override
public boolean shouldFilter() {
return true;
}
/**
* 判断请求鞋带token
* @return
* @throws ZuulException
*/
@Override
public Object run() throws ZuulException {
RequestContext ctx = RequestContext.getCurrentContext();
HttpServletRequest request = ctx.getRequest();
String parameter = request.getParameter("accessToken");
logger.info(request.getRequestURL().toString()+" 请求访问");
if(parameter==null){
logger.error("accessToken为空!");
ctx.setSendZuulResponse(false);
ctx.setResponseStatusCode(401);
ctx.setResponseBody("{\"result\":\"accessToken is empty!\"}");
return null;
}
// token判断逻辑
logger.info(request.getRequestURL().toString()+" 请求成功");
return null;
}
}
10.创建子工程-Config Service
用到了在更新
11.创建子工程-Bus Service
用到了在更新
11.启动报警
问题1: Error creating bean with name ‘configurationPropertiesBeans’
解决:
按照上面依赖去配置。报这个警就是spring boot和spring cloud不匹配