Problem with nginx reverse proxy and docker. Only one proxy_path is working - docker

I am completly lost.. So i have two proxy_paths in my nginx conf: '/' and '/api'. '/' redirects to my frontend and is working perfectly but the '/api' proxy path is not working at all. The proxy server is logging requests to '/api/' but not forwarding them to my actual api-server. I'm missing something. Is the '/' proxy_path some sort of catch all that overrides any other proxy paths? Any assistance would be invaluable! Thanks! Here are my configs:
nginx reverse proxy conf:
server {
listen 80;
server_name proxy;
location / {
proxy_pass http://frontend_prod:3000/;
}
location /api {
proxy_pass http://api_prod:3333/;
}
}
docker-compose:
version: '3.1'
services:
proxy:
build: ./proxy/
ports:
- '9000:80'
restart: always
depends_on:
- frontend_prod
- api_prod
frontend_prod:
build: ./frontend/nginx/
ports:
- '3000'
depends_on:
- api_prod
restart: always
db:
image: mariadb
restart: always
environment:
MYSQL_ROOT_PASSWORD: hunter2
api_prod:
build: ./backend/api/
command: npm run production
ports:
- '3333'
depends_on:
- db

Related

Nginx and Docker with static html: Proxy pass does not forward to expected route

I want to serve static html as a service with Docker and nginx as a reverse proxy (there are also a python backend and mysql container, which I excluded here)
I have got the following docker-compose file:
version: "3.7"
frontend:
build: ./frontend
container_name: frontend
restart: always
ports:
- "5000:80"
nginx:
build: ./nginx
container_name: nginx
restart: always
ports:
- "80:80"
Dockerfile for Frontend:
FROM nginx:alpine
COPY . /usr/share/nginx/html
nginx.conf in my I do this:
server {
listen 80;
location /frontend {
proxy_pass http://frontend:5000/;
#proxy_pass http://frontend:5000; -> also tried this
}
}
Everything builds fine, but the proxy_pass does not work as expected.
Where I can reach my app:
http://localhost:5000/
Desired:
http://localhost/frontend
What did I do wrong?
The NGINX location should be the root (I imagine there is no /frontend web path)
location / {
proxy_pass http://frontend:5000/;
}

simple nginx reverse proxy not working in docker compose

fhsmgr proxy works at / but not any other location with 404
fhsdir proxy gives 404 at /dir, though when i browse directly to it on localhost:5000 i get the expected output, so the host is up and running. also, nginx does not complain about invalid host and exit like i've seen it do before.
i have tried trailing '/' so '/dir/' to no avail.
i have tried putting fhsmgr at '/mgr' and i get the expected 404 at index '/' but then 404 again at '/mgr'.
i have tried without proxy_redirect off; as well.
i have removed the upstream statements and just directly put in container names
seemingly the only thing it'll let me proxy is at '/', though i know i've proxied to other servers at different location paths in setups like this before.
-- docker compose
version: "3.7"
services:
fhsmgr:
build: fhsmgr
restart: always
fhsdir:
build: fhsdir
restart: always
ports:
- 5000:5000
nginx:
build: nginx
restart: always
ports:
- 80:80
environment:
- NGINX_ENVSUBST_OUTPUT_DIR=/etc/nginx
- FHSMGR_HOST=fhsmgr
- FHSMGR_PORT=5000
- FHSDIR_HOST=fhsdir
- FHSDIR_PORT=5000
-- nginx conf
events {}
http {
# upstream fhsmgr {
# server ${FHSMGR_HOST}:${FHSMGR_PORT};
# }
# upstream fhsdir {
# server ${FHSDIR_HOST}:${FHSDIR_PORT};
# }
# a simple reverse-proxy
server {
listen 80 default_server;
location / {
proxy_pass http://fhsmgr:5000;
proxy_redirect off;
}
location /dir {
proxy_pass http://fhsdir:5000;
proxy_redirect off;
}
}
}
i am modifying this project https://github.com/AwsGeek/lightsail-containers-nginx to get it to work for my use case. Haven't gotten to lightsail, just using docker compose locally
You miss the container_name in your docker-compose,try this
version: "3.7"
services:
fhsmgr:
build: fhsmgr
restart: always
container_name: fhsmgr # allow other containers to access by container_name
fhsdir:
build: fhsdir
restart: always
container_name: fhsdir
ports:
- 5000:5000
nginx:
build: nginx
restart: always
ports:
- 80:80
environment:
- NGINX_ENVSUBST_OUTPUT_DIR=/etc/nginx
- FHSMGR_HOST=fhsmgr
- FHSMGR_PORT=5000
- FHSDIR_HOST=fhsdir
- FHSDIR_PORT=5000

How to connect two docker containers together

I have a reactjs front end application and a simple python flask. And I am using a docker-compose.yml to spin up both the containers, and it is like this:
version: "3.2"
services:
frontend:
build: .
environment:
CHOKIDAR_USEPOLLING: "true"
ports:
- 80:80
links:
- "backend:backend"
depends_on:
- backend
backend:
build: ./api
# volumes:
# - ./api:/usr/src/app
environment:
# CHOKIDAR_USEPOLLING: "true"
FLASK_APP: /usr/src/app/server.py
FLASK_DEBUG: 1
ports:
- 8083:8083
I have used links so the frontend service can talk to backend service using axios as below:
axio.get("http://backend:8083/monitors").then(res => {
this.setState({
status: res.data
});
});
I used docker-compose up --build -d to build and start the two containers and they are started without any issue and running fine.
But now the frontend cannot talk to backend.
I am using an AWS ec2 instance. When the page loads, I tried to see the for any console errors and I get this error:
VM167:1 GET http://backend:8083/monitors net::ERR_NAME_NOT_RESOLVED
Can someone please help me?
The backend service is up and running.
You can use a nginx as reverse proxy for both
The compose file
version: "3.2"
services:
frontend:
build: .
environment:
CHOKIDAR_USEPOLLING: "true"
depends_on:
- backend
backend:
build: ./api
# volumes:
# - ./api:/usr/src/app
environment:
# CHOKIDAR_USEPOLLING: "true"
FLASK_APP: /usr/src/app/server.py
FLASK_DEBUG: 1
proxy:
image: nginx
volumes:
- ./nginx.conf:/etc/nginx/conf.d/example.conf
ports:
- 80:80
minimal nginx config (nginx.conf):
server {
server_name example.com;
server_tokens off;
location / {
proxy_pass http://frontend:80;
}
}
server {
server_name api.example.com;
server_tokens off;
location / {
proxy_pass http://backend:8083;
}
}
The request hits the nginx container and is routed according the domain to the right container.
To use example.com and api.example.com you need to edit your hosts file:
Linux: /etc/hosts
Windows: c:\windows\system32\drivers\etc\hosts
Mac: /private/etc/hosts
127.0.0.1 example.com api.example.com

Error 502 accessing nextcloud via docker with nginx

Heyo!
Update: I figured it out and added my answer.
I'm currently in the process of learning docker and I've written a docker-compose file that should launch nginx, gitea, nextcloud and route them all via domain name as a reverse proxy.
All is going well except for with nextcloud. I can access it via localhost:3001 but not via the nginx reverse proxy. All is well with gitea, it works both ways.
The error I'm getting is:
nginx_proxy | 2018/08/10 00:17:34 [error] 8#8: *1 connect() failed (111: Connection refused) while connecting to upstream, client: 172.19.0.1, server: cloud.example.ca, request: "GET / HTTP/1.1", upstream: "http://172.19.0.4:3001/", host: "cloud.example.ca"
docker-compose.yml:
version: '3.1'
services:
nginx:
container_name: nginx_proxy
image: nginx:latest
restart: always
volumes:
// Here I'm swapping out my default.conf for the container's by mounting my
directory over theirs.
- ./nginx-conf:/etc/nginx/conf.d
ports:
- 80:80
- 443:443
networks:
- proxy
nextcloud_db:
container_name: nextcloud_db
image: mariadb:latest
restart: always
volumes:
- nextcloud_db:/var/lib/mysql
environment:
MYSQL_ROOT_PASSWORD_FILE: /run/secrets/cloud_db_root
MYSQL_PASSWORD_FILE: /run/secrets/cloud_db_pass
MYSQL_DATABASE: devcloud
MYSQL_USER: devcloud
secrets:
- cloud_db_root
- cloud_db_pass
networks:
- database
gitea_db:
container_name: gitea_db
image: mariadb:latest
restart: always
volumes:
- gitea_db:/var/lib/mysql
environment:
MYSQL_ROOT_PASSWORD_FILE: /run/secrets/cloud_db_root
MYSQL_PASSWORD_FILE: /run/secrets/cloud_db_pass
MYSQL_DATABASE: gitea
MYSQL_USER: gitea
secrets:
- cloud_db_root
- cloud_db_pass
networks:
- database
nextcloud:
image: nextcloud
container_name: nextcloud
ports:
- 3001:80
volumes:
- nextcloud:/var/www/html
restart: always
networks:
- proxy
- database
gitea:
container_name: gitea
image: gitea/gitea:latest
environment:
- USER_UID=1000
- USER_GID=1000
restart: always
volumes:
- gitea:/data
ports:
- 3000:3000
- 22:22
networks:
- proxy
- database
volumes:
nextcloud:
nextcloud_db:
gitea:
gitea_db:
networks:
proxy:
database:
secrets:
cloud_db_pass:
file: cloud_db_pass.txt
cloud_db_root:
file: cloud_db_root.txt
My default.conf that gets mounted into /etc/nginx/conf.d/default.conf
upstream nextcloud {
server nextcloud:3001;
}
upstream gitea {
server gitea:3000;
}
server {
listen 80;
listen [::]:80;
server_name cloud.example.ca;
location / {
proxy_pass http://nextcloud;
}
}
server {
listen 80;
listen [::]:80;
server_name git.example.ca;
location / {
proxy_pass http://gitea;
}
}
I of course have my hosts file setup to route the domains to localhost. I've done a bit of googling but nothing I've found so far seems to align with what I'm running into. Thanks in advance!
Long story short, one does not simply reverse proxy to port 80 with nextcloud. It's just not allowed. I have it deployed and working great with a certificate over 443! :)

Traefik with nginx container

I spend so much time on it and I didn't found any solution.
I already setup Traefik and the nginx container, here is my docker-compose.yml
version: '3'
networks:
proxy:
external: true
internal:
external: false
services:
mysql:
image: 'mysql:5.7'
environment:
MYSQL_ROOT_PASSWORD: null
networks:
- internal
labels:
- traefik.enable=false
adminer:
image: 'adminer:latest'
labels:
- traefik.backend=adminer
- 'traefik.frontend.rule=Host:db-admin.xxxx.xyz'
- traefik.docker.network=proxy
- traefik.port=8080
networks:
- internal
- proxy
depends_on:
- mysql
portainer:
image: portainer/portainer
networks:
- internal
- proxy
labels:
- "traefik.frontend.rule=Host:portainer.xxxx.xyz"
- "traefik.port=9000"
- "traefik.backend=portainer"
- traefik.docker.network=proxy
volumes:
- "/var/run/docker.sock:/var/run/docker.sock"
restart: unless-stopped
Nginx-Pro:
image: nginx:latest
container_name: Nginx-Pro
labels:
- traefik.backend=Nginx-Pro
- traefik.frontend.rule=Host:new.xxxx.fr
- traefik.docker.network=proxy
- "traefik.port=80"
- "traefix.port=443"
- "traefik.frontend.entryPoints=http"
networks:
- internal
- proxy
depends_on:
- mysql
volumes:
- /var/www/nginx-pro/:/var/www/
- /etc/nginx/nginx-pro/:/etc/nginx
So I also setup vhost on the server in /etc/nginx/sites-enabled
I also add log to traefik conf but nothing is appening.
Here is my vhost config :
server {
listen *:80;
root /var/www/new.xxx.fr;
# Add index.php to the list if you are using PHP
index index.php index.html index.htm index.nginx-debian.html;
server_name new.xxx.fr www.new.xxx.fr;
location / {
# First attempt to serve request as file, then
# as directory, then fall back to displaying a 404.
try_files $uri $uri/ /index.php?$args;
}
location ~ /\.ht {
deny all;
}
}
And the problem is that i always have Bad Gateway message from Traefik.
You need to add traefik.frontend.passHostHeader so nginx can match the Host header with the server_name.
But as this nginx is only for the one domain you match already with traefik.frontend.rule=Host:new.xxxx.fr you can also leave the server_name out of the nginx vhost config and use the default config.
Also remove "traefix.port=443" as you only use http between traefik and nginx, what you want is "traefik.frontend.entryPoints=http,https", you can also add "traefik.frontend.headers.SSLRedirect=true" to always redirect http to https.

Resources