Вот уже пару дней я выдергиваю волосы. У меня есть бэкэнд-сервер, использующий Spring-boot с Rest API
Этот сервер вызывается из внешнего интерфейса с использованием AngularJS, который также обрабатывается Nginx.
Все работает локально. Всякий раз, когда я пытаюсь сделать запрос от внешнего интерфейса к серверной части, я получаю следующую ошибку:
Я знаю, что вы думаете: просто добавьте add_header 'Access-Control-Allow-Origin' 'http: // [MY_IP]'; в ваш файл nginx.conf на бэкэнде, и все будет работать, как здесь. или здесь.
Но это не так. Я все перепробовал, переместил в разные места, поставил '*' вместо адреса, включил и отключил SSL ... Единственное, что работает, - это когда я вручную отключаю ограничения Cross-Origin в браузере. И самое приятное то, что когда я снимаю эти ограничения, я вижу, что заголовок Access-Control-Allow-Origin установлен на http: // [MY_IP] в консоли отладки моего браузера!
Есть идеи, что может пойти не так?
Вот мой файл nginx.conf:
user nginx;
worker_processes auto;
error_log /var/log/nginx/error.log;
pid /run/nginx.pid;
# Load dynamic modules. See /usr/share/nginx/README.dynamic.
include /usr/share/nginx/modules/*.conf;
events {
worker_connections 1024;
}
http {
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;
tcp_nodelay on;
keepalive_timeout 65;
types_hash_max_size 2048;
include /etc/nginx/mime.types;
default_type application/octet-stream;
# Load modular configuration files from the /etc/nginx/conf.d directory.
# See http://nginx.org/en/docs/ngx_core_module.html#include
# for more information.
include /etc/nginx/conf.d/*.conf;
include /etc/nginx/sites-enabled/*;
}
Вот мой файл /etc/nginx/sites-enabled/default.conf:
upstream backend_api {
server 10.34.18.2:8080;
}
server {
listen 80 default_server;
listen [::]:80 default_server;
server_name _;
root /var/www/html/;
index index.html;
client_max_body_size 5M;
location /todos {
access_log /var/log/nginx/todos.backend.access.log;
error_log /var/log/nginx/todos.backend.error.log;
proxy_set_header HOST $host;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_pass http://backend_api;
}
location / {
access_log /var/log/nginx/todos.frontend.access.log;
error_log /var/log/nginx/todos.frontend.error.log;
try_files $uri $uri/ =404;
}
}
Создаю символическую ссылку:
ln -s /etc/nginx/sites-available/default /etc/nginx/sites-enabled/
Если конечная точка API, к которой ваш код обращается, является сервером Spring Boot, вы понимаете, что это сервер, который должен отправить обратно Access-Control-Allow-Origin, верно? Поэтому, если настоящая проблема заключается в том, что браузер регистрирует сообщение «отсутствует заголовок Access-Control-Allow-Origin» в консоли разработчика, исправление состоит в том, чтобы настроить сервер Spring Boot для отправки этого заголовка обратно. Если ваш запрос не идет на сервер nginx, тогда ваша конфигурация nginx не имеет значения (и в любом случае фрагменты конфигурации nginx в вопросе не показывают, что заголовок Access-Control-Allow-Origin нигде установлен ...)


Я не уверен, что это заставит cors работать, но это может помочь приблизиться к решению:
Access-Control-Allow-Origin: http://[MY_IP] - не единственный заголовок, о котором вам нужно позаботиться.
Поскольку Content-Type - это application/json, а также вы не используете непростые заголовки, вам также нужно будет дать конкретное разрешение для заголовка Content-Type, то же самое с Accept-Encoding и DNT.
Access-Control-Allow-Headers: Content-Type, Accept-Encoding, DNT
Я не уверен насчет этого для этого конкретного GET, но в любом случае также допустимые методы:
Access-Control-Allow-Methods: GET
И если вы отправляете файлы cookie, заголовок авторизации или клиентские сертификаты для аутентификации:
Access-Control-Allow-Credentials: true
Я не думаю, что это ваш текущий случай, но обратите внимание, что возврат Access-Control-Allow-Credentials: true и слепая репликация полученного Origin в ответе Access-Control-Allow-Origin позволяет любому сайту получить доступ к вашему серверу, выдавая себя за владельца учетных данных.
И на всякий случай, если вы соблазнитесь, ACAO: * с ACAC: true не будет работать в соответствии со спецификацией.
Возможно, вам также придется позаботиться о методе OPTIONS, вызываемом во время предварительной проверки cors, который должен соответствовать тому, что будет отвечать фактический вызов.
И помните, что отказ от возврата одного из этих заголовков - это способ отрицать это.
Ссылка: CORS - MDN
Вы пробовали изменить URL-адрес в коде запроса на
http://10.34.18.2:8080/docs/(с косой чертой в конце)? Дело в том, что снимок экрана i.stack.imgur.com/eFKpE.png не показывает никаких ошибок - вместо этого на снимке экрана просто показан успешный запрос кhttp://10.34.18.2:8080/docsи сервер, отвечающий (без ошибок) перенаправлением 302 наhttp://10.34.18.2:8080/docs/. Таким образом, сервер просто говорит: «Вы забыли добавить косую черту в конце URL-адреса запроса».. Если при входе в консоль инструментов разработчика возникает другая ошибка, добавьте ее в вопрос.