Двухбуквенные домены и ИЕ

Про проблему с двухбуквенными доменами в браузере Микрософта знают наверное, очень многие. Если вкратце, считается, что на двухбуквенных доменах второго уровня «Эксплорер» не ставит куки.

Отчасти так оно и есть.

Сделано это вот для чего. Некоторые страны (например, Великобритания) запрещают регистацию домена второго уровня для своих нужд, домен должен находиться на третьем уровне в зоне специальных доменов второго уровня. Если бы я родился и жил в Лондоне, мой блог мог бы располагаться по адресу bolknote.co.uk.

Вот отсюда и родилось это ограничение — так как на домене третьего уровня в некоторых странах располагается куча чужих друг другу сайтов, они могли бы читать и писать куки друг друга через общий домен (и воровать данные авторизации, например), но браузеры не озаботились механизмом предотвращения этой угрозы.

В «Экплорере» (скорее всего это произошло в шестой версии) защиту устроили просто — если в домене второго уровня две буквы и он не располагается на домене общего назначения (.com, .net и т. п.), то это специальный домен из вышеописанного случая и ставить куку на него нельзя.

Но тогда как же, чёрт возьми, поступает «Яндекс» со своих двухбуквенным «ya.ru»? Есть какая-то особая магия?

Разочарую — её нет, есть исключения.

Ребята из «Микрософта» через какое-то время поняли, что проверять домен на двухбуквенность — плохая идея, оказалось, что существуют двухбуквенные домены без специального значения и специальные домены с другим количеством букв (например — географические домены). Пришлось встроить в браузер список исключений, найти его можно по урлу res://urlmon.dll/ietldlist.xml.

Список исключений в IE (41.52КиБ)

Т. е. если домен встречается в теге «tld» или содержит только две буквы на втором уровне, то куку ставить нельзя, но если он встретился в теге «domain» — то можно. Посмотрите на скриншот, домен «Яндекса» содержится в списке исключений. Естественно, список может меняться при обновлении браузера.

Остальным браузерам так же приходится решать эту проблему. Например, ФФ содержит примерно такой же список:

# примерное количество значений в этом списке у ФФ:
bolk@Bolk ~  $ grep -aF chel.ru /Applications/Firefox.app/Contents/MacOS/XUL  |  strings | fgrep . | fgrep -v / | sort -u | wc -l
   4019

# двадцать последних (по алфавиту) значений:
bolk@Bolk ~  $ grep -aF chel.ru /Applications/Firefox.app/Contents/MacOS/XUL  |  strings | fgrep . | fgrep -v / | sort -u | tail -20
z.bg
z.se
za.com
za.net
za.org
zachpomor.pl
zagan.pl
zakopane.pl
zaporizhzhe.ua
zarow.pl
zgora.pl
zgorzelec.pl
zgrad.ru
zhitomir.ua
zj.cn
zlg.br
zoological.museum
zoology.museum
zp.ua
zt.ua

Не знаю все ли четыре тысячи относятся к обсуждаемому списку (кстати, в нём всего 133 российских домена), но такой список точно существует.

Тот же список есть и в «Хроме» (на моём «Маке» он содержится в файле «Google Chrome Framework» и состоит из более 3,5 тысяч значений), в «Сафари» ничего похожего я обнаружить не смог, то ли такого механизма там нет, то ли спрятано глубже, чем мне позволяет искать моя лень. «Опера» держит свой список в файле «public_domains.dat», в нём на настоящий момент 4291 значение.

Таким образом, если вы владелец двухбуквенного домена и вам не повезло, у вас не работают куки как положено, пишите на адреса техподдержки производителей браузеров, а пока делайте редирект на домен третьего уровня (например, на «www»).

Комментарии 28

Виталий № 1
Для этих целей существует список Public Suffix List ( http://publicsuffix.org/learn/ ), на который, как утверждается, ориентируются Mozilla, Chrome и Opera.
Виктор № 2
Что-то я не нахожу домен hh.ru :)
Евгений Степанищев (bolknote.ru) автор № 5
Что-то я не нахожу домен hh.ru :)

Видимо они не заморачиваются с установкой кук на корневой домен:

bolk@Bolk ~ $ telnet hh.ru 80
Trying 94.124.200.86…
Connected to hh.ru.
Escape character is '^]'.
GET / HTTP/1.0
Host: kazan.hh.ru

HTTP/1.1 200 OK
Server: nginx/1.2.0
Date: Tue, 17 Jul 2012 19:35:34 GMT
Content-Type: text/html; charset=utf-8
Content-Length: 61518
Connection: close
Set-Cookie: hhrole=anonymous; Path=/
Set-Cookie: unique_banner_user=1342553734.358669954861416; expires=Wed, 18 Jul 2012 19:35:34 GMT; Path=/
Set-Cookie: unique_banner_user=1342553734.351531650608922; expires=Wed, 18 Jul 2012 19:35:34 GMT; Path=/
Expires: Tue, 17 Jul 2012 19:35:33 GMT
Cache-Control: no-cache
X-Request-ID: ab1f4b6b1d93688e17e7bbcfb46f1bfb
Евгений Степанищев (bolknote.ru) автор № 3
Видимо, они его с разной скоростью в браузерах обновляют.
Павел (blog.ad.by) № 8
Спасибо, интересная информация. Правда, с современной точки зрения голый домен — это пережиток прошлого, префикс www всегда будет нужен в обозримом будущем. Так что не вижу смысла писать разработчикам.
Andrey Nikanorov № 10
Вот мне тоже интересно, про «пережиток прошлого». Я бы сказал, что www — пережиток. Да и зачем он нужен то?
shaltai-boltai № 11
Интересно, сами-то британцы довольны таким запретом? Хотели как лучше.. и сами же учинили нехилый бардак на этом втором уровне.

Зачем, спрашивается, из-за странных людей усложнять жизнь всем остальным?
Евгений Степанищев (bolknote.ru) автор № 13
Зачем, спрашивается, из-за странных людей усложнять жизнь всем остальным?

Не только британцы этим страдают. Минимум три домена — uk, us и nl. nl вообще один из первых национальных доменов, возможно тогда так принято было.

Данила № 12
Проблемы со _ВСЕМИ_ двухсимвольными доменами есть только в IE. Остальные браузеры, ориентируясь на Public Suffix List не имеют особой проблемы, потому что запрещают ставить только на действительно публичные домены (вроде pp.ru или т.н. «геодоменов», вроде e-burg.ru). Собственно, поэтому они и не очень часто обновляются — там мейнтейнится список запретов, а не исключений.

Что касается «IE не ставит» — это тоже не совсем так. Он не ставит куку, если видит заголовок Set-Cookie с явно указанным «запретным» domain. И прекрасно ставит, если domain не указан, более того — в нарушение стандарта эту же куку показывает на всех субдоменах.
Евгений Степанищев (bolknote.ru) автор № 14
Проблемы со всеми двухсимвольными доменами есть только в IE.

Нет в IE проблем со всеми доменами, я об этом целую заметку написал.

Остальные браузеры, ориентируясь на Public Suffix List не имеют особой проблемы, потому что запрещают ставить только на действительно публичные домены (вроде pp.ru или т.н. «геодоменов», вроде e-burg.ru). Собственно, поэтому они и не очень часто обновляются — там мейнтейнится список запретов, а не исключений.

Нет, это не так. Исключения там тоже есть. Они начинаются с восклицательного знака, например:

*.ar
!congresodelalengua3.ar
!educ.ar
!gobiernoelectronico.ar
!mecon.ar

-

Что касается «IE не ставит» — это тоже не совсем так. Он не ставит куку, если видит заголовок Set-Cookie с явно указанным «запретным» domain.

Где-то можно прочитать про чьи-нибудь эксперименты на эту тему?

Евгений Степанищев (bolknote.ru) автор № 15
Он не ставит куку, если видит заголовок Set-Cookie с явно указанным «запретным» domain.

Сомневаюсь, что это так. Иначе неясно с чего бы «Яндекс» указывал домен на ya.ru:

HEAD / HTTP/1.1
Host: ya.ru

HTTP/1.1 200 Ok
Server: nginx
Date: Wed, 18 Jul 2012 04:58:34 GMT
Content-Type: text/html; charset=UTF-8
Content-Length: 4193
Connection: close
Cache-Control: no-cache,no-store,max-age=0,must-revalidate
Expires: Wed, 18 Jul 2012 04:58:34 GMT
Last-Modified: Wed, 18 Jul 2012 04:58:34 GMT
P3P: policyref="/w3c/p3p.xml", CP="NON DSP ADM DEV PSD IVDo OUR IND STP PHY PRE NAV UNI"
Set-Cookie: yandexuid=6413745831342587514; Expires=Sat, 16-Jul-2022 04:58:34 GMT; Domain=.ya.ru; Path=/
Данила № 16

Для лучшего понимания контекста — я тот человек, по вопросу которого на хабре ты эту запись написал.
В оригинальном вопросе на хабре ( http://habrahabr.ru/qa/21647/ ) как раз немного обсуждается, как оно работает.

Нет в IE проблем со всеми доменами, я об этом целую заметку написал.

Ок, со всеми двухсимвольными, кроме исключений.

Нет, это не так. Исключения там тоже есть. Они начинаются с восклицательного знака.

Насколько я понимаю, они начинаются с восклицательного знака, отменяя наложенное ранее «широкое» правило из этого же списка.
Т.е. СНАЧАЛА *.ar — все домены второго уровня в TLD ar объявляются «публичными» (куку не ставить), а потом !educ.ar — отменяет это правило. Т.е. это не «исключения», о которых я говорил. Public Suffix List содержит список «куда не ставить» и браузеры, которые им пользуются — не имеют других соображений о том «куда не ставить», в отличие от IE.

Где-то можно прочитать про чьи-нибудь эксперименты на эту тему?

Можно в комментариях мои слова прочитать — у меня как раз пара двухсимвольных доменов есть.
Да собственно можешь сам попробовать — http://66.ru/test/iframe/index.php ифреймы показывают текущие куки, а http://66.ru/test/iframe/index.php?set=bolk попробует поставить куку в разных вариантах. Можно так же позаходить на http://www.66.ru/test/iframe/index.php и http://other.66.ru/test/iframe/index.php и попробовать поставить куки оттуда разными браузерами.

Сомневаюсь, что это так. Иначе неясно с чего бы «Яндекс» указывал домен на ya.ru:

Яндекс указывает домен на .ya.ru (на не на ya.ru) потому что ya.ru в списке исключений IE и работает как любой другой домен.

Данила № 17
В «Экплорер» (скорее всего это произошло в шестой версии) защиту устроили просто — если в домене второго уровня две буквы, то это специальный домен из вышеописанного случая и ставить куку на него нельзя.

Кстати говоря, эта логика со времен шестого эксплорера довольно заметно изменилась — например в .gr и .pl современный IE соглашается ставить куки на любой двухсимвольный домен второго уровня.

Евгений Степанищев (bolknote.ru) автор № 19
Комментарий для Данила:

Ага, спасибо за ссылки, буду экспериментировать как только найду где-нибудь IE.
Евгений Степанищев (bolknote.ru) автор № 20

Комментарий для Данила:

Яндекс указывает домен на .ya.ru (на не на ya.ru) потому что ya.ru в списке исключений IE

В списке исключений он ведь только с восьмой версии. А есть ещё шестая и седьмая.

Данила № 22

Комментарий для Евгения Степанищева:

В списке исключений он ведь только с восьмой версии. А есть ещё шестая и седьмая.

Судя по всему, Яндекс положил болт. В шестом IE при заходе на ya.ru — кука на ya.ru не ставится.

Евгений Степанищев (bolknote.ru) автор № 23
Комментарий для Данила:

Ага, понятно.

Я поспрашивал ребят из «Яндекса», но найти того, кто владеет информацией про короткий домен непросто (в смысле на какой браузер забили).
Данила № 26
А еще есть vk.com, 6-го IE только под рукой нет чтобы проверить :)

к .com это не относится.

twitter.com/thenameisbusy № 27
Комментарий для Данила:

Прощу прощения, промахнулся.

В Сафари под виндой есть файл
C:\Program Files\Safari\Safari.resources\TopLevelDomains.plist

расшарил, кому интересно --
https://docs.google.com/open?id=0BzMtX0bME … mQxTlJ0Y0U
Евгений Степанищев (bolknote.ru) автор № 28
Ага, нашёл такой файл на «Маке», спасибо. Вот тут хранится:

/System/Library/PrivateFrameworks/Safari.framework/Versions/A/Resources/TopLevelDomains.plist