如何在 Nginx 代理服务器中启用 CORS?
How to enable CORS in Nginx proxy server?
正如我的标题,这是位于 conf.d/api-server.conf
中的配置文件
server {
listen 80;
server_name api.localhost;
location / {
add_header 'Access-Control-Allow-Origin' 'http://api.localhost';
add_header 'Access-Control-Allow_Credentials' 'true';
add_header 'Access-Control-Allow-Headers' 'Authorization,Accept,Origin,DNT,X-CustomHeader,Keep-Alive,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Content-Range,Range';
add_header 'Access-Control-Allow-Methods' 'GET,POST,OPTIONS,PUT,DELETE,PATCH';
if ($request_method = 'OPTIONS') {
add_header 'Access-Control-Max-Age' 1728000;
add_header 'Content-Type' 'text/plain charset=UTF-8';
add_header 'Content-Length' 0;
return 204;
}
proxy_redirect off;
proxy_set_header host $host;
proxy_set_header X-real-ip $remote_addr;
proxy_set_header X-forward-for $proxy_add_x_forwarded_for;
proxy_pass http://127.0.0.1:3000;
}
}
nginx.conf 文件保持默认不变。
我向api.localhost发送请求后(api.localhost/admin/login),我仍然收到405错误:
XMLHttpRequest cannot load http://api.localhost/admin/login. Response
to preflight request doesn't pass access control check: No 'Access-
Control-Allow-Origin' header is present on the requested resource.
Origin 'http://admin.localhost:3000' is therefore not allowed access.
The response had HTTP status code 405.
问题是您的 if 条件不会在 /
中发送 parent 中的 headers。如果您检查预检响应 headers 它将是
HTTP/1.1 204 No Content
Server: nginx/1.13.3
Date: Fri, 01 Sep 2017 05:24:04 GMT
Connection: keep-alive
Access-Control-Max-Age: 1728000
Content-Type: text/plain charset=UTF-8
Content-Length: 0
那什么也没有。所以有两个可能的修复方法。复制 if 块中的 add_header
也
server {
listen 80;
server_name api.localhost;
location / {
add_header 'Access-Control-Allow-Origin' 'http://api.localhost';
add_header 'Access-Control-Allow-Credentials' 'true';
add_header 'Access-Control-Allow-Headers' 'Authorization,Accept,Origin,DNT,X-CustomHeader,Keep-Alive,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Content-Range,Range';
add_header 'Access-Control-Allow-Methods' 'GET,POST,OPTIONS,PUT,DELETE,PATCH';
if ($request_method = 'OPTIONS') {
add_header 'Access-Control-Allow-Origin' 'http://api.localhost';
add_header 'Access-Control-Allow-Credentials' 'true';
add_header 'Access-Control-Allow-Headers' 'Authorization,Accept,Origin,DNT,X-CustomHeader,Keep-Alive,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Content-Range,Range';
add_header 'Access-Control-Allow-Methods' 'GET,POST,OPTIONS,PUT,DELETE,PATCH';
add_header 'Access-Control-Max-Age' 1728000;
add_header 'Content-Type' 'text/plain charset=UTF-8';
add_header 'Content-Length' 0;
return 204;
}
proxy_redirect off;
proxy_set_header host $host;
proxy_set_header X-real-ip $remote_addr;
proxy_set_header X-forward-for $proxy_add_x_forwarded_for;
proxy_pass http://127.0.0.1:3000;
}
}
或者您可以将它移到位置块之外,这样每个请求都有响应
server {
listen 80;
server_name api.localhost;
add_header 'Access-Control-Allow-Origin' 'http://api.localhost';
add_header 'Access-Control-Allow-Credentials' 'true';
add_header 'Access-Control-Allow-Headers' 'Authorization,Accept,Origin,DNT,X-CustomHeader,Keep-Alive,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Content-Range,Range';
add_header 'Access-Control-Allow-Methods' 'GET,POST,OPTIONS,PUT,DELETE,PATCH';
location / {
if ($request_method = 'OPTIONS') {
add_header 'Access-Control-Max-Age' 1728000;
add_header 'Content-Type' 'text/plain charset=UTF-8';
add_header 'Content-Length' 0;
return 204;
}
proxy_redirect off;
proxy_set_header host $host;
proxy_set_header X-real-ip $remote_addr;
proxy_set_header X-forward-for $proxy_add_x_forwarded_for;
proxy_pass http://127.0.0.1:3000;
}
}
如果您只想在配置中的某些位置允许 CORS。像 /api
那么你应该用你的 headers
创建一个模板 conf
add_header 'Access-Control-Allow-Origin' 'http://api.localhost';
add_header 'Access-Control-Allow-Credentials' 'true';
add_header 'Access-Control-Allow-Headers' 'Authorization,Accept,Origin,DNT,X-CustomHeader,Keep-Alive,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Content-Range,Range';
add_header 'Access-Control-Allow-Methods' 'GET,POST,OPTIONS,PUT,DELETE,PATCH';
然后使用
include conf.d/corsheaders.conf;
在您的 OPTIONS
区块和 /api
区块中。所以 CORS 只允许用于 /api
。如果您不关心 CORS 的位置,那么您可以使用第二种方法将核心 headers 移动到服务器块
正如我的标题,这是位于 conf.d/api-server.conf
中的配置文件server {
listen 80;
server_name api.localhost;
location / {
add_header 'Access-Control-Allow-Origin' 'http://api.localhost';
add_header 'Access-Control-Allow_Credentials' 'true';
add_header 'Access-Control-Allow-Headers' 'Authorization,Accept,Origin,DNT,X-CustomHeader,Keep-Alive,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Content-Range,Range';
add_header 'Access-Control-Allow-Methods' 'GET,POST,OPTIONS,PUT,DELETE,PATCH';
if ($request_method = 'OPTIONS') {
add_header 'Access-Control-Max-Age' 1728000;
add_header 'Content-Type' 'text/plain charset=UTF-8';
add_header 'Content-Length' 0;
return 204;
}
proxy_redirect off;
proxy_set_header host $host;
proxy_set_header X-real-ip $remote_addr;
proxy_set_header X-forward-for $proxy_add_x_forwarded_for;
proxy_pass http://127.0.0.1:3000;
}
}
nginx.conf 文件保持默认不变。
我向api.localhost发送请求后(api.localhost/admin/login),我仍然收到405错误:
XMLHttpRequest cannot load http://api.localhost/admin/login. Response
to preflight request doesn't pass access control check: No 'Access-
Control-Allow-Origin' header is present on the requested resource.
Origin 'http://admin.localhost:3000' is therefore not allowed access.
The response had HTTP status code 405.
问题是您的 if 条件不会在 /
中发送 parent 中的 headers。如果您检查预检响应 headers 它将是
HTTP/1.1 204 No Content
Server: nginx/1.13.3
Date: Fri, 01 Sep 2017 05:24:04 GMT
Connection: keep-alive
Access-Control-Max-Age: 1728000
Content-Type: text/plain charset=UTF-8
Content-Length: 0
那什么也没有。所以有两个可能的修复方法。复制 if 块中的 add_header
也
server {
listen 80;
server_name api.localhost;
location / {
add_header 'Access-Control-Allow-Origin' 'http://api.localhost';
add_header 'Access-Control-Allow-Credentials' 'true';
add_header 'Access-Control-Allow-Headers' 'Authorization,Accept,Origin,DNT,X-CustomHeader,Keep-Alive,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Content-Range,Range';
add_header 'Access-Control-Allow-Methods' 'GET,POST,OPTIONS,PUT,DELETE,PATCH';
if ($request_method = 'OPTIONS') {
add_header 'Access-Control-Allow-Origin' 'http://api.localhost';
add_header 'Access-Control-Allow-Credentials' 'true';
add_header 'Access-Control-Allow-Headers' 'Authorization,Accept,Origin,DNT,X-CustomHeader,Keep-Alive,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Content-Range,Range';
add_header 'Access-Control-Allow-Methods' 'GET,POST,OPTIONS,PUT,DELETE,PATCH';
add_header 'Access-Control-Max-Age' 1728000;
add_header 'Content-Type' 'text/plain charset=UTF-8';
add_header 'Content-Length' 0;
return 204;
}
proxy_redirect off;
proxy_set_header host $host;
proxy_set_header X-real-ip $remote_addr;
proxy_set_header X-forward-for $proxy_add_x_forwarded_for;
proxy_pass http://127.0.0.1:3000;
}
}
或者您可以将它移到位置块之外,这样每个请求都有响应
server {
listen 80;
server_name api.localhost;
add_header 'Access-Control-Allow-Origin' 'http://api.localhost';
add_header 'Access-Control-Allow-Credentials' 'true';
add_header 'Access-Control-Allow-Headers' 'Authorization,Accept,Origin,DNT,X-CustomHeader,Keep-Alive,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Content-Range,Range';
add_header 'Access-Control-Allow-Methods' 'GET,POST,OPTIONS,PUT,DELETE,PATCH';
location / {
if ($request_method = 'OPTIONS') {
add_header 'Access-Control-Max-Age' 1728000;
add_header 'Content-Type' 'text/plain charset=UTF-8';
add_header 'Content-Length' 0;
return 204;
}
proxy_redirect off;
proxy_set_header host $host;
proxy_set_header X-real-ip $remote_addr;
proxy_set_header X-forward-for $proxy_add_x_forwarded_for;
proxy_pass http://127.0.0.1:3000;
}
}
如果您只想在配置中的某些位置允许 CORS。像 /api
那么你应该用你的 headers
add_header 'Access-Control-Allow-Origin' 'http://api.localhost';
add_header 'Access-Control-Allow-Credentials' 'true';
add_header 'Access-Control-Allow-Headers' 'Authorization,Accept,Origin,DNT,X-CustomHeader,Keep-Alive,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Content-Range,Range';
add_header 'Access-Control-Allow-Methods' 'GET,POST,OPTIONS,PUT,DELETE,PATCH';
然后使用
include conf.d/corsheaders.conf;
在您的 OPTIONS
区块和 /api
区块中。所以 CORS 只允许用于 /api
。如果您不关心 CORS 的位置,那么您可以使用第二种方法将核心 headers 移动到服务器块