Xmlhttprequest крос-доменні запити

Зазвичай запит XMLHttpRequest може робити запит тільки в рамках поточного сайту. При спробі використовувати інший домен / порт / протокол - браузер видає помилку.

Існує сучасний стандарт XMLHttpRequest. він ще в стані чернетки, але передбачає крос-доменні запити і багато іншого.

Більшість можливостей цього стандарту вже підтримуються всіма браузерами, але на жаль, не в IE9-.

Втім, частково крос-доменні запити підтримуються, починаючи з IE8, тільки замість XMLHttpRequest потрібно використовувати об'єкт XDomainRequest.

Розберемо крос-доменні запити на прикладі коду:

  1. Ми створюємо XMLHttpRequest і перевіряємо, чи підтримує він подія onload. Якщо немає, то це старий XMLHttpRequest. значить це IE8,9, і використовуємо XDomainRequest.
  2. Запит на інший домен відсилається просто зазначенням відповідного URL в open. Він обов'язково повинен бути асинхронним, в іншому - ніяких особливостей.

Крос-доменні запити проходять спеціальний контроль безпеки, мета якого - не дати злим хакерам ™ завоювати інтернет.

Серйозно. Розробники стандарту передбачили все заслони, щоб «злий хакер» не зміг, скориставшись новим стандартом, зробити щось принципово відмінне від того, що і так міг раніше і, таким чином, «зламати» який-небудь сервер, що працює по-старому стандарту і не очікує нічого принципово нового.

Давайте, на хвилиночку, уявімо, що з'явився стандарт, який дає, без обмежень, можливість робити будь-якій сторінці HTTP-запити куди завгодно, які завгодно.

Як зможе цим скористатися злий хакер?

Специфікація CORS накладає спеціальні обмеження на запити, які покликані не допустити подібного апокаліпсису.

Запити в ній діляться на два види.

Простими вважаються запити, якщо вони задовольняють наступним двом умовам:

  1. Простий метод. GET, POST або HEAD
  2. Прості заголовки - тільки зі списку:
  • Accept
  • Accept-Language
  • Content-Language
  • Content-Type зі значенням application / x-www-form-urlencoded. multipart / form-data або text / plain.

«Непростими» вважаються всі інші, наприклад, запит з методом PUT або з заголовком Authorization не підходить під обмеження вище.

Принципова різниця між ними полягає в тому, що «простий» запит можна сформувати і відправити на сервер і без XMLHttpRequest, наприклад за допомогою HTML-форми.

А ось запити з нестандартними заголовками або з методом DELETE в такий спосіб не створити. Тому старий сервер може бути до них не готовий. Або, наприклад, він може вважати, що такі запити веб-сторінка в принципі не вміє надсилати, значить вони прийшли з привілейованого додатки, і дати їм занадто багато прав.

Тому при посилці «непростих» запитів потрібно спеціальним чином запитати у сервера, чи згоден він в принципі на подібні крос-доменні запити чи ні? І, якщо сервер не відповість, що згоден - значить, немає.

У специфікації CORS, як ми побачимо далі, є багато деталей, але всі вони об'єднані єдиним принципом: нові можливості доступні тільки з явного згоди сервера (за замовчуванням - немає).

У крос-доменний запит браузер автоматично додає заголовок Origin. що містить домен, з якого здійснено запит.

Сервер повинен, зі свого боку, відповісти спеціальними заголовками, чи дозволяє він такий запит до себе.

Xmlhttprequest крос-доменні запити

Тобто, відповідь сервера може бути приблизно таким:

Якщо Access-Control-Allow-Origin немає, то браузер вважає, що дозвіл не отримано, і завершує запит з помилкою.

Що може зробити хакер, використовуючи такі запити?

Описані вище обмеження призводять до того, що запит повністю безпечний.

Дійсно, зла сторінка може сформувати будь-GET / POST-запит і відправити його, але без дозволу сервера відповіді вона не отримає.

У IE9- використовується XDomainRequest. який представляє собою урізаний XMLHttpRequest.

На нього діють обмеження:

Сучасний стандарт XMLHttpRequest передбачає кошти для подолання цих обмежень, але на момент виходу IE8 вони ще не були опрацьовані, тому їх не реалізували. А IE9 виправив деякі помилки, але в загальному не додав нічого нового.

Тому на сайтах, які хочуть підтримувати IE9-, то на практиці крос-доменні запити рідко використовують, вважаючи за краще інші способи крос-доменної комунікації. Наприклад, динамічно створюваний тег SCRIPT або допоміжний IFRAME з іншого домену. Ми розберемо ці підходи в наступних розділах.

Як дозволити крос-доменні запити від довіреної сайту в IE9-?

Дозволити крос-доменні запити для «довірених» сайтів можна в налаштуваннях IE, у вкладці «Безпека», включивши пункт «Доступ до джерел даних за межами домену».

Зазвичай це робиться для зони «Надійні вузли», після чого в неї вноситься довірений сайт. Тепер він може робити крос-доменні запити XMLHttpRequest.

Цей спосіб можна застосувати для корпоративних сайтів, а також в тих випадках, коли відвідувач свідомо вам довіряє, але чомусь (комп'ютер на роботі, адмін забороняє ставити інший браузер?) Хоче використовувати саме IE. Наприклад, він може пропонуватися в якості додаткової інструкції «як змусити цей сервіс працювати під IE».

В IE дозволений інший порт

У крос-доменні обмеження IE не включені порт.

Це дозволяє вирішити деякі завдання, пов'язані із взаємодією різних сервісів в рамках одного сайту. Але тільки для IE.

Розширені можливості, описані далі, підтримуються всіма сучасними браузерами, крім IE9-.

Схожі статті