From aa44bf1cd17b7f261acfd7b3e9a2eecc4d21b238 Mon Sep 17 00:00:00 2001 From: Eli Schwartz Date: Thu, 9 May 2019 07:10:06 -0400 Subject: [PATCH 1/5] py3: hashlib .hexdigest() always returns a hexadecimal string This is a subset of ascii and cannot be decoded. --- src/calibre/srv/books.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/calibre/srv/books.py b/src/calibre/srv/books.py index 3fd0bed4da..d8ceeede36 100644 --- a/src/calibre/srv/books.py +++ b/src/calibre/srv/books.py @@ -50,7 +50,7 @@ def books_cache_dir(): def book_hash(library_uuid, book_id, fmt, size, mtime): raw = json_dumps((library_uuid, book_id, fmt.upper(), size, mtime, RENDER_VERSION)) - return sha1(raw).hexdigest().decode('ascii') + return sha1(raw).hexdigest() staging_cleaned = False From 457eea7407b19cb40d0f5bdfaeb772d0ba234a6e Mon Sep 17 00:00:00 2001 From: Eli Schwartz Date: Thu, 9 May 2019 10:37:43 -0400 Subject: [PATCH 2/5] py3: use correct __next__ method I'm not sure why this is storing a seemingly unused method-wrapper object, but it needs to use the correctly named one on python2/python3. --- src/calibre/srv/render_book.py | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/src/calibre/srv/render_book.py b/src/calibre/srv/render_book.py index 407c457889..c269f6d015 100644 --- a/src/calibre/srv/render_book.py +++ b/src/calibre/srv/render_book.py @@ -31,7 +31,7 @@ from calibre.ebooks.oeb.polish.utils import extract, guess_type from calibre.utils.logging import default_log from calibre.utils.short_uuid import uuid4 from polyglot.binary import as_base64_unicode as encode_component, from_base64_unicode as decode_component -from polyglot.builtins import iteritems, map, unicode_type +from polyglot.builtins import iteritems, map, is_py3, unicode_type from polyglot.urllib import quote, urlparse RENDER_VERSION = 1 @@ -501,7 +501,10 @@ def html_as_dict(root): if child.tag.partition('}')[-1] not in ('head', 'body'): root.remove(child) root.text = root.tail = None - nsmap = defaultdict(count().next) + if is_py3: + nsmap = defaultdict(count().__next__) + else: + nsmap = defaultdict(count().next) nsmap[XHTML_NS] tags = [serialize_elem(root, nsmap)] tree = [0] From ba0a4992b6dd8ca3003cb473dc2932816d906ec2 Mon Sep 17 00:00:00 2001 From: Eli Schwartz Date: Thu, 9 May 2019 11:36:06 -0400 Subject: [PATCH 3/5] py3: save server preferences using bytestrings --- src/calibre/gui2/preferences/server.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/calibre/gui2/preferences/server.py b/src/calibre/gui2/preferences/server.py index 65caf30461..b8885171fb 100644 --- a/src/calibre/gui2/preferences/server.py +++ b/src/calibre/gui2/preferences/server.py @@ -967,7 +967,7 @@ class CustomList(QWidget): # {{{ if path: raw = self.serialize(self.current_template) with lopen(path, 'wb') as f: - f.write(raw) + f.write(raw.encode('utf-8')) def thumbnail_state_changed(self): is_enabled = bool(self.thumbnail.isChecked()) @@ -1020,7 +1020,7 @@ class CustomList(QWidget): # {{{ else: raw = self.serialize(template) with lopen(custom_list_template.path, 'wb') as f: - f.write(raw) + f.write(raw.encode('utf-8')) return True # }}} From aa8efc504db0d1828762f9645c62fd9c2bf7cd61 Mon Sep 17 00:00:00 2001 From: Eli Schwartz Date: Thu, 9 May 2019 13:26:33 -0400 Subject: [PATCH 4/5] py3: make user auth work; don't mess with encodings for strftime The Windows-specific hack initially added in commit 8743efbed1e54d8dd4e71ba71ebd5a7806564270 should be able to be removed now as it is no longer necessary. The python encoding on Windows is sane in python3. --- src/calibre/srv/utils.py | 9 ++++----- 1 file changed, 4 insertions(+), 5 deletions(-) diff --git a/src/calibre/srv/utils.py b/src/calibre/srv/utils.py index 6575787519..f82cce7eac 100644 --- a/src/calibre/srv/utils.py +++ b/src/calibre/srv/utils.py @@ -22,7 +22,7 @@ from calibre.utils.shared_file import share_open, raise_winerror from polyglot.builtins import iteritems, map, range from polyglot import reprlib from polyglot.http_cookie import SimpleCookie -from polyglot.builtins import unicode_type +from polyglot.builtins import is_py3, unicode_type from polyglot.urllib import parse_qs, quote as urlquote from polyglot.binary import as_hex_unicode as encode_name, from_hex_unicode as decode_name @@ -530,10 +530,9 @@ def get_use_roman(): return _use_roman -if iswindows: +if iswindows and not is_py3: def fast_now_strftime(fmt): - fmt = fmt.encode('mbcs') - return time.strftime(fmt).decode('mbcs', 'replace') + return time.strftime(fmt).encode('mbcs', 'replace').decode('mbcs') else: def fast_now_strftime(fmt): - return time.strftime(fmt).decode('utf-8', 'replace') + return time.strftime(fmt) From dc96af576365820d85d094536cee05a9a66b4207 Mon Sep 17 00:00:00 2001 From: Eli Schwartz Date: Thu, 9 May 2019 13:49:56 -0400 Subject: [PATCH 5/5] py3: textwrap.dedent requires unicode strings, encode after the fact Also all the format arguments are unicode strings, *and* in the wisdom of python3, you can % format a bytestring but not .format() it. --- src/calibre/ebooks/docx/writer/container.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/calibre/ebooks/docx/writer/container.py b/src/calibre/ebooks/docx/writer/container.py index 82ae0bd8f7..9dd894db8b 100644 --- a/src/calibre/ebooks/docx/writer/container.py +++ b/src/calibre/ebooks/docx/writer/container.py @@ -223,13 +223,13 @@ class DOCX(object): @property def containerrels(self): - return textwrap.dedent(b'''\ + return textwrap.dedent('''\ - '''.format(**self.namespace.names)) + '''.format(**self.namespace.names)).encode('utf-8') @property def websettings(self):