Skip to content

Commit 014de9b

Browse files
authored
Bug: add_named_destination() maintains named destination list sort order (#1930)
To quote the "Table 36 – Entries in a name tree node dictionary" the part about the `Names` key: > The keys shall be sorted in lexical order, as described below. [...] > > The Names entries in the leaf (or root) nodes shall contain the tree’s keys and their associated values, arranged in key-value pairs and shall be sorted lexically in ascending order by key. Shorter keys shall appear before longer ones beginning with the same byte sequence. Any encoding of the keys may be used as long as it is self-consistent; keys shall be compared for equality on a simple byte-by-byte basis. Fixes #1927
1 parent d4ff6fc commit 014de9b

File tree

2 files changed

+28
-2
lines changed

2 files changed

+28
-2
lines changed

pypdf/_writer.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1997,10 +1997,10 @@ def add_named_destination(
19971997
)
19981998

19991999
dest_ref = self._add_object(dest)
2000-
nd = self.get_named_dest_root()
20012000
if not isinstance(title, TextStringObject):
20022001
title = TextStringObject(str(title))
2003-
nd.extend([title, dest_ref])
2002+
2003+
self.add_named_destination_array(title, dest_ref)
20042004
return dest_ref
20052005

20062006
def addNamedDestination(

tests/test_writer.py

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -607,6 +607,32 @@ def test_add_named_destination(pdf_file_path):
607607
writer.write(output_stream)
608608

609609

610+
def test_add_named_destination_sort_order(pdf_file_path):
611+
"""
612+
Issue #1927 does not appear.
613+
614+
add_named_destination() maintains the named destination list sort order
615+
"""
616+
writer = PdfWriter()
617+
618+
assert writer.get_named_dest_root() == []
619+
620+
writer.add_blank_page(200, 200)
621+
writer.add_named_destination("b", 0)
622+
# "a" should be moved before "b" on insert
623+
writer.add_named_destination("a", 0)
624+
625+
root = writer.get_named_dest_root()
626+
627+
assert len(root) == 4
628+
assert root[0] == "a", '"a" was not inserted before "b" in the named destination root'
629+
assert root[2] == "b"
630+
631+
# write "output" to pypdf-output.pdf
632+
with open(pdf_file_path, "wb") as output_stream:
633+
writer.write(output_stream)
634+
635+
610636
def test_add_uri(pdf_file_path):
611637
reader = PdfReader(RESOURCE_ROOT / "pdflatex-outline.pdf")
612638
writer = PdfWriter()

0 commit comments

Comments
 (0)