开发环境
系统:windows 10
Java:jdk-11.0.2
IDE:IDEA 2019.1
项目结构
demo-spring-cloud
--demo-spring-cloud-eureka
项目代码
demo-spring-cloud
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>org.mrding.demo</groupId>
<artifactId>demo-spring-cloud</artifactId>
<packaging>pom</packaging>
<version>1.0-SNAPSHOT</version>
<modules>
<module>demo-spring-cloud-eureka</module>
<module>demo-spring-cloud-service-one</module>
<module>demo-spring-cloud-service-two</module>
<module>demo-spring-cloud-service-api</module>
</modules>
<properties>
<java.version>11</java.version>
</properties>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-dependencies</artifactId>
<version>2.1.1.RELEASE</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>Greenwich.RELEASE</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
<dependencies>
<!--actuator监控中心-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-actuator</artifactId>
</dependency>
<!--jaxb模块引用(用于解决启动报错) - start-->
<dependency>
<groupId>javax.xml.bind</groupId>
<artifactId>jaxb-api</artifactId>
</dependency>
<dependency>
<groupId>com.sun.xml.bind</groupId>
<artifactId>jaxb-impl</artifactId>
<version>2.3.2</version>
</dependency>
<dependency>
<groupId>org.glassfish.jaxb</groupId>
<artifactId>jaxb-runtime</artifactId>
<version>2.3.2</version>
</dependency>
<dependency>
<groupId>javax.activation</groupId>
<artifactId>activation</artifactId>
<version>1.1.1</version>
</dependency>
<!--jaxb模块引用 - end-->
<!--测试-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<configuration>
<source>${java.version}</source>
<target>${java.version}</target>
</configuration>
</plugin>
</plugins>
</build>
</project>
demo-spring-cloud-eureka
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>demo-spring-cloud</artifactId>
<groupId>org.mrding.demo</groupId>
<version>1.0-SNAPSHOT</version>
</parent>
<modelVersion>4.0.0</modelVersion>
<artifactId>demo-spring-cloud-eureka</artifactId>
<dependencies>
<!--Eureka服务器端依赖-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-eureka-server</artifactId>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<configuration>
<mainClass>org.mrding.demo.spring.cloud.eureka.EurekaServerApplication</mainClass>
</configuration>
</plugin>
</plugins>
</build>
</project>
启动类
@SpringBootApplication
@EnableEurekaServer
public class EurekaServerApplication {
public static void main(String[] args) {
SpringApplication.run(EurekaServerApplication.class, args);
}
}
application.yml
server:
#服务端口
port: 8001
spring:
application:
#应用名称
name: spring-cloud-eureka-server
eureka:
server:
#关闭自我保护【用于本地测试时配置-快速剔除失效服务】
enable-self-preservation: false
#检查失效服务间隔【用于本地测试时配置-快速剔除失效服务】
eviction-interval-timer-in-ms: 9000
instance:
#实例主机名(建议使用IP)
hostname: 127.0.0.1
#自定义实例ID(默认为 主机名:应用名:端口号)
instance-id: ${eureka.instance.hostname}:${server.port}
client:
#非集群服务配置,不将自己当客户端注册到自己
register-with-eureka: false
#非集群服务配置,不从服务端拉取服务列表
fetch-registry: false
#指定eureka集群所有服务地址,逗号分隔
#如果当前服务是eureka服务端,当前服务地址也要包含在内,服务地址结构:http://[hostname]:[port]/eureka/
#其中hostname建议最好与配置中的eureka.instance.hostname对应,因为服务端会根据hostname从service-url中区分
#出本机服务url和集群其它伙伴服务url,如果不对应,会将自身也当成伙伴服务,伙伴服务列表在eureka主页上
#DS Replicas部分展示
service-url:
defaultZone: http://127.0.0.1:8001/eureka/
management:
endpoints:
web:
exposure:
#actuator监控中心,开放所有权限
include: '*'
#################################### eureka 集群配置示例 start #################################
#eureka:
# server:
# #关闭自我保护【用于本地测试时配置-快速剔除失效服务】
# enable-self-preservation: false
# #检查失效服务间隔【用于本地测试时配置-快速剔除失效服务】
# eviction-interval-timer-in-ms: 1000
# instance:
# #实例主机名(建议使用IP)
# hostname: 127.0.0.1
# #自定义实例ID
# instance-id: ${eureka.instance.hostname}:${server.port}
# #续约更新时间间隔【用于本地测试时配置-快速剔除失效服务】
# lease-renewal-interval-in-seconds: 3
# #续约到期时间【用于本地测试时配置-快速剔除失效服务】
# lease-expiration-duration-in-seconds: 9
# client:
# #指定eureka集群所有服务地址,逗号分隔
# #如果当前服务是eureka服务端,当前服务地址也要包含在内,服务地址结构:http://[hostname]:[port]/eureka/
# #其中hostname建议最好与配置中的eureka.instance.hostname对应,因为服务端会根据hostname从service-url中区分
# #出本机服务url和集群其它伙伴服务url,如果不对应,会将自身也当成伙伴服务,伙伴服务列表在eureka主页上
# #DS Replicas部分展示
# service-url:
# defaultZone: http://127.0.0.1:8001/eureka/,http://localhost:8002/eureka/,http://192.168.10.110:8003/eureka/
#################################### eureka 集群配置示例 end #################################
说明
好了,看起来就是这么简单,一些查自网上及个人理解的信息,都在注释里了,这里针对集群配置这块再说明一下:
eureka默认是集群配置的,所以默认情况下会将自己注册到集群所有其它节点上,同时从其它节点上同步拉取服务注册信息,单机情况下,集群内就一个节点,就是本身,不需要注册到其它节点,也不需要从其它节点拉取注册信息,所以有如下配置
#非集群服务配置,不将自己当客户端注册到自己
register-with-eureka: false
#非集群服务配置,不从服务端拉取服务列表
fetch-registry: false
而service-url表示集群服务url集合,不能为空,否则会有一个默认值:http://localhost:8761/eureka/, 如果此时你的服务端口不是8761,且eureka.instance.hostname的值不是localhost,那么服务启动后会报错,为什么呢?
因为eureka会根据eureka.instance.hostname的值,与service-url中各地址的hostname部分对比(结构:http://[hostname]:[port]/eureka/),如果不匹配,就认为不是自身节点,而是集群中其它节点,既然同为集群中的节点,那么它就会去尝试和这个节点通信,同步注册信息,结果访问不通,当然就报异常了...
上面的结论是我多次修改配置,测试总结出来的,而基于这一结论,我认为service-url这个属性的配置,不论集群还是单机,都应该配置上所有eureka服务的地址(单机时就是当前服务地址),且每个eureka服务的地址中的hostname部分一定要与它自身的eureka.instance.hostname值保持一致
以上,纯属个人总结,如有不对之处,或不同的理解,还请大神留言告之,不尽感激。