bpo-34898: Add mtime parameter to gzip.compress(). (GH-9704)
Without setting mtime, time.time() will be used as the timestamp which will end up in the compressed data and each invocation of the compress() function will vary over time.
This commit is contained in:
parent
d2b11af915
commit
0e7497cb46
|
@ -157,13 +157,15 @@ The module defines the following items:
|
|||
Accepts a :term:`path-like object`.
|
||||
|
||||
|
||||
.. function:: compress(data, compresslevel=9)
|
||||
.. function:: compress(data, compresslevel=9, *, mtime=None)
|
||||
|
||||
Compress the *data*, returning a :class:`bytes` object containing
|
||||
the compressed data. *compresslevel* has the same meaning as in
|
||||
the compressed data. *compresslevel* and *mtime* have the same meaning as in
|
||||
the :class:`GzipFile` constructor above.
|
||||
|
||||
.. versionadded:: 3.2
|
||||
.. versionchanged:: 3.8
|
||||
Added the *mtime* parameter for reproducible output.
|
||||
|
||||
.. function:: decompress(data)
|
||||
|
||||
|
|
|
@ -131,6 +131,13 @@ asyncio
|
|||
On Windows, the default event loop is now :class:`~asyncio.ProactorEventLoop`.
|
||||
|
||||
|
||||
gzip
|
||||
----
|
||||
|
||||
Added the *mtime* parameter to :func:`gzip.compress` for reproducible output.
|
||||
(Contributed by Guo Ci Teo in :issue:`34898`.)
|
||||
|
||||
|
||||
idlelib and IDLE
|
||||
----------------
|
||||
|
||||
|
|
|
@ -520,12 +520,12 @@ class _GzipReader(_compression.DecompressReader):
|
|||
super()._rewind()
|
||||
self._new_member = True
|
||||
|
||||
def compress(data, compresslevel=_COMPRESS_LEVEL_BEST):
|
||||
def compress(data, compresslevel=_COMPRESS_LEVEL_BEST, *, mtime=None):
|
||||
"""Compress data in one shot and return the compressed string.
|
||||
Optional argument is the compression level, in range of 0-9.
|
||||
"""
|
||||
buf = io.BytesIO()
|
||||
with GzipFile(fileobj=buf, mode='wb', compresslevel=compresslevel) as f:
|
||||
with GzipFile(fileobj=buf, mode='wb', compresslevel=compresslevel, mtime=mtime) as f:
|
||||
f.write(data)
|
||||
return buf.getvalue()
|
||||
|
||||
|
|
|
@ -499,6 +499,17 @@ class TestGzip(BaseTest):
|
|||
with gzip.GzipFile(fileobj=io.BytesIO(datac), mode="rb") as f:
|
||||
self.assertEqual(f.read(), data)
|
||||
|
||||
def test_compress_mtime(self):
|
||||
mtime = 123456789
|
||||
for data in [data1, data2]:
|
||||
for args in [(), (1,), (6,), (9,)]:
|
||||
with self.subTest(data=data, args=args):
|
||||
datac = gzip.compress(data, *args, mtime=mtime)
|
||||
self.assertEqual(type(datac), bytes)
|
||||
with gzip.GzipFile(fileobj=io.BytesIO(datac), mode="rb") as f:
|
||||
f.read(1) # to set mtime attribute
|
||||
self.assertEqual(f.mtime, mtime)
|
||||
|
||||
def test_decompress(self):
|
||||
for data in (data1, data2):
|
||||
buf = io.BytesIO()
|
||||
|
|
|
@ -1615,6 +1615,7 @@ Monty Taylor
|
|||
Anatoly Techtonik
|
||||
Martin Teichmann
|
||||
Gustavo Temple
|
||||
Guo Ci Teo
|
||||
Mikhail Terekhov
|
||||
Victor Terrón
|
||||
Pablo Galindo
|
||||
|
|
|
@ -0,0 +1,2 @@
|
|||
Add `mtime` argument to `gzip.compress` for reproducible output.
|
||||
Patch by Guo Ci Teo.
|
Loading…
Reference in New Issue