Kaydet (Commit) 1fe0d13d authored tarafından Martin Panter's avatar Martin Panter

Issue #26243: zlib.compress() keyword argument support by Aviv Palivoda

üst 38418662
...@@ -46,14 +46,19 @@ The available exception and functions in this module are: ...@@ -46,14 +46,19 @@ The available exception and functions in this module are:
platforms, use ``adler32(data) & 0xffffffff``. platforms, use ``adler32(data) & 0xffffffff``.
.. function:: compress(data[, level]) .. function:: compress(data, level=-1)
Compresses the bytes in *data*, returning a bytes object containing compressed data. Compresses the bytes in *data*, returning a bytes object containing compressed data.
*level* is an integer from ``0`` to ``9`` controlling the level of compression; *level* is an integer from ``0`` to ``9`` or ``-1`` controlling the level of compression;
``1`` is fastest and produces the least compression, ``9`` is slowest and ``1`` is fastest and produces the least compression, ``9`` is slowest and
produces the most. ``0`` is no compression. The default value is ``6``. produces the most. ``0`` is no compression. The default value is ``-1``
(Z_DEFAULT_COMPRESSION). Z_DEFAULT_COMPRESSION represents a default
compromise between speed and compression (currently equivalent to level 6).
Raises the :exc:`error` exception if any error occurs. Raises the :exc:`error` exception if any error occurs.
.. versionchanged:: 3.6
Keyword arguments are now supported.
.. function:: compressobj(level=-1, method=DEFLATED, wbits=15, memLevel=8, strategy=Z_DEFAULT_STRATEGY[, zdict]) .. function:: compressobj(level=-1, method=DEFLATED, wbits=15, memLevel=8, strategy=Z_DEFAULT_STRATEGY[, zdict])
......
...@@ -150,6 +150,13 @@ to check if the :class:`~zipfile.ZipInfo` instance represents a directory. ...@@ -150,6 +150,13 @@ to check if the :class:`~zipfile.ZipInfo` instance represents a directory.
(Contributed by Thomas Kluyver in :issue:`26039`.) (Contributed by Thomas Kluyver in :issue:`26039`.)
zlib
----
The :func:`~zlib.compress` function now accepts keyword arguments.
(Contributed by Aviv Palivoda in :issue:`26243`.)
Optimizations Optimizations
============= =============
......
...@@ -162,6 +162,10 @@ class CompressTestCase(BaseCompressTestCase, unittest.TestCase): ...@@ -162,6 +162,10 @@ class CompressTestCase(BaseCompressTestCase, unittest.TestCase):
x = zlib.compress(HAMLET_SCENE) x = zlib.compress(HAMLET_SCENE)
self.assertEqual(zlib.decompress(x), HAMLET_SCENE) self.assertEqual(zlib.decompress(x), HAMLET_SCENE)
def test_keywords(self):
x = zlib.compress(data=HAMLET_SCENE, level=3)
self.assertEqual(zlib.decompress(x), HAMLET_SCENE)
def test_speech128(self): def test_speech128(self):
# compress more data # compress more data
data = HAMLET_SCENE * 128 data = HAMLET_SCENE * 128
......
...@@ -175,6 +175,9 @@ Core and Builtins ...@@ -175,6 +175,9 @@ Core and Builtins
Library Library
------- -------
- Issue #26243: Support keyword arguments to zlib.compress(). Patch by Aviv
Palivoda.
- Issue #26117: The os.scandir() iterator now closes file descriptor not only - Issue #26117: The os.scandir() iterator now closes file descriptor not only
when the iteration is finished, but when it was failed with error. when the iteration is finished, but when it was failed with error.
......
...@@ -3,38 +3,39 @@ preserve ...@@ -3,38 +3,39 @@ preserve
[clinic start generated code]*/ [clinic start generated code]*/
PyDoc_STRVAR(zlib_compress__doc__, PyDoc_STRVAR(zlib_compress__doc__,
"compress($module, bytes, level=Z_DEFAULT_COMPRESSION, /)\n" "compress($module, /, data, level=Z_DEFAULT_COMPRESSION)\n"
"--\n" "--\n"
"\n" "\n"
"Returns a bytes object containing compressed data.\n" "Returns a bytes object containing compressed data.\n"
"\n" "\n"
" bytes\n" " data\n"
" Binary data to be compressed.\n" " Binary data to be compressed.\n"
" level\n" " level\n"
" Compression level, in 0-9."); " Compression level, in 0-9.");
#define ZLIB_COMPRESS_METHODDEF \ #define ZLIB_COMPRESS_METHODDEF \
{"compress", (PyCFunction)zlib_compress, METH_VARARGS, zlib_compress__doc__}, {"compress", (PyCFunction)zlib_compress, METH_VARARGS|METH_KEYWORDS, zlib_compress__doc__},
static PyObject * static PyObject *
zlib_compress_impl(PyModuleDef *module, Py_buffer *bytes, int level); zlib_compress_impl(PyModuleDef *module, Py_buffer *data, int level);
static PyObject * static PyObject *
zlib_compress(PyModuleDef *module, PyObject *args) zlib_compress(PyModuleDef *module, PyObject *args, PyObject *kwargs)
{ {
PyObject *return_value = NULL; PyObject *return_value = NULL;
Py_buffer bytes = {NULL, NULL}; static char *_keywords[] = {"data", "level", NULL};
Py_buffer data = {NULL, NULL};
int level = Z_DEFAULT_COMPRESSION; int level = Z_DEFAULT_COMPRESSION;
if (!PyArg_ParseTuple(args, "y*|i:compress", if (!PyArg_ParseTupleAndKeywords(args, kwargs, "y*|i:compress", _keywords,
&bytes, &level)) &data, &level))
goto exit; goto exit;
return_value = zlib_compress_impl(module, &bytes, level); return_value = zlib_compress_impl(module, &data, level);
exit: exit:
/* Cleanup for bytes */ /* Cleanup for data */
if (bytes.obj) if (data.obj)
PyBuffer_Release(&bytes); PyBuffer_Release(&data);
return return_value; return return_value;
} }
...@@ -439,4 +440,4 @@ exit: ...@@ -439,4 +440,4 @@ exit:
#ifndef ZLIB_COMPRESS_COPY_METHODDEF #ifndef ZLIB_COMPRESS_COPY_METHODDEF
#define ZLIB_COMPRESS_COPY_METHODDEF #define ZLIB_COMPRESS_COPY_METHODDEF
#endif /* !defined(ZLIB_COMPRESS_COPY_METHODDEF) */ #endif /* !defined(ZLIB_COMPRESS_COPY_METHODDEF) */
/*[clinic end generated code: output=cf81e1deae3af0ce input=a9049054013a1b77]*/ /*[clinic end generated code: output=3c96b58b923c1273 input=a9049054013a1b77]*/
...@@ -137,18 +137,17 @@ PyZlib_Free(voidpf ctx, void *ptr) ...@@ -137,18 +137,17 @@ PyZlib_Free(voidpf ctx, void *ptr)
/*[clinic input] /*[clinic input]
zlib.compress zlib.compress
bytes: Py_buffer data: Py_buffer
Binary data to be compressed. Binary data to be compressed.
level: int(c_default="Z_DEFAULT_COMPRESSION") = Z_DEFAULT_COMPRESSION level: int(c_default="Z_DEFAULT_COMPRESSION") = Z_DEFAULT_COMPRESSION
Compression level, in 0-9. Compression level, in 0-9 or -1.
/
Returns a bytes object containing compressed data. Returns a bytes object containing compressed data.
[clinic start generated code]*/ [clinic start generated code]*/
static PyObject * static PyObject *
zlib_compress_impl(PyModuleDef *module, Py_buffer *bytes, int level) zlib_compress_impl(PyModuleDef *module, Py_buffer *data, int level)
/*[clinic end generated code: output=5d7dd4588788efd3 input=be3abe9934bda4b3]*/ /*[clinic end generated code: output=1b97589132b203b4 input=671c615a4b2267da]*/
{ {
PyObject *ReturnVal = NULL; PyObject *ReturnVal = NULL;
Byte *input, *output = NULL; Byte *input, *output = NULL;
...@@ -156,13 +155,13 @@ zlib_compress_impl(PyModuleDef *module, Py_buffer *bytes, int level) ...@@ -156,13 +155,13 @@ zlib_compress_impl(PyModuleDef *module, Py_buffer *bytes, int level)
int err; int err;
z_stream zst; z_stream zst;
if ((size_t)bytes->len > UINT_MAX) { if ((size_t)data->len > UINT_MAX) {
PyErr_SetString(PyExc_OverflowError, PyErr_SetString(PyExc_OverflowError,
"Size does not fit in an unsigned int"); "Size does not fit in an unsigned int");
goto error; goto error;
} }
input = bytes->buf; input = data->buf;
length = (unsigned int)bytes->len; length = (unsigned int)data->len;
zst.avail_out = length + length/1000 + 12 + 1; zst.avail_out = length + length/1000 + 12 + 1;
...@@ -1323,7 +1322,7 @@ PyDoc_STRVAR(zlib_module_documentation, ...@@ -1323,7 +1322,7 @@ PyDoc_STRVAR(zlib_module_documentation,
"zlib library, which is based on GNU zip.\n" "zlib library, which is based on GNU zip.\n"
"\n" "\n"
"adler32(string[, start]) -- Compute an Adler-32 checksum.\n" "adler32(string[, start]) -- Compute an Adler-32 checksum.\n"
"compress(string[, level]) -- Compress string, with compression level in 0-9.\n" "compress(data[, level]) -- Compress data, with compression level 0-9 or -1.\n"
"compressobj([level[, ...]]) -- Return a compressor object.\n" "compressobj([level[, ...]]) -- Return a compressor object.\n"
"crc32(string[, start]) -- Compute a CRC-32 checksum.\n" "crc32(string[, start]) -- Compute a CRC-32 checksum.\n"
"decompress(string,[wbits],[bufsize]) -- Decompresses a compressed string.\n" "decompress(string,[wbits],[bufsize]) -- Decompresses a compressed string.\n"
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment