Alex
Alex

Reputation: 5227

Docker containers are not able to see each other in docker compose, nor is host

There are couple of issues that I have encountered while working with Docker.

  1. Host (Windows 10) is not able to access any resources hosted by containers.
  2. Containers themselves are also not seeing each other.

My config:

version: '3.7'
services:
  chrome:
    build: ./chrome
    container_name: chrome_container
    ports:
      - "9223:9223"

  dotnetapp:
    depends_on:
       - chrome
    build: ./dotnetapp
    container_name: live_container
    environment:
      - ASPNETCORE_ENVIRONMENT=Production
    stdin_open: true
    tty: true

Dockerfile for chrome (all it does - starts Chrome with debugging, enabled on port 9223):

FROM debian:buster-slim

# preparation
RUN apt-get update; apt-get clean
RUN apt-get install -y wget
RUN apt-get install -y gnupg2

# installing xvfb
RUN apt-get install -y xvfb

# installing Chrome
RUN wget -q -O - https://dl.google.com/linux/linux_signing_key.pub | apt-key add -
RUN sh -c 'echo "deb http://dl.google.com/linux/chrome/deb/ stable main" >> /etc/apt/sources.list.d/google.list'
RUN apt-get update && apt-get install -y google-chrome-beta

EXPOSE 9223

COPY ./docker-entrypoint.sh /usr/local/bin/
RUN ln -s usr/local/bin/docker-entrypoint.sh / # backwards compat
ENTRYPOINT ["docker-entrypoint.sh"]
CMD ["test"]

docker-entrypoint.sh

#!/bin/bash
set -e

if [ "$1" = 'test' ]; then
    rm -f /tmp/.X99-lock
fi

xvfb-run -e /dev/stdout --server-args='-screen 0, 2560x1440x16' google-chrome --window-size=2560,1440 --no-sandbox --remote-debugging-port=9223 --user-data-dir=remote-profile https://www.google.com/

Dockerfile for second app (is used just for docker internal network testing)

FROM mcr.microsoft.com/dotnet/core/runtime:2.2

# run app
CMD ["/bin/bash"]

So, now, to elaborate on point 1:

I can launch chrome container by running: docker-compose up --build chrome.

On host system I then try to open a browser either localhost:9223 or http://172.17.0.2:9223/ and in both cases I get "page could not be reached error". P.s. I got IP from docker inspect command.

enter image description here

On the other hand, if I try to go into running container docker exec -it chrome_container bash and execute command curl localhost:9223 then it shows a SUCCESS result.

enter image description here

At this point if I try using other address like curl chrome:9223 or curl http://chrome:9223 orcurl chrome_container:9223 or curl http://chrome_container:9223 then they also FAIL. According to documentation - all containers within internal network shall be accessible by the service host name. This is simply false in my scenario.

I also tried starting the image without relying on docker compose like this docker run -p 9223:9223 -it --rm all_chrome but the result is the same. The resource is not available from within host system.

Now, to elaborate on issue 2.

When I run both applications like this docker-compose up. And log-into second app by docker exec -it live_container bash. And then try to access first container using above mentioned URLS - all of them fail (curl localhost:9223 or curl 0.0.0.0:9223 or curl chrome:9223 or curl http://chrome:9223 orcurl chrome_container:9223 or curl http://chrome_container:9223).

I tried restarting Docker a couple of times and tried different ports. How can I figure out these things?

  1. How to access resource at 9223 port at Host system?

  2. Why isn't the second service able to see the first service using the host name, as documented here?

I am using Docker on Windows 10.

enter image description here

EDIT: More details.

enter image description here

enter image description here

So it seems like something is happening when accessing by localhost on a Host system (win 10).

Upvotes: 1

Views: 2673

Answers (1)

Alex
Alex

Reputation: 5227

Just found the information in a topic, that Chrome simply does not accept connections from outside of localhost network while in debug mode.

So, starting the container as:

docker run -p 5656:5656 -it --rm all_chrome

And then to solve the issue I have to use a proxy. Here is an example:

socat tcp-listen:5656,fork tcp:localhost:9223

After that - accessing through localhost works fine:

enter image description here

I am yet to figure out how to start socat in daemon mode so I can make it a part of startup script in docker.. but that's a minor thing.

Edit. Couple of notes.

Accessing Chrome container from another container

If you tried to access the debug session from another container using the IP, then that would work just fine:

curl 172.19.0.2:5656

Otherwise, if you tried to use a host name - you would see an error.

curl chrome:5656

error:

Host header is specified and is not an IP address or localhost.root@38f2b5fa34ca:/app# curl chrome:5656

This can be sovled, by stripping down Host header value:

curl chrome:5656 -H 'Host: '

The problem, still, is that this is not very convenient approach. Because application do not always have the possibility to remove the header from the request. For exampe - a chromedriver. Therefore, a solution would be to make a configuration on chrome docker container, that would remove Host header value for all incoming requests.. I tried doing it using squid proxy, but without success.. So, instead, I came up with another solution.

The solution is to use a static, fixed IP address for containers' internal network.. In that way - you can always be sure that docker will be using the same address and therefore, your application can use it in their calls.

The config is following:

version: '3.7'
services:
  chrome:
    networks:
        front:
            ipv4_address: 172.16.238.5 
  app2:
    networks:
        front:
            ipv4_address: 172.16.238.10 
networks:
  front:
    driver: bridge
    ipam:
     config:
       - subnet: 172.16.238.0/24

Now in app2 you can make calls using the fixed IP:

CURL 172.16.238.5:5656

This is so far the easiest solution..

p.s. If you are running chrome in headless mode, then you can provide additional argument which in theory will solve some of your problems --remote-debugging-address. Try it.

Upvotes: 3

Related Questions