CORS Issues with Nginx as Reverse Proxy for Django
I am running Nginx as my webserver to server the static frontend files and as a reverse proxy for my Django Server. The Problem is that i am having CORS Issues, when doing request from the frontend. My Design-Plan was to use the Apex Domain example.com
for the frontend and all API Calls go to api.example.com
.
I already did a tone of research and tried to catch OPTIONS request etc. but i still have CORS Errors. Also Django has the django-cors package installed and Axios is using .withDefaultCredentials = true
. My current nginx config looks like this:
server {
listen 80;
listen [::]:80;
server_name $DOMAIN_HOSTNAME;
root /var/www/example.com/dist;
location /media {
alias /var/www/example.com/media/;
}
location / {
try_files $uri $uri/ /index.html =404;
}
}
upstream djangoserver {
server django:8000;
}
server {
listen 80;
listen [::]:80;
server_name $API_DOMAIN_HOSTNAME;
location / {
proxy_pass http://djangoserver;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header Host $http_host;
proxy_set_header 'Access-Control-Allow-Origin' $http_origin;
proxy_set_header 'Access-Control-Allow-Credentials' 'true';
proxy_redirect off;
add_header 'Access-Control-Allow-Origin' 'https://example.com';
add_header 'Access-Control-Allow-Methods' 'GET, POST, PUT, DELETE, OPTIONS';
add_header 'Access-Control-Allow-Headers' 'DNT,X-CustomHeader,Keep-Alive,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type';
add_header 'Access-Control-Allow-Credentials' 'true';
if ($request_method = 'OPTIONS') {
add_header 'Access-Control-Allow-Origin' 'https://example.com';
add_header 'Access-Control-Allow-Methods' 'GET, POST, PUT, DELETE, OPTIONS';
add_header 'Access-Control-Allow-Headers' 'DNT,X-CustomHeader,Keep-Alive,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type';
add_header 'Access-Control-Allow-Credentials' 'true';
return 204;
}
}
}
Also so no confusion is happening internally the nginx is serving on port 80, but its behind cloudflare which is establishing a https connection from client to cloudflares network. In the Django setting there is the domain configured:
# Allowed hosts this django app is allowed to run on.
ALLOWED_HOSTS = [
"localhost",
"127.0.0.1",
os.environ.get('DOMAIN_IP'),
os.environ.get('FRONTEND_DOMAIN_HOSTNAME')
]
# Cors policy (allowed origins) options...
CORS_ALLOWED_ORIGINS = [
"http://127.0.0.1",
"http://127.0.0.1" + ":" + os.environ.get("FRONTEND_PORT"),
"https://127.0.0.1",
"https://127.0.0.1" + ":" + os.environ.get("FRONTEND_PORT"),
"http://localhost",
"http://localhost" + ":" + os.environ.get("FRONTEND_PORT"),
"https://localhost",
"https://localhost" + ":" + os.environ.get("FRONTEND_PORT"),
"http://" + os.environ.get('FRONTEND_DOMAIN_HOSTNAME'),
"http://" + os.environ.get('FRONTEND_DOMAIN_HOSTNAME') + ":" + os.environ.get("FRONTEND_PORT"),
"https://" + os.environ.get('DOMAIN_IP'),
"https://" + os.environ.get('DOMAIN_IP') + ":" + os.environ.get("FRONTEND_PORT"),
]
CORS_ALLOW_CREDENTIALS = True
CSRF_TRUSTED_ORIGINS = CORS_ALLOWED_ORIGINS
Am i doing something wrong with my design or am i just missing something? I'm quite new to nginx configs.