How Reverse Proxy Django to a subdomain - django

I'm trying to use Nginx to reverse proxy some applications to different subdomain, the problem is when I try to do this with a Django application it doesn't work well, I get the message that the path does not exist or 404 Page not found.
this is a pice of my docker-compose.yaml
version: "3.9"
services:
ww4api:
build: .
hostname: ww4api
command: gunicorn --bind 0.0.0.0:8000 authApi.wsgi --workers=4
depends_on:
- db
- orion
restart: always
container_name: ww4api
environment:
- WW4API_ALLOWED_HOSTS=ww4,ww4api,localhost
ports:
- 8000:8000
volumes:
- .:/app
pgadmin:
container_name: pgadmin
image: dpage/pgadmin4
hostname: pgadmin
restart: always
depends_on:
- timescale
environment:
- PGADMIN_LISTEN_PORT=5050
nginx:
hostname: nginx
build: settings/nginx
restart: always
ports:
- 80:80
- 434:434
tty: true
volumes:
- ./data-models/context:/srv/ww4/context
- ./syncthingFolder/Sync:/srv/ww4/projects
- ./:/srv/ww4
networks:
- default
and this is part of my nginx.config
worker_processes auto;
events {
worker_connections 1024;
}
http {
include /etc/nginx/mime.types;
server_tokens off;
upstream ww4api {
server ww4api:8000;
}
upstream mintaka {
server mintaka:8080;
}
server {
listen 80;
root /srv/ww4;
index index.html;
keepalive_timeout 1s;
keepalive_requests 5000;
location / {
try_files $uri $uri/ =404;
}
location /pgadmin4/ {
resolver 127.0.0.11 ipv6=off;
proxy_pass http://pgadmin:5050/;
proxy_set_header X-Script-Name /pgadmin4;
proxy_set_header X-Scheme $scheme;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_redirect off;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
add_header 'Access-Control-Allow-Origin' '*';
proxy_read_timeout 600s;
proxy_send_timeout 600s;
}
location /ww4/ {
proxy_pass http://ww4api;
proxy_set_header X-Script-Name /ww4;
proxy_set_header X-Scheme $scheme;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_redirect http://localhost/ww4/ http://$host/ww4/;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
add_header 'Access-Control-Allow-Origin' '*';
proxy_read_timeout 600s;
proxy_send_timeout 600s;
}
}
}
What am I doing wrong?

Related

Django channels connection failed (nginx + daphne + certbot + docker-compose)

I'm using Django channels using docker-compose
and nginx outside it
websockets were working just fine but after installing certbot, it stopped working
it returns 404 as if it is treated as just normal http request
VM253:1 WebSocket connection to 'wss://example.com/ws/results/tjrtudvzanxxqbyt' failed:
daphne : "GET /ws/results/tjrtudvzanxxqbyt" 404 2618
my nginx file for the server is
upstream language_transcriber{
server localhost:8000;
}
# the nginx server instance
server {
listen 443 default_server;
server_name example.com;
access_log /var/log/nginx/example.com.log;
ssl_certificate_key /etc/nginx/ssl/example.com.private_key.pem;
ssl_certificate /etc/nginx/ssl/fullchain.crt;
root /var/www;
ssl on;
# pass the request to the node.js server with the correct headers
# and much more can be added, see nginx config options
location /ws/ {
proxy_set_header Host $http_host;
proxy_set_header X-Real-IP$remote_addr;
proxy_set_header X-Forwarded-For$proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Host $server_name;
proxy_set_header X-Forwarded-Proto$scheme;
proxy_set_header X-Url-Scheme $scheme; proxy_redirect off;
proxy_set_header X-NginX-Proxy true;
proxy_http_version 1.1;proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection $connection_upgrade;
proxy_pass http://127.0.0.1:8000;
}
location /static/ {
alias /var/www/example.com/static/;
autoindex off;
}
location / {
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
proxy_http_version 1.1;
proxy_set_header Host $host;
proxy_set_header X-Forwarded-Host $server_name;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_set_header X-Url-Scheme $scheme;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header Host $http_host;
proxy_set_header X-NginX-Proxy true;
proxy_pass http://language_transcriber/;
proxy_redirect off;
}
}
and here's my docker-compose.yml
version: "3.8"
services:
django:
build: .
container_name: django
command: daphne -b 0.0.0.0 -p 8001 project.asgi:application --access-log=/code/media/daphne.access.log
ports:
- "8000:8001"
volumes:
- ./media:/code/media
environment:
- redis_host=redis://redis:6379/0
celery:
build: .
command: celery -A project worker --concurrency=10 --loglevel=info --pool=gevent -E -Ofair --logfile=/code/media/celery.log
restart: always
stdin_open: true # docker run -i
tty: true # docker run -t
environment:
- redis_host=redis://redis:6379/0
depends_on:
- django
- redis
volumes:
- ./media:/code/media
redis:
image: "redis:alpine"
worker_channels:
build: .
command: python manage.py runworker thumbnails-generate thumbnails-delete
depends_on:
- django
- redis
environment:
- redis_host=redis://redis:6379/0
volumes:
waves-volume:
the app works just fine on my localhost but on production it just serves http not ws

NGINX Static Files Over Https?

I have the following docker-compose set up that is working for displaying pictures when deployed locally and without https:
NGINX:
events{
}
http{
server {
listen 80;
server_name localhost;
root /usr/share/nginx/html;
location / {
proxy_pass http://frontend:3000;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "";
proxy_set_header Host $host;
proxy_cache_bypass $http_upgrade;
}
}
}
docker-compose:
frontend:
build:
context: ../../
restart: always
volumes:
- '../../:/app'
- '/app/node_modules'
ports:
- "3000:3000"
depends_on:
- "backend"
environment:
- CHOKIDAR_USEPOLLING=true
stdin_open: true
tty: true
nginx:
build:
context: ../../nginx
restart: always
ports:
- "80:80"
- "443:443"
volumes:
- volume1:/usr/share/nginx/html
links:
- "backend"
- "db"
- "frontend"
frontend:
<img
onError={()=>{
console.log("inside the onError function")
setImgError(true)
}}
src={"http://localhost:9000/static/"+comment.file_name}
className='commentimage'
/>
This is not working when using https. Which is to say - / and /api/ work as expected but not /images/.
events{
}
http{
server {
listen 80;
server_name localhost lightchan.org www.lightchan.org;
root /usr/share/nginx/html;
location /.well-known/acme-challenge/ {
root /var/www/certbot;
}
return 301 https://lightchan.org$request_uri;
}
server {
listen 443 default_server ssl http2;
listen [::]:443 ssl http2;
server_name localhost lightchan.org www.lightchan.org;
#ssl_certificate /etc/nginx/ssl/live/lightchan.org/fullchain.pem;
#ssl_certificate_key /etc/nginx/ssl/live/lightchan.org/privkey.pem;
ssl_certificate /etc/letsencrypt/live/lightchan.org/fullchain.pem;
ssl_certificate_key /etc/letsencrypt/live/lightchan.org/privkey.pem;
location / {
proxy_pass http://frontend:3000;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
proxy_set_header Host $host;
proxy_cache_bypass $http_upgrade;
}
location ^~ /api/ {
rewrite ^/api/(.*)$ /$1 break;
proxy_pass http://backend:8000;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
proxy_set_header Host $host;
proxy_cache_bypass $http_upgrade;
}
location ^~ /images/ {
rewrite ^/images/(.*)$ /$1 break;
proxy_pass https://164.92.157.124/static/;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
proxy_set_header Host $host;
proxy_cache_bypass $http_upgrade;
}
}
}
My docker-compose:
frontend:
build:
context: ../../
restart: always
volumes:
- '../../:/app'
- '/app/node_modules'
ports:
- "3000:3000"
depends_on:
- "backend"
environment:
- CHOKIDAR_USEPOLLING=true
stdin_open: true
tty: true
links:
- 'backend'
nginx:
build:
context: ../../nginx
restart: always
ports:
- "80:80"
- "443:443"
volumes:
- volume1:/usr/share/nginx/html
- varwwwcertbot:/var/www/certbot
- certbotconf:/etc/letsencrypt
links:
- "backend"
- "db"
- "frontend"
certbot:
image: certbot/certbot:latest
volumes:
- varwwwcertbot:/var/www/certbot
- certbotconf:/etc/letsencrypt
My frontend in this case I don't know how to reference. I have
<img
onError={()=>{
console.log("inside the onError function")
setImgError(true)
}}
src={"https://nginx:80/images/"+comment.file_name}
className='commentimage'
/>
Which doesn't look right. I've docker execed into the running nginx container and double checked that the image that I want to display exists in the static directory (which it does). If I attempt to navigate to <DNS>/images/<image.extension> I'm routed back through my frontend application. I've attempted to replace the line
proxy_pass https://164.92.157.124/static/;
with
proxy_pass https://backend:3000/static/;
but that will route through my Django application for static files and I want NGINX to serve them just as a folder.
I've also attempted to rewrite the /images/ block like this:
location ^~ /images/ {
root /usr/share/nginx/html/static;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
proxy_set_header Host $host;
proxy_cache_bypass $http_upgrade;
}
But that didn't work either, and I'm not positive that I'm allowed to rewrite the root for a server block when I redirect using https. In this instance, <DNS>/image/<image.ext> 404's rather than routing to the frontend again.
From reading other Stack Overflow posts people have mentioned that the ^~ signifier takes precedence over absolute routes so I would expect /images/ would be replaced first over /. So I don't understand why this is not true in the first two instances.
Routing to the backend, the IP address of the host, and the NGINX root are the three options that I can think of for the block content.
Any ideas?

Cannot access Strapi in a container using AWS Lightsail, Ubuntu, Docker and NGINX

I'm trying to practice and I have created an instance using AWS Lightsail with Ubuntu 20.04 LTS, also I've installed Docker and Docker Compose.
I would like to run this applications:
MariaDB
Strapi CMS
Let's assume that my public IP is: 1.20.20.20
When I try to access "http://1.20.20.20:1337", I receives "This site can’t be reached".
I thought that maybe I needed a web server and I have included NGINX in my docker-compose configuration.
My folders in the instance:
envs/strapi.env
nginx/strapi.conf
docker-compose.yml
docker-compose.yml
version: '3.8'
services:
nginx:
image: nginx:stable
container_name: nginx
volumes:
- ./nginx/strapi.conf:/etc/nginx/conf.d/default.conf
ports:
- 80:80
restart: on-failure
depends_on:
- strapi
db:
image: mariadb:10.6.4
container_name: db
restart: always
env_file:
- envs/db.env
volumes:
- db-data:/var/lib/mysql
networks:
- apps
strapi:
image: strapi/strapi:3.6.8
container_name: strapi
env_file:
- envs/strapi.env
restart: always
depends_on:
- db
ports:
- 1337:1337
networks:
- apps
volumes:
db-data:
networks:
apps:
driver: bridge
nginx/strapi.conf (I have copied the configuration from Strapi docs):
server {
# Listen HTTP
listen 1337;
server_name 1.20.20.20;
# Static Root
location / {
root /var/www/html;
}
# Strapi API
location /api/ {
rewrite ^/api/?(.*)$ /$1 break;
proxy_pass http://strapi;
proxy_http_version 1.1;
proxy_set_header X-Forwarded-Host $host;
proxy_set_header X-Forwarded-Server $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_set_header Host $http_host;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "Upgrade";
proxy_pass_request_headers on;
}
# Strapi Admin
location /admin {
proxy_pass http://strapi/admin;
proxy_http_version 1.1;
proxy_set_header X-Forwarded-Host $host;
proxy_set_header X-Forwarded-Server $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_set_header Host $http_host;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "Upgrade";
proxy_pass_request_headers on;
}
}
Still cannot access the CMS using my browser.
For some reason, when I do "docker ps -a", the status of the nginx container is always Restarting....
I have tried to follow and read steps that I have found on a few articles without luck. I don't have a lot of experience using NGINX and Ubuntu servers.
My goal is to be able to access the web app (Strapi CMS) through my browser.
Any help would be appreciated.

No connection with dockerized nginx gunicorn

I've created simple example for dockerized django with nginx and gunicorn. But for some reason connection doesn't go through nginx.
Here is nginx.conf contents
worker_processes 1;
error_log /var/log/nginx/error.log info;
events {
worker_connections 1024;
}
http {
gzip on;
gzip_http_version 1.1;
gzip_comp_level 2;
include /etc/nginx/mime.types;
default_type application/octet-stream;
server {
listen 80;
server_name www.example.dj example.dj;
location = /favicon.ico {
alias /app/static_root/favicon.ico;
}
location /static/ {
alias /app/static_root/;
}
location / {
proxy_set_header Host $http_host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_pass http://unix:/app/example.sock;
}
}
}
docker-compose.yml file
version: '3'
services:
web:
build: .
hostname: web
command: bash -c "python manage.py migrate && gunicorn example.wsgi:application --workers 3 --bind unix:/app/example.sock"
volumes:
- ./src:/app
expose:
- "8000"
nginx:
image: nginx:latest
ports:
- "80:8000"
volumes:
- ./src:/app
- ./config/nginx/nginx.conf:/etc/nginx/nginx.conf
depends_on:
- web
In /etc/hosts I have
127.0.0.1 www.example.dj example.dj
So when I run docker-compose up I expect to see django start page by http://example.dj url, but there is no connection. Can you guys help me with it?
Code available on the github

gunicorn setup for django channels

My django app works fine on local machine as well as on Heroku, however I'm having troubles to deploy it do Digital Ocean Ubuntu 16.04 droplet. Followed this tutorial, app has started but websockets didn't work.
By running in terminal virtual environment: daphne -b 0.0.0.0 -p 8000 slist.asgi:channel_layer
and in second terminal window:
./manage.py runworker
The app works but only on port 8000. I can't access it on mydomain.com but only on mydomain.com:8000.
When I close terminal windows the site cannot be accessed.
What and how needs to be set for the site to run without my terminal windows and without the ':8000'?
My gunicorn.service file:
[Unit]
Description=gunicorn daemon
After=network.target
[Service]
User=kuba1
Group=www-data
WorkingDirectory=/home/kuba1/slistproject
ExecStart=/home/kuba1/slistproject/slistvenv/bin/gunicorn --workers 3 --bind unix:/home/kuba1/slistproject/slistvenv/src/slist.sock slist.wsgi:application
[Install]
WantedBy=multi-user.target
my Nginx settings:
server {
listen 80;
server_name server_name fortests.ovh;
client_max_body_size 20M;
location /static/ {
root /home/kuba1/slistproject/slistvenv/src;
}
location / {
proxy_pass http://unix:/home/kuba1/slistproject/slistvenv/src/slist.sock;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
proxy_redirect off;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Host $server_name;
}
}
You have to proxy_pass the domain to that port 8000:
location / {
proxy_pass_header Server;
proxy_set_header X-Forwarded-Proto https;
proxy_set_header Host $http_host;
proxy_redirect off;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Scheme $scheme;
proxy_connect_timeout 10;
proxy_read_timeout 10;
proxy_pass http://localhost:8001/;
}
It should be:
proxy_set_header Connection "Upgrade";
Working config for me:
upstream websocket {
server unix:/path/to/daphne.sock fail_timeout=20;
}
location /url/socket/ {
try_files $uri #proxy_to_channel_app;
}
location #proxy_to_channel_app {
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Real-IP $remote_addr;
# enable this if and only if you use HTTPS
proxy_set_header X-Forwarded-Proto https;
proxy_set_header Host $http_host;
# web socket setup
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection 'Upgrade';
# we don't want nginx trying to do something clever with
# redirects, we set the Host: header above already.
proxy_redirect off;
proxy_pass http://websocket;
}
Daphne command:
daphne -u run/daphne.sock project.asgi:channel_layer