Docker and Eureka with Spring Boot failing to register clients

I have a very simple demo of using Spring Boot + Docker Compose + Eureka.

My server runs on port 8671 with the following application properties:

  • Checking container connectivity with ping in a Calico network of Docker containers
  • Docker COPY not updating files when rebuilding container
  • Not able to connect to the Docker server running on another Linux system
  • Docker run Error: Status 403 trying to pull repository Unable to access the repository:
  • How to increase ulimit in Docker in Elastic Beanstalk?
  • Docker compose version 2.1+ on mac
  • server:
      port: 8761
    eureka:
      instance:
        prefer-ip-address: true
      client:
        registerWithEureka: false
        fetchRegistry: false
      server:
        waitTimeInMsWhenSyncEmpty: 0
    

    My Eureka client runs on port 9000 with the following application properties:

    server:
      port: 9000
    spring:
      application:
        name: user-registration
    eureka:
      client:
        registerWithEureka: true
        fetchRegistry: true
        serviceUrl:
          defaultZone: http://localhost:8761/eureka/
      instance:
        prefer-ip-address: true
    

    When I start up my docker.compose file in the parent maven project, this is the contents of my docker-compose file:

    eureka-server:
      image: rosenthal/eureka-server
    ports:
       - "8761:8761"
    user-registration:
      image: rosenthal/user-registration
      ports:
       - "9000:9000"
      links:
       - eureka-server
    

    When I run my application by first starting the eureka server, following by the client via

    mvn spring-boot:run 
    

    The server successfully registers my client (I call it user-registration).

    When I run my application through docker-compose, the client fails to register with the following output:

     DiscoveryClient_USER-REGISTRATION/0fd640cbc3ba:user-registration:9000: 
     registering service...
     user-registration_1  | 2017-06-21 04:36:05.120 ERROR 1 --- [nfoReplicator-0]        
     c.n.d.s.t.d.RedirectingEurekaHttpClient  : Request execution error
     user-registration_1  | 
     user-registration_1  | com.sun.jersey.api.client.ClientHandlerException: 
     java.net.ConnectException: Connection refused (Connection refused)
    

    My first assumption was that running docker-compose ran into a race condition on waiting for the server to start, but my eureka client seems to have a heartbeat trying to call home to the server it’s configured with. This means it’s just not able to find the Eureka server I have registered (and is running, I can navigate to it on localhost:8671).

    What am I missing here? Everything runs fine running locally with spring-boot starting up with it’s own embedded tomcat containers. As soon as I start to do it with docker-compose, it doesn’t want to work.

    EDIT

    I realized my problem, I believe. So docker doesn’t run on localhost, it runs on the public IP it is assigned when I start up docker. Navigating to this ip + port shows my service running for Eureka Server. The client still doesn’t register.

    SO, I made changes to the application.yml file for my eureka client to:

    serviceUrl:
      defaultZone: http://192.168.59.103:8761/eureka/
    

    That IP is the one my docker daemon is running under. Now, it misses the first registration when I do docker-compose, but the second heartbeat picks up my client.

    How can I ensure the client waits until the server is FULLY up? I used the proper docker “links” field in my docket compose file, but it didn’t work as I hoped. Additionally, how can I see the defaultZone file to be my DOCKER_HOST IP?

    Final result

    The resulting docker-compose file that got everything working for me was:

    eureka-server:
      image: thorrism/eureka-server
      ports:
       - "8761:8761"
    user-registration:
      image: thorrism/user-registration
      ports:
       - "9000:9000"
      links:
       - eureka-server
      environment:
        EUREKA_CLIENT_SERVICEURL_DEFAULTZONE: http://eureka-server:8761/eureka
    

  • ASP.NET Core EF commands: Unable to connect to any of the specified MySQL hosts
  • How could I enable docker remote api on mac osx
  • How to use the official docker elasticsearch container?
  • Creating user in gerrit through ssh
  • How to delete logs in IBM Containers service (BlueMix)
  • xdebug only gets triggered via running script from cli and not browser
  • 2 Solutions collect form web for “Docker and Eureka with Spring Boot failing to register clients”

    If useful for you, that’s in some way how I configure it for my production environment (docker-compose file version 2):

    version: '2'
    services:
      eureka-server:
        image: rosenthal/eureka-server
        expose:
        - "8761"
      user-registration:
        image: rosenthal/user-registration
        container_name: user-registration
        ports:
        - "9000:8080"
        environment:
          server.port: 8080
          eureka.client.enabled: 'true'
          eureka.host: eureka-server
          eureka.instance.preferIpAddress: 'true'
    

    From the docs that’s what expose does:

    Expose ports without publishing them to the host machine – they’ll only be accessible to linked services. Only the internal port can be specified.

    As you’ve got everything in the same network, containers can see each other with no links between them.

    SIDE NOTE

    Keep in mind that with this configuration port 9000 will be publicly accessible at the host machine, and mapped to the 8080 port of the user-registration container.

    Set an environment property to override the eureka.client.serviceUrl.defaultZone to match the service name in your docker compose file.

    eureka-server:
      image: rosenthal/eureka-server
      ports:
       - "8761:8761"
    user-registration:
      image: rosenthal/user-registration
      ports:
       - "9000:9000"
      environment:
       - EUREKA_CLIENT_SERVICEURL_DEFAULTZONE: http://eureka-server:8761/eureka
    

    This will override the property from the packaged application.properties.

    NOTE: As mentioned in the comments you don’t need the links section in the compose file. I removed is as such. See https://docs.docker.com/compose/networking/ for info on that.

    Docker will be the best open platform for developers and sysadmins to build, ship, and run distributed applications.