为什么需要统一配置中心?
- 不方便维护:多人对同时对同一份配置修改,冲突不断
- 配置内容安全与权限:线上配置不对开发人员公开,因为敏感故只对运维公开
- 重点(更新配置项目需重启):统一配置中心可实现动态配置,不需重启项目(包括线上配置更新)
- 一开始把配置放置在远端的git上面。config-server把它拉下来放在本地git,如果远端git出问题了,从本地git把配置拉出来。然后其它client的部分,从server拿到client的组件。
开始
- Eureka的client端的依赖、Config Server的依赖
- @EnableDiscoveryClient、@EnableConfigServer
- 中心配置 yml、远程仓库配置
- order.yml (不管选择哪个环境,这个是一定会加载访问的,所以可以把公共配置放这,用不上则注释掉吧) order-dev.yml order-test.yml,这规则内部约定好的。如图:这里虽访问的是 order-test.yml,但是会把 order.yml 和它进行合并。
配置命名的约定规则
- /order-dev.yml(/文件名-环境名.文件后缀)
- /dev/order-dev.yml(/分支名/文件名-环境名.文件后缀)
- /{name}-{profiles}.yml
- /{label}/{name}-{profiles}.yml
- name 服务名
- profile 环境
- label 分支(默认不写就是“master”主分支)
Config Server
<?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.imooc</groupId>
<artifactId>config</artifactId>
<version>0.0.1-SNAPSHOT</version>
<packaging>jar</packaging>
<name>config</name>
<description>Demo project for Spring Boot</description>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.0.0.BUILD-SNAPSHOT</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>Finchley.BUILD-SNAPSHOT</spring-cloud.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-config-server</artifactId>
</dependency>
<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-test</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-config-monitor</artifactId>
</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>
<repositories>
<repository>
<id>spring-snapshots</id>
<name>Spring Snapshots</name>
<url>https://repo.spring.io/snapshot</url>
<snapshots>
<enabled>true</enabled>
</snapshots>
</repository>
<repository>
<id>spring-milestones</id>
<name>Spring Milestones</name>
<url>https://repo.spring.io/milestone</url>
<snapshots>
<enabled>false</enabled>
</snapshots>
</repository>
</repositories>
<pluginRepositories>
<pluginRepository>
<id>spring-snapshots</id>
<name>Spring Snapshots</name>
<url>https://repo.spring.io/snapshot</url>
<snapshots>
<enabled>true</enabled>
</snapshots>
</pluginRepository>
<pluginRepository>
<id>spring-milestones</id>
<name>Spring Milestones</name>
<url>https://repo.spring.io/milestone</url>
<snapshots>
<enabled>false</enabled>
</snapshots>
</pluginRepository>
</pluginRepositories>
</project>
package com.imooc.config;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.client.discovery.EnableDiscoveryClient;
import org.springframework.cloud.config.server.EnableConfigServer;
@SpringBootApplication
@EnableDiscoveryClient
@EnableConfigServer
public class ConfigApplication {
public static void main(String[] args) {
SpringApplication.run(ConfigApplication.class, args);
}
}
spring:
application:
name: config
cloud:
config:
server:
git:
uri: https://gitee.com/SpringCloud_Sell/config-repo
username: [email protected]
password: T#27h*E$cg@%}j
basedir: /Users/admin/code/myProjects/java/imooc/SpringCloud_Sell/config/basedir
eureka:
client:
service-url:
defaultZone: http://localhost:8761/eureka/
- Ps:然后配置中心服务器也是可以高可用的。只是不像eureka那样需要互相注册了,只要端口改一下要多少启动多少就可以了,然后客户端访问配置中心的服务也是负载均衡效果的。如图这个是客户端里的配置和日志,配置这里 CONFIG 自带高可用,也就是上面的 Config Server,然而日志里,光标这个位置多启动几次发现服务地址会不一样(即负载均衡)。
Config Client(e.g. Order)
order server
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-config-client</artifactId>
</dependency>
# bootstrap.yml
spring:
application:
name: order
cloud:
config:
discovery:
enabled: true
service-id: CONFIG
profile: test
eureka:
client:
service-url:
defaultZone: http://localhost:8761/eureka/
(1)加载顺序
- bootstrap.yml 先加载
- application.yml 后加载
- 使用spring cloud config时需要先从云端拿到到配置参数,加载到ApplicationContext内,否则启动会报错,所以要在bootstrap.yml中配置spring cloud config
(2)使用spring cloud config
- 在bootstrap.yml中先配置好spring.application.name、spring.cloud.config.server.git.uri(这里是通过 config client 到 config server 里的 git.uri)
- 问:这里高亮部分为啥要写在这,不是应该写在git配置上的嘛?
- 答:顺序:先注册到服务中心,通过服务中心发现config,发现配置文件。如果说没有配服务中心默认找8761的,如果有则能找到,没有的话就回出问题了。如果服务中心不是8761的则要写在bootstrap里面。
package com.imooc.order.controller;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.cloud.context.config.annotation.RefreshScope;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
@RestController
@RequestMapping("/env")
public class EnvController {
@Value("${env}")
private String env;
@GetMapping("/print")
public String print() {
return env;
}
}
- 这里是拿来做测试用,看是否可以打通!