16

我正在评估使用在单独的 docker 容器中运行的 Spring Boot 和 Spring Cloud(Zuul 和 Eureka)构建微服务,部署在单独的 Amazon EC2 实例中。

我有一个向 Eureka 注册的简单 REST 服务,并已将 Zuul 配置为通过在 Eureka 中查找来将请求路由到该服务。 在此处输入图像描述

我可以使用 boot2docker 在我的 Mac 上本地运行(即不在 Amazon/EC2 中),但是当部署在 EC2 上时,Zuul 找不到该服务,并报告“转发错误”(状态 500)。

在 EC2 中,所有内容都配置为在端口 80 上运行(在评估时,我可以轻松地通过我们的防火墙访问)。我可以在 Eureka 系统状态页面中看到 Zuul 和我的服务(尽管所有链接都不起作用!)。

客户端配置为使用完整的 AWS 域名查找 Eureka,因此我可以看到他们如何找到 Eureka OK。例如

  client:
    serviceUrl:
      defaultZone: http://ec2-XX-XX-XX-XX.ap-southeast-2.compute.amazonaws.com:80/eureka/,http://ec2-YY-YY-YY-YY.ap-southeast-2.compute.amazonaws.com:80/eureka/

但是,客户端似乎正在使用其内部 docker IP 地址注册自己(基于 Eureka 系统状态链接)。

在此处输入图像描述

edgeserver 链接指向http://172.17.0.2/info trialservice 链接指向http://172.17.0.3/info

我猜这是不正确的,其他 EC2 实例不知道如何访问该地址。

我已阅读此页面https://github.com/Netflix/eureka/wiki/Configuring-Eureka-in-AWS-Cloud建议使用 AWS EC2 弹性 IP 地址,但我希望我不必这样做.

我还看到这里有一个关于这个主题的当前讨论,https://github.com/spring-cloud/spring-cloud-netflix/issues/432

有没有人设法让这种类型的设置工作,如果是这样,他们是如何配置 Eureka 属性的?

4

1 回答 1

19

好的,为了回答我自己的问题,我找到了解决方案。它基本上涉及配置 eureka 以使用主机名和 docker 以使用 net=host 选项。

这是我的设置(仅显示一个可用区的设置):

应用程序.yml:

Zuul:   
    spring:
      profiles: aws         
    server:
      port: 80          
    eureka:
      datacenter: cloud
      instance:
        preferIpAddress: false
      client:
        serviceUrl:
          defaultZone: http://ec2-XX-XX-XX-XX.ap-southeast-2.compute.amazonaws.com:80/eureka/

Eureka:
    spring:
      profiles: aws-discoA          
    server:
      port: 80          
    eureka:
      instance:
        preferIpAddress: false
      datacenter: cloud
      enableSelfPreservation: false
      client:
        name: eureka
        preferSameZone: false
        shouldOnDemandUpdateStatusChange: false
        region: default
        serviceUrl:
          defaultZone: http://ec2-YY-YY-YY-YY.ap-southeast-2.compute.amazonaws.com:80/eureka/

Service:
    spring:
      profiles: aws
    server:
      port: 0 # or 80 if there is only 1 service/docker in this EC2
    eureka:
      datacenter: cloud
      instance:
        preferIpAddress: false
      client:
        serviceUrl:
          defaultZone: http://ec2-XX-XX-XX-XX.ap-southeast-2.compute.amazonaws.com:80/eureka/

我不确定是否需要“数据中心:云”?

然后启动每个:

Zuul

    sudo docker run -d --name edge -e JAVA_TOOL_OPTIONS="-Dspring.profiles.active=aws -Deureka.instance.hostname=$HOSTNAME" --net="host" edge

Eureka

    sudo docker run -d --name discovery -e JAVA_TOOL_OPTIONS="-Dspring.profiles.active=aws-discoA -Deureka.instance.hostname=$HOSTNAME" --net="host" discovery

Service

    sudo docker run -d --name service -e JAVA_TOOL_OPTIONS="-Dspring.profiles.active=aws -Deureka.instance.hostname=$HOSTNAME" --net="host" service

为了确保这在更复杂的设置中有效,我配置了更多服务器,其中一些服务器每个 EC2 有多个 docker,现在有以下设置。

在此处输入图像描述

此设置在两个可用区中重复,在 Zuul 服务器前面有一个负载均衡器。每个服务都有一个端点,它只返回它的名称、主机名、端口和它被调用的次数。

然后我可以点击负载均衡器并看到每个服务都被称为 AWS 负载均衡器,并且功能区负载均衡器在服务中循环。

于 2015-08-06T22:45:47.840 回答