Форум сайта python.su
5
Подскажите, пожалуйста - как сделать так, чтобы нормально принимались url с кириллическими символами?
На гугле не забанили, но не могу найти ничего толкового - для 2.7 предлагают различные варианты, для третьего ничего нет.
Побовала urllib.quote, как описано здесь - не работает.
# -*- coding: cp1251 -*- from urllib.parse import quote import urllib.request url = 'http://кто.рф/' #Адрес взят просто от балды как пример кириллического домена urllib.request.urlopen(quote(url)).read()
Traceback (most recent call last):Также не дают результата encode, decode, urlencode. Ну или я не понимаю, как ими пользоваться, хотя тут понимать, кажется, нечего. А все должно быть предельно просто, кириллицы в линках ведь уйма…
File “C:\Users\User\PycharmProjects\rating\Files\1.py”, line 7, in <module>
urllib.request.urlopen(quote(url)).read()
File “C:\Python34\lib\urllib\request.py”, line 161, in urlopen
return opener.open(url, data, timeout)
File “C:\Python34\lib\urllib\request.py”, line 448, in open
req = Request(fullurl, data)
File “C:\Python34\lib\urllib\request.py”, line 266, in __init__
self.full_url = url
File “C:\Python34\lib\urllib\request.py”, line 292, in full_url
self._parse()
File “C:\Python34\lib\urllib\request.py”, line 321, in _parse
raise ValueError(“unknown url type: %r” % self.full_url)
ValueError: unknown url type: ‘http%3A//%D0%BA%D1%82%D0%BE.%D1%80%D1%84/’
Отредактировано Elaphe (Май 2, 2015 20:45:19)
Офлайн
quote нужно использовать только для части URL, идущей после домена.
Для домена нужно использовать другой метод кодировки. Если в домене есть не-ascii символы, используйте idna кодировку.
Вот вам код для создания своего решения:
from urllib.parse import quote, urlsplit, urlunsplit import urllib.request url = 'http://кто.рф/ел?моей=ложкой' parts = list(urlsplit(url)) parts[0] = quote(parts[0], safe=':/?&') parts[1] = parts[1].encode('idna').decode('ascii') parts[2] = quote(parts[2], safe=':/?&') parts[3] = quote(parts[3], safe=':/?&') parts[4] = quote(parts[4], safe=':/?&') url = urlunsplit(parts) data = urllib.request.urlopen(url).read()
Офлайн
5
Спасибо за ответ.
Примерно так я тоже пробовала (примерно - потому что не использовала urlsplit, urlunsplit, там запрос позволяет обойтись без него). В итоге, к сожалению, получается нерабочая ссылка. Видимо, дело в кодировке, только как проблему решить - пока неясно. Буду рыть дальше…
Офлайн
5
Подсказали.
Если кодировка не utf8, то строку нужно декодировать. В моем случае для нужной части url сработал такой код:
parts[3] = quote(parts[3].encode('cp1251'), safe=':/?=&')
Офлайн