With the advent of Docker 20.10
, host-gateway
is supposed to be available on Linux platforms (as detailed in this wonderful answer). As such, it should be possible to create a docker-compose
script which is platform agnostic. (I myself am on Debian.)
Here are some links to some questions and answers that were helpful in getting me this far: here, here, and here (along with some of the other answers and comments)
I’m trying to create a script for running The Graph, which involves having ipfs
and postgres
running inside a Docker container, and connecting to an instance of a blockchain outside of Docker (on port 8545). Here is the script:
version: '3'
services:
graph-node:
extra_hosts:
- "host.docker.internal:host-gateway"
image: graphprotocol/graph-node
ports:
- '8000:8000'
- '8001:8001'
- '8020:8020'
- '8030:8030'
- '8040:8040'
depends_on:
- ipfs
- postgres
environment:
postgres_host: postgres
postgres_user: graph-node
postgres_pass: let-me-in
postgres_db: graph-node
ipfs: 'ipfs:5001'
ethereum: 'localhost:http://host.docker.internal:8545'
RUST_LOG: info
ipfs:
image: ipfs/go-ipfs:v0.4.23
ports:
- '5001:5001'
volumes:
- ./data/ipfs:/data/ipfs
postgres:
image: postgres
ports:
- '5432:5432'
command: ["postgres", "-cshared_preload_libraries=pg_stat_statements"]
environment:
POSTGRES_USER: graph-node
POSTGRES_PASSWORD: let-me-in
POSTGRES_DB: graph-node
volumes:
- ./data/postgres:/var/lib/postgresql/data
Docker starts just fine, and the instances of ipfs
, postgres
, and the graph-node
all start up fine, but then the graph-node
‘s RPC calls (to the blockchain) all fail with errors similar to the following:
WARN Trying again after eth_getBlockByNumber(0, false) RPC call failed (attempt #18) with result Err(Transport error: Error(Connect, Os { code: 111, kind: ConnectionRefused, message: "Connection refused" }))
Am I using extra-hosts
wrong? What might I be able to do to make this script work both on my Linux machine, but also for Mac and Windows users?
Thanks!
2
Answers
It is possible that the application running on your host is bound to a different interface than the one used by Docker.
You can check with
netstat
:If it is listening on
127.0.0.1
, like in this example, this means it can only be accessed via the loopback interface.The solution is to find out what IP address host-gateway points to and make sure the service binds to that IP address instead of 127.0.0.1.
If it’s no problem when the service is available on all interfaces (including for example your wifi network), you can bind to
0.0.0.0
to make it available on all interfaces.If the host system is Linux, it is possible that your host firewall rules are being applied to communication between your containers. You can check whether that is the case with
sysctl
, it would return1
for the following settings:You can fix this behavior by setting these values to ‘0’: