From 1702f127837d2bd789e520f04a4d44eae56d382d Mon Sep 17 00:00:00 2001 From: Andy Wilson Date: Thu, 20 Dec 2018 13:51:16 -0700 Subject: [PATCH] BUG: File I/O needs bytes in Python 3 The wrapper that allows us to use Python file-like objects as C++ streams was specific to Python 2 inasmuch as it wrapped data in a str() before sending it to the write() method. As of Boost 1.67, Boost.Python doesn't have a convenient wrapper for bytes the way it does str. We instantiate a bytes() object around the raw data ourselves. Some of the issues involved are discussed in this pull request: https://github.com/boostorg/python/pull/54 --- tracktable/PythonWrapping/PythonFileLikeObjectStreams.h | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/tracktable/PythonWrapping/PythonFileLikeObjectStreams.h b/tracktable/PythonWrapping/PythonFileLikeObjectStreams.h index f7a98553..7befe76b 100644 --- a/tracktable/PythonWrapping/PythonFileLikeObjectStreams.h +++ b/tracktable/PythonWrapping/PythonFileLikeObjectStreams.h @@ -137,11 +137,17 @@ class PythonWriteSink // can do is dump the data out, claim it was all written and // hope for the best. +#if PY_MAJOR_VERSION == 2 boost::python::str data(buffer, n); boost::python::object write_result(this->Writer(data)); boost::python::extract bytes_written(write_result); - +#else + boost::python::object data(boost::python::handle<>(PyBytes_FromStringAndSize(buffer, n))); + boost::python::object write_result(this->Writer(data)); + boost::python::extract bytes_written(write_result); +#endif + return (bytes_written.check() ? bytes_written() : n); }