Перейти до основного вмісту

Посібники / Коди статусу HTTP пояснено

406 Not Acceptable: що означає і як виправити

406 Not Acceptable означає, що сервер не може створити відповідь, яка збігається з тим, що клієнт сказав, що прийме. Сам запит у порядку; узгодження між тим, що запросили, і тим, що сервер здатен запропонувати, провалилося, зазвичай через формат, мову чи кодування відповіді.

Що означає 406 Not Acceptable

HTTP підтримує узгодження вмісту через родину заголовків Accept: Accept для типу медіа відповіді, Accept-Language для мови й Accept-Encoding для стиснення. Клієнт може надіслати будь-який з них, щоб сказати "дай мені лише ту відповідь, яку я можу використати." Згідно з RFC 9110, якщо сервер не може створити подання, яке клієнт вказав, що прийме, і обирає повідомити про це, а не все одно щось надіслати, він відповідає 406. На практиці більшість серверів тихо ігнорують вузький заголовок Accept і надсилають свою відповідь за замовчуванням, тому справжній 406 трапляється рідше за сам заголовок.

Як з'являється помилка

Браузер рідко спричиняє 406 під час звичайного завантаження сторінок, оскільки браузери надсилають поблажливі заголовки Accept, що збігаються майже з будь-чим, що пропонує сервер. Значно частіше вона трапляється від API-клієнтів, скриптів і інструментів командного рядка, що встановлюють жорсткий заголовок Accept:

curl -i -H "Accept: application/xml" https://api.example.com/v1/status
HTTP/1.1 406 Not Acceptable
Content-Type: application/json

У цьому прикладі клієнт запросив лише XML, а API може створювати лише JSON, тож сервер відмовляє, а не надсилає формат, який клієнт явно сказав, що не хоче.

Що спричиняє 406 Not Acceptable

  • Справжній збій узгодження вмісту. Заголовок Accept, Accept-Language чи Accept-Encoding, що називає лише формати, які сервер не може створити, найчастіше клієнт, що запитує XML у JSON-лише API, чи конкретний мовний варіант, якого в сервера немає.
  • Веб-фаєрвол застосунків на спільному хостингу. Це дуже поширена реальна причина, що не має жодного стосунку до узгодження вмісту: ModSecurity й подібні правила WAF у середовищах спільного хостингу блокують запити, чий заголовок Accept виглядає незвично, відсутнім чи автоматизованим, і відповідають 406 як відповіддю блокування незалежно від того, що узгоджувалося.
  • API, що обслуговує лише JSON, отримує запит із клієнта, який надсилає Accept: text/html. Деякі API суворі щодо цього й відмовляють, а не деградують, що проявляється як 406 для будь-якого клієнта, включно з вкладкою браузера, відкритою напряму на ендпоінті.
  • Неправильно налаштоване правило зворотного проксі чи CDN, що перевіряє й відхиляє на основі заголовка Accept з міркувань кешування чи фільтрації ботів, не пов'язаних з тим, що може створити origin-сервер.
  • Надто сувора обробка Accept-Encoding. Сервер, налаштований відмовляти в будь-якому запиті, що не перелічує метод стиснення, якому він надає перевагу, замість відкату до нестисненої відповіді.

Як зрозуміти, хто винен

Якщо лише конкретний скрипт чи інтеграція натрапляє на 406, перевірте, що кажуть його заголовки Accept, оскільки звужений чи неправильно налаштований заголовок на боці клієнта часто пряма причина. Якщо той самий запит працює зі звичайним, поблажливим заголовком Accept, але провалюється з конкретним, сервер справді не може обслужити той формат. Якщо зачеплений також звичайний трафік браузера, чи помилка почалася одразу після зміни хостингу чи WAF без жодної зміни коду з вашого боку, правила безпеки спільного хостингу - більш імовірний винуватець, і запуск HTTP-перевірки з кількох локацій із точними заголовками, які надсилає ваша інтеграція, - найшвидший спосіб підтвердити, чи блокування стабільне, чи специфічне для однієї мережі.

Як виправити 406 Not Acceptable

Якщо ви відвідувач

  1. Приберіть чи послабте заголовок Accept у скрипті чи інструменті, що робить запит, якщо ви його контролюєте, і дозвольте йому прийняти формат за замовчуванням, який пропонує сервер.
  2. Перевірте документацію API щодо того, які типи вмісту й мови він підтримує, перш ніж припускати, що сервер зламаний.
  3. Спробуйте запит напряму з браузера, оскільки браузери надсилають широкі заголовки Accept і рідко натрапляють на цю помилку, що допомагає підтвердити, що блокування специфічне для заголовків вашого клієнта.

Якщо ви керуєте сайтом

  1. Спершу перевірте свої правила ModSecurity чи WAF, якщо 406 несподіваний і поширений, оскільки середовища спільного хостингу часто блокують за патернами заголовка Accept, а не через справжній збій узгодження. Погляньте на власні логи WAF щодо ідентифікатора правила, що спрацювало, перш ніж торкатися коду застосунку.
  2. Підтвердьте, які формати ваш API справді обслуговує, і або підтримайте більше з того, що запитують реальні клієнти, або чітко задокументуйте вимогу, щоб 406 був інформативним, а не несподіваним.
  3. Відкочуйтеся до подання за замовчуванням замість повної відмови, там де це прийнятно для вашого API, оскільки більшість реальних клієнтів краще обробляють "ось JSON, хоча ви запитували широко," ніж пряму відмову.
  4. Перевіряйте правила зворотного проксі й CDN на щось, що перевіряє заголовок Accept для кешування чи керування ботами, оскільки правило, призначене для однієї мети, може дати 406 як побічний ефект для непов'язаного трафіку.

Як запобігти, щоб 406 не поклав інтеграцію

406, введений оновленням безпеки хостинг-провайдера чи новим правилом WAF, не виглядатиме як збій зсередини вашої власної мережі, оскільки ваші власні запити можуть використовувати інші заголовки, ніж постраждала інтеграція. Запланована HTTP-перевірка, що надсилає той самий заголовок Accept, який використовують ваші реальні клієнти, з умовою на очікуваний код статусу, ловить збій узгодження тієї миті, коли він починається. Перевірка з кількох локацій також допомагає відділити правило WAF на весь хостинг від того, що застосовується лише на певних edge-вузлах.

Пов'язані помилки

Дивіться 403 Forbidden для тісно пов'язаного випадку, коли WAF чи правило проти ботів прямо блокує запит, а не через узгодження вмісту, огляд 4xx для ширшої родини, і 413 Payload Too Large деінде в цій партії.

Часті запитання

Чи 406 - це те саме, що помилка CORS?

Ні. Збої CORS трапляються тому, що браузер відмовляється показувати міждоменну відповідь скрипту, що її викликав; 406 - це сам сервер, що відмовляється взагалі створювати тіло відповіді, бо не може задовольнити запитуваний формат, мову чи кодування.

Чому я бачу 406 лише з curl чи Postman, ніколи з браузера?

Браузери за замовчуванням надсилають широкі, поблажливі заголовки Accept. Інструменти на кшталт curl не надсилають нічого чи вузький заголовок, якщо ви не встановите його явно, що значно ймовірніше спричиняє справжній збій узгодження чи спрацьовує правило WAF, налаштоване позначати незвичні заголовки.

Чи може 406 прийти від ModSecurity, навіть якщо мій заголовок Accept цілком нормальний?

Так. Багато наборів правил ModSecurity на спільному хостингу позначають запити як автоматизовані на основі комбінації сигналів, включно з точною структурою й порядком заголовків Accept, і відповідають 406 як загальною відповіддю блокування, а не тому, що узгодження вмісту справді провалилося.

Чи має мій API повертати 406, чи просто відкочуватися до JSON за замовчуванням?

Відкат до розумного формату за замовчуванням дружніший до реальних клієнтів, і саме так робить більшість продакшн-API. Повернення 406 виправдане, коли мовчазна видача неправильного формату активно вводила б викликача в оману.

Яка різниця між 406 і 415?

406 стосується того, що клієнт може прийняти у відповіді. 415 Unsupported Media Type стосується того, що сервер може прийняти в тілі запиту, яке надіслав клієнт. Вони охоплюють протилежні напрямки тієї самої ідеї узгодження.

Перевірити зараз

Запустіть безкоштовну перевірку власного сайту - обліковий запис не потрібен.

HTTP check

Стежити за цим постійно

Отримуйте сповіщення в момент збою: HostTracker перевіряє з понад 300 локацій і повідомляє вас електронною поштою, SMS, у Slack, Telegram та інших каналах.

Можливості HostTracker

Ще в цьому розділі: Коди статусу HTTP пояснено