tl; dr; О той же политике происхождения
У меня есть процесс Grunt, который запускает экземпляр сервера express.js. Это работало абсолютно нормально до тех пор, пока не начало обслуживать пустую страницу, и в журнале ошибок в консоли разработчика Chrome (последняя версия) появилось следующее:
XMLHttpRequest не может загрузить https://www.example.com/ На запрошенном ресурсе отсутствует заголовок Access-Control-Allow-Origin. Следовательно, к источнику ' http: // localhost: 4300 ' не разрешен доступ.
Что мешает мне получить доступ к странице?
javascript
cors
same-origin-policy
Питер Дэвид Картер
источник
источник
Ответы:
tl; dr - в конце есть сводка, а в ответе заголовки, чтобы было проще найти нужные части. Тем не менее, рекомендуется прочитать все, так как это дает полезную основу для понимания того, почему, это упрощает понимание того, как применяется в различных обстоятельствах.
О той же политике происхождения
Это та же политика происхождения . Это функция безопасности, реализованная браузерами.
В вашем конкретном случае показано, как он реализован для XMLHttpRequest (и вы получите идентичные результаты, если бы использовали выборку), но он также применяется к другим вещам (например, изображениям, загруженным в
<canvas>
или документы, загруженные в<iframe>
), просто с немного разные реализации.(Как ни странно, это также применимо к шрифтам CSS, но это потому, что найденные литейщики настаивали на DRM, а не на проблемах безопасности, которые обычно покрывает политика одинакового происхождения).
Стандартный сценарий, демонстрирующий необходимость СОП, можно продемонстрировать тремя символами :
https://www.[website].com/
в вашем примере)http://localhost:4300
в вашем примере)Алиса вошла на сайт Боба и хранит там некоторые конфиденциальные данные. Возможно, это интрасеть компании (доступная только для браузеров в локальной сети) или ее онлайн-банкинг (доступный только с помощью файла cookie, который вы получаете после ввода имени пользователя и пароля).
Алиса посещает веб-сайт Мэллори, на котором есть некоторый JavaScript, который заставляет браузер Алисы делать HTTP-запрос на веб-сайт Боба (с ее IP-адреса с ее файлами cookie и т. Д.). Это может быть так же просто, как использовать
XMLHttpRequest
и читатьresponseText
.Политика одинакового происхождения браузера не позволяет этому JavaScript читать данные, возвращаемые веб-сайтом Боба (к которым Боб и Алиса не хотят, чтобы Мэллори имел доступ). (Обратите внимание , что вы можете, например, отобразить изображение с помощью
<img>
элемента по происхождению , так как содержание изображения не подвергаются JavaScript (или Mallory) ... если вы не бросить холст в смесь , в этом случае вы будете генерировать один и то же происхождение ошибка нарушения).Почему применяется та же политика происхождения, если вы не думаете, что это должно быть
Для любого заданного URL-адреса возможно, что СОП не требуется. Вот несколько распространенных сценариев, когда это так:
… Но браузер не имеет возможности узнать, верно ли что-либо из вышеперечисленного, поэтому доверие не является автоматическим, и применяется СОП. Разрешение должно быть предоставлено явным образом, прежде чем браузер передаст данные другому веб-сайту.
Почему одна и та же политика происхождения применяется только к JavaScript на веб-странице
Расширения браузера
*
, вкладка «Сеть» в инструментах разработчика браузера и такие приложения, как Postman, являются установленным программным обеспечением. Они не передают данные с одного веб-сайта в JavaScript, принадлежащий другому веб-сайту, только потому, что вы посетили этот другой веб-сайт . Установка программного обеспечения обычно требует более осознанного выбора.Нет третьей стороны (Мэллори), которая считается риском.
*
Расширения браузера нужно писать осторожно, чтобы избежать проблем с перекрестным происхождением. См., Например, документацию Chrome .Почему вы можете отображать данные на странице, не читая их с помощью JS
Существует ряд обстоятельств, при которых сайт Мэллори может заставить браузер получать данные от третьей стороны и отображать их (например, путем добавления
<img>
элемента для отображения изображения). Однако JavaScript Мэллори не может прочитать данные в этом ресурсе, это могут сделать только браузер Алисы и сервер Боба, поэтому он по-прежнему безопасен.CORS
Access-Control-Allow-Origin
HTTP ответ заголовок , предусмотренный в сообщении об ошибке является частью CORS стандарта , что позволяет Бобу явным образом предоставить разрешение на сайт Мэллорите , чтобы получить доступ к данным через браузер Алисы.Базовая реализация будет просто включать:
… В заголовках ответов, чтобы любой веб-сайт мог читать данные.
… Позволит только определенному сайту получить к нему доступ, и Боб может динамически генерировать его на основе заголовка
Origin
запроса, чтобы разрешить доступ к нему нескольким, но не всем сайтам.Специфика того, как Боб устанавливает этот заголовок ответа, зависит от HTTP-сервера Боба и / или серверного языка программирования. Есть набор руководств по различным распространенным конфигурациям, которые могут помочь.
NB: Некоторые запросы являются комплексными и отправить предполетной OPTIONS запросить, чтобы сервер должен будет реагировать раньше браузер отправит GET / POST / PUT / Whatever запрос о том , что JS хочет сделать. Реализации CORS, которые добавляются только
Access-Control-Allow-Origin
к определенным URL-адресам, часто сбиваются с толку.Очевидно, что предоставление разрешения через CORS - это то, что Боб сделал бы только в том случае, если:
Но я не Боб!
У Мэллори нет стандартного механизма для добавления этого заголовка, потому что он должен поступать с веб-сайта Боба, который она не контролирует.
Если Боб запускает общедоступный API, то может быть механизм для включения CORS (возможно, путем форматирования запроса определенным образом или параметра конфигурации после входа на сайт портала разработчика для сайта Боба). Однако это должен быть механизм, реализованный Бобом. Мэллори может прочитать документацию на сайте Боба, чтобы узнать, доступно ли что-нибудь, или она может поговорить с Бобом и попросить его внедрить CORS.
Сообщения об ошибках, в которых упоминается "Ответ на предполетную проверку"
Некоторые запросы на перекрестное происхождение проходят предварительную проверку .
Это происходит, когда (грубо говоря) вы пытаетесь сделать запрос на другой источник, который:
enctype
).Если вы правильно делаете что-то, что требует предполетной подготовки
В этих случаях , то остальная часть этого ответа все еще применяется , но вы также должны убедиться , что сервер может прослушивать предполетной запрос (который будет
OPTIONS
(а неGET
,POST
или что вы пытаетесь отправить) и ответить на него с правомAccess-Control-Allow-Origin
header, но такжеAccess-Control-Allow-Methods
иAccess-Control-Allow-Headers
для разрешения ваших конкретных HTTP-методов или заголовков.Если вы по ошибке запускаете предполетную проверку
Иногда люди делают ошибки при построении запросов Ajax, а иногда они вызывают необходимость предварительной проверки. Если API предназначен для разрешения запросов из разных источников, но не требует ничего, что потребовало бы предварительной проверки, это может нарушить доступ.
Распространенные ошибки, которые вызывают это, включают:
Access-Control-Allow-Origin
и другие заголовки ответа CORS на запрос. Они не относятся к запросу, не делают ничего полезного (какой смысл в системе разрешений, в которой вы могли бы предоставить себе разрешение?), И должны появляться только в ответе.Content-Type: application/json
заголовок в запрос GET, не имеющий тела запроса для описания содержимого (обычно, когда автор путаетContent-Type
иAccept
).В любом из этих случаев удаления дополнительного заголовка запроса часто бывает достаточно, чтобы избежать необходимости в предварительной проверке (которая решит проблему при взаимодействии с API-интерфейсами, которые поддерживают простые запросы, но не запросы с предварительной проверкой).
Непрозрачные ответы
Иногда вам нужно сделать HTTP-запрос, но вам не нужно читать ответ. например, если вы отправляете сообщение журнала на сервер для записи.
Если вы используете в
fetch
API (вместоXMLHttpRequest
), то вы можете настроить его , чтобы не пытаться использовать CORS.Обратите внимание, что это не позволит вам делать то, что вам требуется от CORS. Вы не сможете прочитать ответ. Вы не сможете отправить запрос, требующий предполетной проверки.
Это позволит вам сделать простой запрос, не видеть ответа и не заполнять консоль разработчика сообщениями об ошибках.
Как это сделать, объясняется сообщением об ошибке Chrome, которое выдается, когда вы делаете запрос с помощью
fetch
и не получаете разрешения на просмотр ответа с помощью CORS:Таким образом:
Альтернативы CORS
JSONP
Боб также мог предоставить данные, используя такой хакерский прием, как JSONP. Именно так люди использовали Ajax с перекрестным происхождением до появления CORS.
Он работает, представляя данные в виде программы JavaScript, которая вводит данные на страницу Мэллори.
Это требует, чтобы Мэллори доверял Бобу, чтобы он не предоставлял вредоносный код.
Обратите внимание на общую тему: сайт, предоставляющий данные, должен сообщить браузеру, что сторонний сайт может получить доступ к данным, которые он отправляет в браузер.
Поскольку JSONP работает путем добавления
<script>
элемента для загрузки данных в форме программы JavaScript, которая вызывает функцию, уже находящуюся на странице, попытка использовать технику JSONP для URL-адреса, который возвращает JSON, не удастся - обычно с ошибкой CORB - потому что JSON не является JavaScript.Переместите два ресурса в один источник
Если HTML-документ, в котором выполняется JS, и запрашиваемый URL-адрес относятся к одному и тому же источнику (используют одну и ту же схему, имя хоста и порт), то одна и та же политика происхождения предоставляет разрешение по умолчанию. CORS не нужен.
Прокси
Мэллори могла использовать серверный код для получения данных (которые она могла затем передать со своего сервера в браузер Алисы через HTTP, как обычно).
Это либо:
Этот серверный код может быть написан и размещен третьей стороной (например, CORS Anywhere). Обратите внимание на последствия этого для конфиденциальности: третья сторона может отслеживать, кто какие прокси на своих серверах.
Бобу не нужно было бы предоставлять какие-либо разрешения, чтобы это произошло.
Здесь нет никаких последствий для безопасности, поскольку это только между Мэллори и Бобом. Боб не может думать, что Мэллори - это Алиса, и предоставлять Мэллори данные, которые должны оставаться конфиденциальными между Алисой и Бобом.
Следовательно, Мэллори может использовать этот метод только для чтения общедоступных данных.
Однако обратите внимание, что получение контента с чужого веб-сайта и отображение его самостоятельно может быть нарушением авторских прав и привести к судебному преследованию.
Написание чего-то другого, кроме веб-приложения
Как отмечалось в разделе «Почему одна и та же политика происхождения применяется только к JavaScript на веб-странице», вы можете избежать использования СОП, не написав JavaScript на веб-странице.
Это не означает, что вы не можете продолжать использовать JavaScript и HTML, но вы можете распространять их, используя какой-либо другой механизм, например Node-WebKit или PhoneGap.
Расширения браузера
Расширение браузера может вставлять заголовки CORS в ответ до того, как будет применена политика того же происхождения.
Они могут быть полезны для разработки, но непрактичны для производственного сайта (неразумно просить каждого пользователя вашего сайта установить расширение, отключающее функцию безопасности его браузера).
Они также обычно работают только с простыми запросами (сбой при обработке предполетных запросов OPTIONS).
Обычно лучше иметь подходящую среду разработки с локальным сервером разработки .
Прочие риски безопасности
Обратите внимание, что SOP / CORS не смягчают атаки XSS , CSRF или SQL Injection, которые необходимо обрабатывать независимо.
Резюме
источник
На целевом сервере должен быть разрешен запрос из разных источников. Чтобы разрешить это через экспресс, просто обработайте запрос параметров http:
источник
Поскольку это не упоминается в принятом ответе.
Вы можете использовать простые запросы .
Для выполнения «простых запросов» запрос должен соответствовать нескольким условиям. Например , только что позволяет
POST
,GET
иHEAD
метод, а также позволяя лишь некоторые заголовки заданного (вы можете найти все условия здесь ).Если ваш клиентский код явно не устанавливает затронутые заголовки (например, «Принять») с фиксированным значением в запросе, может возникнуть ситуация, когда некоторые клиенты действительно устанавливают эти заголовки автоматически с некоторыми «нестандартными» значениями, из-за чего сервер не принимает их как Простой запрос - выдаст ошибку CORS.
источник
Это происходит из-за ошибки CORS. CORS расшифровывается как Cross Origin Resource Sharing. Проще говоря, эта ошибка возникает, когда мы пытаемся получить доступ к домену / ресурсу из другого домена.
Подробнее об этом здесь: Ошибка CORS с jquery
Чтобы исправить это, если у вас есть доступ к другому домену, вам нужно будет разрешить Access-Control-Allow-Origin на сервере. Это можно добавить в заголовки. Вы можете включить это для всех запросов / доменов или для определенного домена.
Как заставить работать почтовый запрос на совместное использование ресурсов (CORS)
Эти ссылки могут помочь
источник
Эта проблема CORS дополнительно не прорабатывалась (по другим причинам).
У меня сейчас эта проблема по другой причине. Мой интерфейс также возвращает ошибку заголовка Access-Control-Allow-Origin.
Просто я указал неправильный URL-адрес, поэтому этот заголовок не был отражен должным образом (в чем я предполагал, что это так). localhost (внешний интерфейс) -> вызов незащищенного http (предполагается, что это https), убедитесь, что конечная точка API из внешнего интерфейса указывает на правильный протокол.
источник
У меня такая же ошибка в консоли Chrome.
Моя проблема заключалась в том, что я пытался зайти на сайт, используя
http://
вместоhttps://
. Так что поправлять было нечего, просто нужно было зайти на тот же сайт, используяhttps
.источник
Этот баг обошелся мне в 2 дня. Я проверил свой журнал сервера, запрос / ответ Preflight Option между браузером Chrome / Edge и сервером был в порядке. Основная причина в том, что ответ сервера GET / POST / PUT / DELETE для XHTMLRequest также должен иметь следующий заголовок:
"origin" находится в заголовке запроса (браузер добавит его в запрос за вас). например:
вы можете добавить следующий заголовок ответа, чтобы принять его для всех:
или заголовок ответа для конкретного запроса, например:
Сообщение в браузерах непонятно: "... Запрошенный ресурс"
обратите внимание: CORS хорошо работает для localhost. другой порт означает другой домен. если вы получили сообщение об ошибке, проверьте конфигурацию CORS на стороне сервера.
источник
Запрос «Получить» с добавлением заголовков преобразуется в запрос «Параметры». Так возникают проблемы с политикой Cors. Вы должны реализовать запрос «Параметры» на своем сервере.
источник
Вы должны включить CORS, чтобы он заработал.
источник