2

I am learning docker and trying to create a docker-compose.yml file for a springboot db application(jdk 10). Spring boot picks up 27017 as a default port for mongodb, so if I start a mongo container with below command:

docker run -d -p 27017:27017 mongo

And then start my application in intellij, everything works fine. When I try to use a docker-compose.yml, i get a connection exception.

This is my Dockerfile

FROM openjdk:8-jdk-alpine
ARG JAR_FILE=target/*.jar
COPY ${JAR_FILE} app.jar
ENTRYPOINT ["java","-jar","/app.jar"]

This is my docker-compose.yml:

services:
  java:
    image: adoptopenjdk/openjdk10:latest
  mongo:
    image: mongo
    expose:
      - "27017"
    ports:
     - "0.0.0.0:27017:27017"
  spring_boot_mongo:
    build: .
    ports:
      - "8080:8080"
    links:
      - java
version: "2"

Error while running docker-compose up command:

localhost:27017
spring_boot_mongo_1  |
spring_boot_mongo_1  | com.mongodb.MongoSocketOpenException: Exception opening socket
spring_boot_mongo_1  |  at com.mongodb.internal.connection.SocketStream.open(SocketStream.java:67) ~[mongodb-driver-core-3.8.2.jar!/:na]
spring_boot_mongo_1  |  at com.mongodb.internal.connection.InternalStreamConnection.open(InternalStreamConnection.java:126) ~[mongodb-driver-core-3.8.2.jar!/:na]
spring_boot_mongo_1  |  at com.mongodb.internal.connection.DefaultServerMonitor$ServerMonitorRunnable.run(DefaultServerMonitor.java:117) ~[mongodb-driver-core-3.8.2.jar!/:na]
spring_boot_mongo_1  |  at java.lang.Thread.run(Thread.java:748) [na:1.8.0_212]
spring_boot_mongo_1  | Caused by: java.net.ConnectException: Connection refused (Connection refused)
spring_boot_mongo_1  |  at java.net.PlainSocketImpl.socketConnect(Native Method) ~[na:1.8.0_212]
spring_boot_mongo_1  |  at java.net.AbstractPlainSocketImpl.doConnect(AbstractPlainSocketImpl.java:350) ~[na:1.8.0_212]
spring_boot_mongo_1  |  at java.net.AbstractPlainSocketImpl.connectToAddress(AbstractPlainSocketImpl.java:206) ~[na:1.8.0_212]
spring_boot_mongo_1  |  at java.net.AbstractPlainSocketImpl.connect(AbstractPlainSocketImpl.java:188) ~[na:1.8.0_212]
spring_boot_mongo_1  |  at java.net.SocksSocketImpl.connect(SocksSocketImpl.java:392) ~[na:1.8.0_212]
spring_boot_mongo_1  |  at java.net.Socket.connect(Socket.java:589) ~[na:1.8.0_212]
spring_boot_mongo_1  |  at com.mongodb.internal.connection.SocketStreamHelper.initialize(SocketStreamHelper.java:64) ~[mongodb-driver-core-3.8.2.jar!/:na]
spring_boot_mongo_1  |  at com.mongodb.internal.connection.SocketStream.open(SocketStream.java:62) ~[mongodb-driver-core-3.8.2.jar!/:na]
spring_boot_mongo_1  |  ... 3 common frames omitted
spring_boot_mongo_1  |

This is what I see when i run docker ps:

CONTAINER ID        IMAGE                                          COMMAND                  CREATED             STATUS              PORTS                      NAMES
4da4948d04d9        spring-boot-mongodb-master_spring_boot_mongo   "java -jar /app.jar"     11 seconds ago      Up 10 seconds       0.0.0.0:8080->8080/tcp     spring-boot-mongodb-master_spring_boot_mongo_1
e9a79f3ba8ab        mongo                                          "docker-entrypoint.s…"   12 seconds ago      Up 10 seconds       0.0.0.0:27017->27017/tcp   spring-boot-mongodb-master_mongo_1

This means the mongo mapping works as expected(I see the same o/p when i start mongodb container with the above mentioned docker run command), but the application port mapping was not achieved. Can someone please help me??

Thanks!

user1318369
  • 715
  • 5
  • 15
  • 34

1 Answers1

4

Services from the same docker-compose are connected to same default network. You should use service name in your url when you want to access another container. Container name will be resolved to container IP automatically. You cannot access another container by using localhost - use service name instead. In your case you can set environment variable for your spring_boot_mongo service :

spring_boot_mongo:
    build: .
    ports:
      - "8080:8080"
    environment:
      - SPRING_DATA_MONGODB_.HOST=mongo

if you are using spring data mongo. Otherwise set the environment variable to override your uri in your application container.

Michał Krzywański
  • 15,659
  • 4
  • 36
  • 63
  • Thanks a lot, setting the environment variable fixed the issue(SPRING_DATA_MONGODB_.HOST=mongo). To clarify my understanding, does this mean we are setting the host of spring data mongodo to the host created by the "mongo" container in this case(something similar to the response mentioned in this post: https://stackoverflow.com/questions/37226311/how-can-i-change-define-default-database-of-mongodb-in-spring-data). Also for your second suggestion: set the environment variable to override your uri in your application container - how do I do that? Can you please elaborate? – user1318369 Jun 13 '20 at 00:06
  • 1. You are right, your app will need to connect to the mongo container created by your mongo service - that is why you changed it. 2. You have already overriden the mongo host by setting the environment variable and it was picked by spring. I was not sure how you configure your mongodb connection (uri property or host/port properties) that is why I suggested it. – Michał Krzywański Jun 13 '20 at 07:34