Spring cloud Eureka 服务注册中心

780 阅读4分钟

注册中心简介

微服务架构中最核心的部分是服务治理,服务治理最基础的组件是注册中心,随着微服务架构的发展,出现了很多微服务架构的解决方案,比较熟知的有Spring Cloud全家桶和基于Dubbo的相关组合套件

针对注册中心dubbo 支持了 Zookeeper、Redis、Multicast 和 Simple,官方推荐 Zookeeper。Spring Cloud 支持了 Zookeeper、Consul、Eureka,也可结合阿里开源的Nacos官方推荐 Eureka。

使用量较多的几种注册中心对比如下,

注册中心对比

对比项 Eureka Nacos Consul Zookeeper
CAP AP CP + AP CP CP
一致性算法 Raft Raft Paxos
健康检查 Client Beat TCP/HTTP/MySQL/Client Beat TCP/HTTP/gRPC/Cmd Keep Alive
负载均衡策略 Ribbon 权重、metadata、selector Fabio -
雪崩保护
自动注销实例 支持 支持 不支持 支持
访问协议 TCP HTTP/DNS HTTP/DNS TCP

cap是指在一个分布式系统中,一致性(Consistency)、可用性(Availability)、分区容错性(Partition tolerance),这三个要素最多只能同时实现两点,不可能三者兼顾

  • 一致性(C):在分布式系统中的所有数据备份,在同一时刻是否同样的值(等同于所有节点访问同一份最新的数据副本)
  • 可用性(A):在集群中一部分节点故障后,集群整体是否还能响应客户端的读写请求(对数据更新具备高可用性)
  • 分区容忍性(P),就是高可用性,一个节点崩了,并不影响其他的节点(5个节点,挂了两个,不影响服务) Eureka的设计原则是AP(可用性和分区容错性),它保证了注册中心的可用性,但舍弃了数据一致性(各个节点的数据有可能是不一致的,会保证最终一致性)

Eureka架构

本文重点介绍Eureka,其他组件会在后续文章中进行介绍
Eureka是Netflix基于Rest服务的,服务注册、发现组件,主要包括Eureka Server 和Eureka Client 两个组件

  • Eureka Server:提供服务注册服务,各节点启动后会在Eureka Server中注册,并在服务注册表中存储所有可用服务节点的信息
  • Eureka Client:一个Java Client,用于简化Eureka Server的交互,同时作为轮询负载均衡器,提供服务故障的切换支持

Eureka架构图
上图简要描述了Eureka的基本架构,由三个角色组成:

  • Eureka Server 注册中心

    1. 启动后,从其他节点拉取服务注册信息
    2. 运行过程中,定时运行evict(剔除)任务,剔除没有按时renew(续约)的服务(包括非正常停止和网络故障的服务)
    3. 运行过程中,接收到的register、renew、cancel请求,都会同步至其他注册中心节点
  • Service Provider 服务提供者

    1. 启动后,想注册中心发起register请求,注册服务
    2. 在运行过程中,定时向注册中心发送renew心跳,证明“我还活着”
    3. 停止服务提供者,向注册中心发起cancel请求,清空当前服务注册信息
  • Service Consumer 服务消费者

    1. 启动后,从注册中心拉取服务注册信息
    2. 在运行过程中,定时更新服务注册信息
    3. 服务消费者发起远程调用

项目实战

代码及配置

pom.xml

<parent>
    <artifactId>spring-cloud</artifactId>
    <groupId>com.kk</groupId>
    <version>1.0-SNAPSHOT</version>
</parent>
<modelVersion>4.0.0</modelVersion>
<packaging>jar</packaging>


<artifactId>eureka-server</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-actuator</artifactId>
    </dependency>
</dependencies>

parent pom.xml

<groupId>com.kk</groupId>
<artifactId>spring-cloud</artifactId>
<packaging>pom</packaging>
<version>1.0-SNAPSHOT</version>
<modules>
    <module>eureka-server</module>
    <module>user-service</module>
</modules>


<properties>
    <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
    <java.version>1.8</java.version>
    <spring.boot.version>2.1.5.RELEASE</spring.boot.version>
    <spring.cloud.version>Finchley.SR1</spring.cloud.version>
    <spring.eureka.version>2.1.2.RELEASE</spring.eureka.version>
</properties>


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


<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>


        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
            <version>${spring.boot.version}</version>
        </dependency>


        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-actuator</artifactId>
            <version>${spring.boot.version}</version>
        </dependency>


        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-netflix-eureka-server</artifactId>
            <version>${spring.eureka.version}</version>
        </dependency>
    </dependencies>
</dependencyManagement>

注册中心启动类

@SpringBootApplication
@EnableEurekaServer
public class EurekaServerApplication {


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

配置文件 application.yml

server:
  port: 8090


spring:
  application:
    name: eureka-server


eureka:
  instance:
    prefer-ip-address: true
    hostname: localhost
  client:
    # 设置是否将自己作为客户端注册到注册中心(缺省true)
    # 这里为不需要(查看@EnableEurekaServer注解的源码,会发现它间接用到了@EnableDiscoveryClient)
    register-with-eureka: false
    # 设置是否从注册中心获取注册信息(缺省true)
    # 因为这是一个单点的EurekaServer,不需要同步其它EurekaServer节点的数据,故设为false
    fetch-registry: false
    # 设置eureka服务器所在的地址,查询服务和注册服务都需要依赖这个地址
    service-url:
      defaultZone: http://${eureka.instance.hostname}:${server.port}/eureka/

启动界面

示例代码

github地址