How do I get my docker container running gunicorn / FastAPI server to respond to outside traffic?
This is how my container runs
docker run --detach --net host -v "/path/to/app/app":"/app" -it me/app:appfastapi_latest /start.sh
cat start.sh
#! /usr/bin/env sh
set -e
# Start Gunicorn
exec gunicorn -k "uvicorn.workers.UvicornWorker" -c /app/gunicorn_conf.py "main:app"
cat ./app/gunicorn_conf.py
...
host = "0.0.0.0"
port = "8000"
bind = f"{host}:{port}"
...
docker logs container_id
...
[2022-02-15 05:40:10 +0000] [1] [INFO] Listening at: http://127.0.0.1:8000 (1)
^^^ this was before a fix in the conf, now its
0.0.0.0:8000
...
Curl container from host
curl localhost:8000/hw {"message":"Hello World"}
This is how it should be. But when I do
curl domain:8000/hw
curl: (7) Failed to connect to domain port 8000: Connection refused
I do not know how to troubleshoot this. In the FastAPI main I have
ORIGINS = [
"http://127.0.0.1:8000",
"http://localhost:8000",
"http://domain:8000",
]
app = FastAPI(title="MY API", root_path=ROOT_PATH, docs_url="/")
app.add_middleware(
CORSMiddleware,
allow_origins=ORIGINS,
allow_credentials=True,
allow_methods=["*"],
allow_headers=["*"],
)
and I have the firewall open (I believe)
sudo iptables -L
Chain INPUT (policy ACCEPT)
target prot opt source destination
ACCEPT tcp -- 172.17.0.2 anywhere tcp dpt:mysql
ACCEPT tcp -- anywhere anywhere tcp dpt:8000
Chain FORWARD (policy DROP)
target prot opt source destination
DOCKER-USER all -- anywhere anywhere
DOCKER-ISOLATION-STAGE-1 all -- anywhere anywhere
ACCEPT all -- anywhere anywhere ctstate RELATED,ESTABLISHED
DOCKER all -- anywhere anywhere
ACCEPT all -- anywhere anywhere
ACCEPT all -- anywhere anywhere
Chain OUTPUT (policy ACCEPT) target prot opt source destination Chain DOCKER (1 references) target prot opt source destination Chain DOCKER-ISOLATION-STAGE-1 (1 references) target prot opt source destination DOCKER-ISOLATION-STAGE-2 all -- anywhere anywhere RETURN all -- anywhere anywhere Chain DOCKER-ISOLATION-STAGE-2 (1 references) target prot opt source destination DROP all -- anywhere anywhere RETURN all -- anywhere anywhere
that I have opened for port 8000
with
sudo iptables -A INPUT -p tcp --dport 8000 -j ACCEPT
The system I am on is Debian9,
docker --version
Docker version 19.03.15, build 99e3ed8919
Listening at: http://127.0.0.1:8000
means that gunicorn listening localhost
of docker container. Container's localhost is not accessible from external network. You should set 0.0.0.0:8000
to be able access from outside.
Yes, you tried to set
host = "0.0.0.0"
port = "8000"
But gunicorn config file doesn't have host
and port
parameters. You should use bind = '0.0.0.0:8000'
instead.
And don't forget to publish port -p 8000:8000
when run container