nginx reverse proxy configuration for docker - docker

I am having hard time figuring out configuration to load locally running dockerised web app in the domain.
Below are:
docker-compose.yml
version: "3"
services:
ui:
build: ./ui
volumes:
- ./ui:/app/sr
container_name: ui
ports:
- "4200:4200"
networks:
- webnet
links:
- api
api:
build: ./api
ports:
- "0.0.0.0:5000:5000"
volumes:
- ./api:/app
container_name: api
networks:
- webnet
networks:
webnet:
nginx/conf.d/ui.example.conf
server {
listen 80;
#listen [::]:80;
server_name ui.example.de www.ui.example.de;
location / {
proxy_pass http://ui:4200/;
#proxy_buffering off;
#proxy_set_header X-Real-IP $remote_addr;
}
}
nginx.conf
user www-data;
worker_processes auto;
pid /run/nginx.pid;
include /etc/nginx/modules-enabled/*.conf;
events {
worker_connections 768;
# multi_accept on;
}
http {
include /etc/nginx/mime.types;
default_type application/octet-stream;
log_format main '$remote_addr - $remote_user [$time_local] "$request" '
'$status $body_bytes_sent "$http_referer" '
'"$http_user_agent" "$http_x_forwarded_for"';
access_log /var/log/nginx/access.log main;
sendfile on;
#tcp_nopush on;
keepalive_timeout 65;
#gzip on;
include /etc/nginx/conf.d/*.conf;
}
#mail {
# # See sample authentication script at:
# # http://wiki.nginx.org/ImapAuthenticateWithApachePhpScript
#
# # auth_http localhost/auth.php;
# # pop3_capabilities "TOP" "USER";
# # imap_capabilities "IMAP4rev1" "UIDPLUS";
#
# server {
# listen localhost:110;
# protocol pop3;
# proxy on;
# }
#
# server {
# listen localhost:143;
# protocol imap;
# proxy on;
# }
#}
It runs on local machine under the ip
http://138.246.XXX.XX:4200 as well as in http://138.246.XXX.XX
But when I try to access through the web with http://ui.example.com, it gives Error 503.
I also tried with ip from docker network and my machine ip i.e. http://138.246.XXX.XX:4200 in proxy pass in ui.example.conf.
[NOTE]: I removed default from nginx/sites_enabled. Now that is empty as I am only trying for reverse proxy with nginx.
Does anyone have any idea, what am I missing here?

Try ELB health checker status by connecting container

Related

Next.js Hot Module Remplacement issue in SSH,

I'm currently working on a Next.js project from an SSH connection (I need to work in SSH because of cookie issues with my the api requests).
I also use Docker to build an image for react and a web service because I'm using a nginx server. So when I enable my services, the app loads, I got access to the app, and when I make a change, it works. BUT I have to reload the browser tab to see the change. Apparently my web service don't like the hmr of webpack, I got this log from it :
web_1 | 192.168.10.1 - - [25/Mar/2022:08:45:03 +0000] "GET /_next/webpack-hmr HTTP/1.1" 404 936 "-" "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/99.0.4844.82 Safari/537.36"
Here is my docker-compose.yml:
version: '3'
services:
web:
networks:
- webgateway
- default
build: ./docker/web
depends_on:
- react
volumes:
- $PWD/docker/web/etc/nginx.conf:/etc/nginx/nginx.conf
- $PWD/docker/web/etc/default.conf:/etc/nginx/conf.d/default.conf
labels:
traefik.enable: true
traefik.http.routers.test.tls: false
react:
networks:
- default
build: ./frontend
environment:
HOST_LOCAL: $HOST_LOCAL
COMPOSE_PROJECT_NAME: $COMPOSE_PROJECT_NAME
env_file:
- .local
volumes:
- ./frontend:/opt/services/react
networks:
webgateway:
external: true
Here is my conf for my service web:
docker/web/Dockerfile :
FROM nginx:1.13-alpine
RUN apk update && apk add bash
docker/web/etc/default.conf :
upstream app {
server react:3000;
}
server {
listen 80;
charset utf-8;
client_max_body_size 20M;
error_log /var/log/nginx/error.log;
access_log /var/log/nginx/access.log;
location / {
# checks for static file, if not found proxy to app
try_files $uri #proxy_to_app;
}
location /api/v {
# checks for static file, if not found proxy to app
try_files $uri #proxy_to_api;
}
location #proxy_to_app {
proxy_connect_timeout 600s;
proxy_read_timeout 600s;
proxy_send_timeout 600s;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header Host $http_host;
proxy_redirect off;
proxy_pass http://app;
}
}
docker/web/etc/default.conf :
user root;
worker_processes 1;
error_log /var/log/nginx/error.log warn;
pid /var/run/nginx.pid;
events {
worker_connections 1024;
}
http {
include /etc/nginx/mime.types;
default_type application/octet-stream;
log_format main '$remote_addr - $remote_user [$time_local] "$request" '
'$status $body_bytes_sent "$http_referer" '
'"$http_user_agent" "$http_x_forwarded_for"';
access_log /var/log/nginx/access.log main;
sendfile on;
#tcp_nopush on;
keepalive_timeout 65;
#gzip on;
include /etc/nginx/conf.d/*.conf;
}
Thanks for your time in advance.
I've figured it out, it's a next/webpack_hmr configuration issue, nothing to do with docker or ngnix config...
Using a middleware for refreshing the modules fixed my issue.

Connect two wordpress containers with same NGINX docker

I use nginx in a docker to connect my two wordpress websites, which are dockerized too.
I can set up one website with the following settings:
In docker-compose.yml
nginx:
image: nginx:alpine
volumes:
- ./web_ndnb_prod/src:/var/www/html
- ./nginx/conf.d:/etc/nginx/conf.d:ro
depends_on:
- web_ndnb_test
- web_ndnb_prod
In my NGINX conf file located in /nginx/conf.d
server {
[...]
root /var/www/html/;
[...]
}
However to add a 2nd website, I try to change the root and the websites return a 404
In docker-compose.yml
nginx:
image: nginx:alpine
volumes:
- ./web_ndnb_prod/src:/var/www/web_ndnb_prod
- ./web_ndnb_test/src:/var/www/web_ndnb_test
- ./nginx/conf.d:/etc/nginx/conf.d:ro
depends_on:
- web_ndnb_test
- web_ndnb_prod
In one of the 2 NGINX conf files
server {
[...]
root /var/www/web_ndnb_prod/;
[...]
}
If I execute
sudo docker exec -ti nginx ls /var/www/web_ndnb_prod
It outputs the wordpress files correctly
Why does Nginx not find them?
Edit 1
The main nginx.conf file is
worker_processes auto;
error_log /var/log/nginx/error.log warn;
pid /var/run/nginx.pid;
events {
worker_connections 1024;
}
http {
include /etc/nginx/mime.types;
default_type application/octet-stream;
log_format main '$remote_addr - $remote_user [$time_local] "$request" '
'$status $body_bytes_sent "$http_referer" '
'"$http_user_agent" "$http_x_forwarded_for"';
access_log /var/log/nginx/access.log main;
sendfile on;
#tcp_nopush on;
keepalive_timeout 65;
#gzip on;
include /etc/nginx/conf.d/*.conf;
}

Can't connect from one docker container to another by its public domain name

I have an application composed of containerized web-services deployed with docker-compose (it's a test env). One of the containers is nginx that operates as a reverse proxy for services and also serves static files. A public domain name points to the host machine and nginx has a server section that utilizes it.
The problem I am facing is that I can't talk to nginx by that public domain name from the containers launched on this same machine - connection always timeouts. (For example, I tried doing a curl https://<mypublicdomain>.com)
Referring by the containers name (using docker's hostnames) works just fine. Reuqests to the same domain name from other machines also work ok.
I understand this has to do with how docker does networking, but fail to find any docs that would outline what exactly goes wrong here. Could anyone explain the root of the issue to me or maybe just point in the right direction?
(For extra context: originally I was going to use this to set up monitoring with prometheus and blackbox exporter to make it see the server the same way anyone from the outside would do + to automatically check that SSL is working. For now I pulled back to point the prober to nginx by its docker hostname)
Nginx image
FROM nginx:stable
COPY ./nginx.conf /etc/nginx/nginx.conf.template
COPY ./docker-entrypoint.sh /docker-entrypoint.sh
COPY ./dhparam/dhparam-2048.pem /dhparam-2048.pem
COPY ./index.html /var/www/index.html
ENTRYPOINT ["/docker-entrypoint.sh"]
CMD ["nginx", "-g", "daemon off;"]
docker-compose.yaml
version: "3"
networks:
mainnet:
driver: bridge
services:
my-gateway:
container_name: my-gateway
image: aturok/manuwor_gateway:latest
restart: always
networks:
- mainnet
ports:
- 80:80
- 443:443
expose:
- "443"
volumes:
- /var/stuff:/var/www
- /var/certs:/certsdir
command: "/bin/sh -c 'while :; do sleep 6h & wait $${!}; nginx -s reload; done & nginx -g \"daemon off;\"'"
(I show only the nginx service, as others are irrelevant - I would for example spin up a nettools container and not connect it to the mainnet network - still expect the requests to reach nginx, since I am using the public domain name. The problem also happens with the containers connected to the same network)
nginx.conf (normally it comes with a bunch of env vars, replaced + removed irrelevant backend)
user nginx;
worker_processes 1;
error_log /var/log/nginx/error.log warn;
pid /var/run/nginx.pid;
events {
worker_connections 1024;
}
http {
include /etc/nginx/mime.types;
default_type application/octet-stream;
log_format main '$remote_addr - $remote_user [$time_local] "$request" '
'$status $body_bytes_sent "$http_referer" '
'"$http_user_agent" "$http_x_forwarded_for"';
access_log /var/log/nginx/access.log main;
sendfile on;
#tcp_nopush on;
keepalive_timeout 65;
#gzip on;
#include /etc/nginx/conf.d/*.conf;
server {
listen 80;
server_name mydomain.com;
location /.well-known/acme-challenge/ {
root /var/www/certbot;
}
location / {
return 301 https://$host$request_uri;
}
}
server {
listen 443 ssl;
server_name mydomain.com;
ssl_certificate /certsdir/fullchain.pem;
ssl_certificate_key /certsdir/privkey.pem;
server_tokens off;
ssl_buffer_size 8k;
ssl_dhparam /dhparam-2048.pem;
ssl_protocols TLSv1.2 TLSv1.1 TLSv1;
ssl_prefer_server_ciphers on;
ssl_ciphers ECDH+AESGCM:ECDH+AES256:ECDH+AES128:DH+3DES:!ADH:!AECDH:!MD5;
ssl_ecdh_curve secp384r1;
ssl_session_tickets off;
ssl_stapling on;
ssl_stapling_verify on;
resolver 8.8.8.8;
root /var/www/;
index index.html;
location / {
root /var/www;
try_files $uri /index.html;
}
error_page 500 502 503 504 /50x.html;
location = /50x.html {
root html;
}
}
}
Note: certificates are ok when I access the server from elsewhere

Passing environment variables from Docker to Nginx configuration files not working

I am really stumped and can use help figuring out why my environment variables aren't transferring from Docker to nginx config files.
I have a docker-compose.yml
nginx:
image: nginx
container_name: proxier
volumes:
- ./conf/nginx.conf:/etc/nginx/nginx.conf
- ./conf/server.nginx.conf.tpl:/etc/nginx/server.nginx.conf.tpl
- ./build/web:/srv/static:ro
- ./docker/proxier:/tmp/docker
ports:
- "80:80"
- "443:443"
environment:
- HOST_EXTERNAL_IP=localhost
- DEVSERVER_PORT=8000
- DEVSERVICE_PORT=5000
command: /bin/bash -c "env && envsubst '$$HOST_EXTERNAL_IP $$DEVSERVER_PORT $$DEVSERVICE_PORT' < /etc/nginx/server.nginx.conf.tpl > /etc/nginx/conf.d/default.conf && nginx -g 'daemon off;'"
I have an nginx.conf file
user nginx;
worker_processes 1;
error_log /dev/stdout warn;
pid /var/run/nginx.pid;
events {
worker_connections 1024;
http {
include /etc/nginx/mime.types;
default_type application/octet-stream;
client_max_body_size 100g;
log_format main '$remote_addr - $remote_user [$time_local] "$request" '
'$status $body_bytes_sent "$http_referer" '
'"$http_user_agent" "$http_x_forwarded_for"';
access_log /dev/stdout main;
sendfile off;
tcp_nopush on;
keepalive_timeout 65;
gzip on;
server_tokens off;
upstream app {
server myapp:8000 fail_timeout=0;
}
include /etc/nginx/server.nginx.conf.tpl;
}
I have a server.nginx.conf.tpl file
server {
listen 80;
listen 443 ssl http2 default_server;
server_name localhost;
index index.html;
location ^~ /services/ {
proxy_pass https://myurl.com;
proxy_set_header USER_DN $ssl_client_s_dn;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
}
location / {
proxy_http_version 1.1;
proxy_set_header Connection "keep-alive";
proxy_pass http://${HOST_EXTERNAL_IP}:${DEVSERVER_PORT}; # Won't read environment variables here
}
}
When I run this however, I get the error
nginx: [emerg] unknown "host_external_ip" variable I am using envsubst correctly to pass the environment variable from docker per the docs
Do not copy nginx.conf directly. Instead create a shell file to generate the nginx file e.g.
echo 'you nginx conf goes here with $envVariable' > location/to/conf/folder/nginx.conf
and run that file inside the container. So when that shell file will run. It will replace the environment variables that you set with it's actual value in the nginx.conf.
Do not forget to skip $ of nginx variables.

How to setup nginx when using docker-compose

Below is my ngionx.conf
worker_processes 1;
error_log /var/log/nginx/error.log warn;
pid /var/run/nginx.pid;
events {
worker_connections 1024;
}
http {
include /etc/nginx/mime.types;
default_type application/octet-stream;
log_format main '$remote_addr - $remote_user [$time_local] "$request" '
'$status $body_bytes_sent "$http_referer" '
'"$http_user_agent" "$http_x_forwarded_for"';
access_log /var/log/nginx/access.log main;
sendfile on;
keepalive_timeout 65;
server {
listen 80;
access_log /var/log/nginx/access.log main;
location /beta/ {
proxy_pass http://localhost:9001;
}
location /qa/ {
proxy_pass http://localhost:9002;
}
location /alpha/ {
proxy_pass http://localhost:9003;
}
location / {
proxy_pass http://www.google.com;
}
}
}
and below is my docker-compose.yml
version: '3'
services:
Reverse-proxy:
image: nginx
ports:
- 80:80
volumes:
- /nginx.conf:/etc/nginx/nginx.conf
restart: always
GQLbeta:
image: gql-beta
ports:
- 9001:80
restart: always
GQLqa:
image: gql-qa
ports:
- 9002:80
restart: always
GQLalpha:
image: gql-alpha
ports:
- 9003:80
restart: always
When I run docker-compose up -d, all container is running good.
Then I went localhost:80 on my browerser, it show
which I expected to see google page.
And when i went to localhost/beta, it will show
502 Bad Gateway
which i expected will go to localhost: 9001
Why this happened? Am i miss something to setup?
localhost in the docker container is the container itself, so you should to give a names to your app containers and describe them as a upstreams - it will fix your 502. With default location, try this:
location / {
return 301 http://google.com;
}

Resources