Форум сайта python.su
интересно, а может ли urllib скачивать ответ сервера в gzip и разжимать его?
или, т.к. он не посылает хидер - Accept-Encoding: gzip,deflate - сервер отдает ему ответ несжатым
но можно ли научить urllib принимать gzip?
Офлайн
ИгнатТеоретически да, но это не всегда так, не все сервера следуют стандарту - некоторые отдают gzip всегда.
т.к. он не посылает хидер - Accept-Encoding: gzip,deflate - сервер отдает ему ответ несжатым
ИгнатВот например: http://diveintopython.org/http_web_services/gzip_compression.html
но можно ли научить urllib принимать gzip?
Офлайн
спасибо
написал такой пример:
import urllib.request as req
import http.client
import io
from gzip import GzipFile
http.client.HTTPConnection.debuglevel = 1
request = req.Request('http://www.thedowntown.ru')
request.add_header('Accept-encoding', 'gzip')
opener = req.build_opener()
f = opener.open(request)
data = f.read().decode('utf-8', 'ignore')
compressedstream = io.StringIO(data)
gzipper = GzipFile(fileobj=compressedstream)
data = gzipper.read()
send: b'GET / HTTP/1.1\r\nHost: www.thedowntown.ru\r\nUser-Agent: Python-urllib/3.2\r\nConnection: close\r\nAccept-Encoding: gzip\r\n\r\n'
reply: 'HTTP/1.1 200 OK\r\n'
header: Server header: Date header: Content-Type header: Transfer-Encoding header: Connection header: X-Powered-By header: Expires header: Last-Modified header: Cache-Control header: Accept-Encoding header: Pragma header: Set-Cookie header: Content-Encoding header: Vary ENCODING: gzip
Traceback (most recent call last):
File "/home/python3/gzip_test.py", line 21, in <module>
data = gzipper.read()
File "/usr/local/lib/python3.2/gzip.py", line 331, in read
self._read(readsize)
File "/usr/local/lib/python3.2/gzip.py", line 385, in _read
self._read_gzip_header()
File "/usr/local/lib/python3.2/gzip.py", line 257, in _read_gzip_header
magic = self.fileobj.read(2)
File "/usr/local/lib/python3.2/gzip.py", line 70, in read
self.file.read(size-self._length+read)
TypeError: can't concat bytes to str
Офлайн
Игнат, да научитесь же наконец работе с байтами и строками!
Получаете HTTPResponse, который io.RawIOBase — так что вам ещё нужно? Какого чорта тянете его в строку через urf-8, потом StringIO? Чтобы получить TypeError в итоге?
Нет, вы не перестаёте меня восхищать!
Офлайн
где RawIOBase? (даже если бы я знал что это такое)
data = f.read()#.decode('utf-8', 'ignore')
print(type(data)) --> <class 'bytes'>
print(http.client.HTTPResponse)
print(type(http.client.HTTPResponse))
<class 'http.client.HTTPResponse'>
<class 'abc.ABCMeta'>
Офлайн
заработало, но при помощи zlib
да и код с zlib куда приятнее и понятнее
выложу на всякий случай:
import urllib.request as req
import http.client
import zlib
#http.client.HTTPConnection.debuglevel = 1
def test(gzip=False):
request = req.Request('http://www.thedowntown.ru')
if gzip:
request.add_header('Accept-encoding', 'gzip, deflate')
opener = req.build_opener()
f = opener.open(request)
isGzip = f.headers.get('Content-Encoding')
data_src = f.read()
if isGzip == 'gzip':
print('is GZIP!')
data = zlib.decompress(data_src, 16+zlib.MAX_WBITS)
else:
print('its NOT GZIP!')
data = data_src
data = data.decode('utf-8', 'ignore')
print('downloaded: %d bytes' % len(data_src))
print('decompressed: %d bytes' % len(data))
print('-'*40)
test() # without gzip
test(True) #with gzip
its NOT GZIP!
downloaded: 13133 bytes
decompressed: 10366 bytes
----------------------------------------
is GZIP!
downloaded: 4731 bytes
decompressed: 10366 bytes
----------------------------------------
Отредактировано (Апрель 6, 2011 14:15:34)
Офлайн
print(http.client.HTTPResponse.__mro__)
f = opener.open(request)
gzipper = GzipFile(fileobj=f)
data = gzipper.read()
Офлайн