blob: f8ae57b0aaa89294ebab7b189467d02b515aef16 [file] [log] [blame]
The read_complete flag lets us know if all of the wrapped file's data
has been read. We want to know this because Browser.back() must
.reload() the response if not.
I've noted here the various cases where .read_complete may be set.
>>> import mechanize
>>> text = "To err is human, to moo, bovine.\n"*10
>>> def get_wrapper():
... import cStringIO
... from mechanize._response import seek_wrapper
... f = cStringIO.StringIO(text)
... wr = seek_wrapper(f)
... return wr
.read() case #1
>>> wr = get_wrapper()
>>> wr.read_complete
False
>>> junk = wr.read()
>>> wr.read_complete
True
>>> wr.seek(0)
>>> wr.read_complete
True
Excercise partial .read() and .readline(), and .seek() case #1
>>> wr = get_wrapper()
>>> junk = wr.read(10)
>>> wr.read_complete
False
>>> junk = wr.readline()
>>> wr.read_complete
False
>>> wr.seek(0, 2)
>>> wr.read_complete
True
>>> wr.seek(0)
>>> wr.read_complete
True
.readlines() case #1
>>> wr = get_wrapper()
>>> junk = wr.readlines()
>>> wr.read_complete
True
>>> wr.seek(0)
>>> wr.read_complete
True
.seek() case #2
>>> wr = get_wrapper()
>>> wr.seek(10)
>>> wr.read_complete
False
>>> wr.seek(1000000)
.read() case #2
>>> wr = get_wrapper()
>>> junk = wr.read(1000000)
>>> wr.read_complete # we read to the end, but don't know it yet
False
>>> junk = wr.read(10)
>>> wr.read_complete
True
.readline() case #1
>>> wr = get_wrapper()
>>> junk = wr.read(len(text)-10)
>>> wr.read_complete
False
>>> junk = wr.readline()
>>> wr.read_complete # we read to the end, but don't know it yet
False
>>> junk = wr.readline()
>>> wr.read_complete
True
Test copying and sharing of .read_complete state
>>> import copy
>>> wr = get_wrapper()
>>> wr2 = copy.copy(wr)
>>> wr.read_complete
False
>>> wr2.read_complete
False
>>> junk = wr2.read()
>>> wr.read_complete
True
>>> wr2.read_complete
True
Fix from -r36082: .read() after .close() used to break
.read_complete state
>>> from mechanize._response import test_response
>>> r = test_response(text)
>>> junk = r.read(64)
>>> r.close()
>>> r.read_complete
False
>>> r.read()
''
>>> r.read_complete
False
Tests for the truly horrendous upgrade_response()
>>> def is_response(r):
... names = "get_data read readline readlines close seek code msg".split()
... for name in names:
... if not hasattr(r, name):
... return False
... return r.get_data() == "test data"
>>> from cStringIO import StringIO
>>> from mechanize._response import upgrade_response, make_headers, \
... make_response, closeable_response, seek_wrapper
>>> data="test data"; url="http://example.com/"; code=200; msg="OK"
Normal response (closeable_response wrapped with seek_wrapper): return a copy
>>> r1 = make_response(data, [], url, code, msg)
>>> r2 = upgrade_response(r1)
>>> is_response(r2)
True
>>> r1 is not r2
True
>>> r1.wrapped is r2.wrapped
True
closeable_response with no seek_wrapper: wrap with seek_wrapper
>>> r1 = closeable_response(StringIO(data), make_headers([]), url, code, msg)
>>> is_response(r1)
False
>>> r2 = upgrade_response(r1)
>>> is_response(r2)
True
>>> r1 is not r2
True
>>> r1 is r2.wrapped
True
addinfourl: extract .fp and wrap it with closeable_response and
seek_wrapper
>>> from mechanize._urllib2_fork import addinfourl
>>> r1= addinfourl(StringIO(data), make_headers([]), url)
>>> is_response(r1)
False
>>> r2 = upgrade_response(r1)
>>> is_response(r2)
True
>>> r1 is not r2
True
>>> r1 is not r2.wrapped
True
>>> r1.fp is r2.wrapped.fp
True
addinfourl with code, msg
>>> r1= addinfourl(StringIO(data), make_headers([]), url)
>>> r1.code = 206
>>> r1.msg = "cool"
>>> r2 = upgrade_response(r1)
>>> is_response(r2)
True
>>> r2.code == r1.code
True
>>> r2.msg == r1.msg
True
addinfourl with seek wrapper: cached data is not lost
>>> r1= addinfourl(StringIO(data), make_headers([]), url)
>>> r1 = seek_wrapper(r1)
>>> r1.read(4)
'test'
>>> r2 = upgrade_response(r1)
>>> is_response(r2)
True
addinfourl wrapped with HTTPError -- remains an HTTPError of the same
subclass (through horrible trickery)
>>> hdrs = make_headers([])
>>> r1 = addinfourl(StringIO(data), hdrs, url)
>>> class MyHTTPError(mechanize.HTTPError): pass
>>> r1 = MyHTTPError(url, code, msg, hdrs, r1)
>>> is_response(r1)
False
>>> r2 = upgrade_response(r1)
>>> is_response(r2)
True
>>> isinstance(r2, MyHTTPError)
True
>>> r2 # doctest: +ELLIPSIS
<httperror_seek_wrapper (MyHTTPError instance) at ...
The trickery does not cause double-wrapping
>>> r3 = upgrade_response(r2)
>>> is_response(r3)
True
>>> r3 is not r2
True
>>> r3.wrapped is r2.wrapped
True
Test dynamically-created class __repr__ for case where we have the
module name
>>> r4 = addinfourl(StringIO(data), hdrs, url)
>>> r4 = mechanize.HTTPError(url, code, msg, hdrs, r4)
>>> upgrade_response(r4) # doctest: +ELLIPSIS
<httperror_seek_wrapper (urllib2.HTTPError instance) at ...