From 976ad5746a0155135337efa75648c550705215c0 Mon Sep 17 00:00:00 2001 From: Andrew Murray Date: Sat, 3 Dec 2022 09:29:02 +1100 Subject: [PATCH 1/3] Save comments from any image format by default --- src/PIL/JpegImagePlugin.py | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/src/PIL/JpegImagePlugin.py b/src/PIL/JpegImagePlugin.py index cb8a4e57fd8..c9de714d895 100644 --- a/src/PIL/JpegImagePlugin.py +++ b/src/PIL/JpegImagePlugin.py @@ -714,9 +714,7 @@ def validate_qtables(qtables): extra = info.get("extra", b"") - comment = info.get("comment") - if comment is None and isinstance(im, JpegImageFile): - comment = im.app.get("COM") + comment = info.get("comment", im.info.get("comment")) if comment: if isinstance(comment, str): comment = comment.encode() From c1d0a00943ee6fcc993f47047b798e2b6f9bac6f Mon Sep 17 00:00:00 2001 From: Andrew Murray Date: Sat, 3 Dec 2022 09:31:05 +1100 Subject: [PATCH 2/3] Use _binary instead of struct --- src/PIL/JpegImagePlugin.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/PIL/JpegImagePlugin.py b/src/PIL/JpegImagePlugin.py index c9de714d895..92dbb3193a0 100644 --- a/src/PIL/JpegImagePlugin.py +++ b/src/PIL/JpegImagePlugin.py @@ -732,7 +732,7 @@ def validate_qtables(qtables): icc_profile = icc_profile[MAX_DATA_BYTES_IN_MARKER:] i = 1 for marker in markers: - size = struct.pack(">H", 2 + ICC_OVERHEAD_LEN + len(marker)) + size = o16(2 + ICC_OVERHEAD_LEN + len(marker)) extra += ( b"\xFF\xE2" + size From 525c01143a8a4e0133908826577ccb54ed829a1b Mon Sep 17 00:00:00 2001 From: Andrew Murray Date: Sat, 3 Dec 2022 09:59:22 +1100 Subject: [PATCH 3/3] Test that comment is reread --- Tests/test_file_jpeg.py | 28 ++++++++++++++++++---------- 1 file changed, 18 insertions(+), 10 deletions(-) diff --git a/Tests/test_file_jpeg.py b/Tests/test_file_jpeg.py index ffaf2cabaf4..bb4ebb686f8 100644 --- a/Tests/test_file_jpeg.py +++ b/Tests/test_file_jpeg.py @@ -86,18 +86,26 @@ def test_app(self): assert len(im.applist) == 2 assert im.info["comment"] == b"File written by Adobe Photoshop\xa8 4.0\x00" + assert im.app["COM"] == im.info["comment"] - def test_com_write(self): - dummy_text = "this is a test comment" + def test_comment_write(self): with Image.open(TEST_FILE) as im: - with BytesIO() as buf: - im.save(buf, format="JPEG") - with Image.open(buf) as im2: - assert im.app["COM"] == im2.app["COM"] - with BytesIO() as buf: - im.save(buf, format="JPEG", comment=dummy_text) - with Image.open(buf) as im2: - assert im2.app["COM"].decode() == dummy_text + assert im.info["comment"] == b"File written by Adobe Photoshop\xa8 4.0\x00" + + # Test that existing comment is saved by default + out = BytesIO() + im.save(out, format="JPEG") + with Image.open(out) as reloaded: + assert im.info["comment"] == reloaded.info["comment"] + + # Test that a comment argument overrides the default comment + for comment in ("Test comment text", b"Text comment text"): + out = BytesIO() + im.save(out, format="JPEG", comment=comment) + with Image.open(out) as reloaded: + if not isinstance(comment, bytes): + comment = comment.encode() + assert reloaded.info["comment"] == comment def test_cmyk(self): # Test CMYK handling. Thanks to Tim and Charlie for test data,