Issue #10791: Implement missing method GzipFile.read1(), allowing GzipFile

to be wrapped in a TextIOWrapper.  Patch by Nadeem Vawda.
This commit is contained in:
Antoine Pitrou 2011-04-04 21:00:37 +02:00
parent 457cdf5e96
commit 4ec4b0c041
3 changed files with 48 additions and 0 deletions

View File

@ -348,6 +348,28 @@ class GzipFile(io.BufferedIOBase):
self.offset += size self.offset += size
return chunk return chunk
def read1(self, size=-1):
self._check_closed()
if self.mode != READ:
import errno
raise IOError(errno.EBADF, "read1() on write-only GzipFile object")
if self.extrasize <= 0 and self.fileobj is None:
return b''
try:
self._read()
except EOFError:
pass
if size < 0 or size > self.extrasize:
size = self.extrasize
offset = self.offset - self.extrastart
chunk = self.extrabuf[offset: offset + size]
self.extrasize -= size
self.offset += size
return chunk
def peek(self, n): def peek(self, n):
if self.mode != READ: if self.mode != READ:
import errno import errno

View File

@ -64,6 +64,21 @@ class TestGzip(unittest.TestCase):
d = f.read() d = f.read()
self.assertEqual(d, data1*50) self.assertEqual(d, data1*50)
def test_read1(self):
self.test_write()
blocks = []
nread = 0
with gzip.GzipFile(self.filename, 'r') as f:
while True:
d = f.read1()
if not d:
break
blocks.append(d)
nread += len(d)
# Check that position was updated correctly (see issue10791).
self.assertEqual(f.tell(), nread)
self.assertEqual(b''.join(blocks), data1 * 50)
def test_io_on_closed_object(self): def test_io_on_closed_object(self):
# Test that I/O operations on closed GzipFile objects raise a # Test that I/O operations on closed GzipFile objects raise a
# ValueError, just like the corresponding functions on file objects. # ValueError, just like the corresponding functions on file objects.
@ -323,6 +338,14 @@ class TestGzip(unittest.TestCase):
self.assertEqual(f.read(100), b'') self.assertEqual(f.read(100), b'')
self.assertEqual(nread, len(uncompressed)) self.assertEqual(nread, len(uncompressed))
def test_textio_readlines(self):
# Issue #10791: TextIOWrapper.readlines() fails when wrapping GzipFile.
lines = (data1 * 50).decode("ascii").splitlines(True)
self.test_write()
with gzip.GzipFile(self.filename, 'r') as f:
with io.TextIOWrapper(f, encoding="ascii") as t:
self.assertEqual(t.readlines(), lines)
# Testing compress/decompress shortcut functions # Testing compress/decompress shortcut functions
def test_compress(self): def test_compress(self):

View File

@ -87,6 +87,9 @@ Core and Builtins
Library Library
------- -------
- Issue #10791: Implement missing method GzipFile.read1(), allowing GzipFile
to be wrapped in a TextIOWrapper. Patch by Nadeem Vawda.
- Issue #11688: Add sqlite3.Connection.set_trace_callback(). Patch by - Issue #11688: Add sqlite3.Connection.set_trace_callback(). Patch by
Torsten Landschoff. Torsten Landschoff.