Pequeña actualización a @darrell clase sea capaz de analizar UTF-8 contornos, que he puesto como respuesta porque comentario sería difícil de leer.
problema está en pyPdf.pdf.Destination.title
que pueden ser devueltos en dos sabores:
pyPdf.generic.TextStringObject
pyPdf.generic.ByteStringObject
modo que la salida de _setup_outline_page_ids()
función devuelve también dos tipos diferentes de title
objeto, que falla con UnicodeDecodeError
si el título del esquema contiene algo más que ASCII.
que añade este código para resolver el problema:
if isinstance(title, pyPdf.generic.TextStringObject):
title = title.encode('utf-8')
de toda la clase:
class PdfOutline(pyPdf.PdfFileReader):
def getDestinationPageNumbers(self):
def _setup_outline_page_ids(outline, _result=None):
if _result is None:
_result = {}
for obj in outline:
if isinstance(obj, pyPdf.pdf.Destination):
_result[(id(obj), obj.title)] = obj.page.idnum
elif isinstance(obj, list):
_setup_outline_page_ids(obj, _result)
return _result
def _setup_page_id_to_num(pages=None, _result=None, _num_pages=None):
if _result is None:
_result = {}
if pages is None:
_num_pages = []
pages = self.trailer["/Root"].getObject()["/Pages"].getObject()
t = pages["/Type"]
if t == "/Pages":
for page in pages["/Kids"]:
_result[page.idnum] = len(_num_pages)
_setup_page_id_to_num(page.getObject(), _result, _num_pages)
elif t == "/Page":
_num_pages.append(1)
return _result
outline_page_ids = _setup_outline_page_ids(self.getOutlines())
page_id_to_page_numbers = _setup_page_id_to_num()
result = {}
for (_, title), page_idnum in outline_page_ids.iteritems():
if isinstance(title, pyPdf.generic.TextStringObject):
title = title.encode('utf-8')
result[title] = page_id_to_page_numbers.get(page_idnum, '???')
return result