Skip to content

Commit 893adbf

Browse files
gh-91810: Fix regression with writing an XML declaration with encoding='unicode' (GH-93426) (GH-93791)
Suppress writing an XML declaration in open files in ElementTree.write() with encoding='unicode' and xml_declaration=None. If file patch is passed to ElementTree.write() with encoding='unicode', always open a new file in UTF-8. (cherry picked from commit d7db9dc) Co-authored-by: Serhiy Storchaka <storchaka@gmail.com>
1 parent e8f2fe3 commit 893adbf

File tree

3 files changed

+10
-20
lines changed

3 files changed

+10
-20
lines changed

Lib/test/test_xml_etree.py

+3-13
Original file line numberDiff line numberDiff line change
@@ -3680,13 +3680,7 @@ def test_write_to_filename_as_unicode(self):
36803680
tree = ET.ElementTree(ET.XML('''<site>\xf8</site>'''))
36813681
tree.write(TESTFN, encoding='unicode')
36823682
with open(TESTFN, 'rb') as f:
3683-
data = f.read()
3684-
expected = "<site>\xf8</site>".encode(encoding, 'xmlcharrefreplace')
3685-
if encoding.lower() in ('utf-8', 'ascii'):
3686-
self.assertEqual(data, expected)
3687-
else:
3688-
self.assertIn(b"<?xml version='1.0' encoding=", data)
3689-
self.assertIn(expected, data)
3683+
self.assertEqual(f.read(), b"<site>\xc3\xb8</site>")
36903684

36913685
def test_write_to_text_file(self):
36923686
self.addCleanup(support.unlink, TESTFN)
@@ -3701,17 +3695,13 @@ def test_write_to_text_file(self):
37013695
tree.write(f, encoding='unicode')
37023696
self.assertFalse(f.closed)
37033697
with open(TESTFN, 'rb') as f:
3704-
self.assertEqual(f.read(), convlinesep(
3705-
b'''<?xml version='1.0' encoding='ascii'?>\n'''
3706-
b'''<site>&#248;</site>'''))
3698+
self.assertEqual(f.read(), b'''<site>&#248;</site>''')
37073699

37083700
with open(TESTFN, 'w', encoding='ISO-8859-1') as f:
37093701
tree.write(f, encoding='unicode')
37103702
self.assertFalse(f.closed)
37113703
with open(TESTFN, 'rb') as f:
3712-
self.assertEqual(f.read(), convlinesep(
3713-
b'''<?xml version='1.0' encoding='ISO-8859-1'?>\n'''
3714-
b'''<site>\xf8</site>'''))
3704+
self.assertEqual(f.read(), b'''<site>\xf8</site>''')
37153705

37163706
def test_write_to_binary_file(self):
37173707
self.addCleanup(support.unlink, TESTFN)

Lib/xml/etree/ElementTree.py

+5-7
Original file line numberDiff line numberDiff line change
@@ -731,6 +731,7 @@ def write(self, file_or_filename,
731731
with _get_writer(file_or_filename, encoding) as (write, declared_encoding):
732732
if method == "xml" and (xml_declaration or
733733
(xml_declaration is None and
734+
encoding.lower() != "unicode" and
734735
declared_encoding.lower() not in ("utf-8", "us-ascii"))):
735736
write("<?xml version='1.0' encoding='%s'?>\n" % (
736737
declared_encoding,))
@@ -757,13 +758,10 @@ def _get_writer(file_or_filename, encoding):
757758
except AttributeError:
758759
# file_or_filename is a file name
759760
if encoding.lower() == "unicode":
760-
file = open(file_or_filename, "w",
761-
errors="xmlcharrefreplace")
762-
else:
763-
file = open(file_or_filename, "w", encoding=encoding,
764-
errors="xmlcharrefreplace")
765-
with file:
766-
yield file.write, file.encoding
761+
encoding="utf-8"
762+
with open(file_or_filename, "w", encoding=encoding,
763+
errors="xmlcharrefreplace") as file:
764+
yield file.write, encoding
767765
else:
768766
# file_or_filename is a file-like object
769767
# encoding determines if it is a text or binary writer
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
Suppress writing an XML declaration in open files in ``ElementTree.write()``
2+
with ``encoding='unicode'`` and ``xml_declaration=None``.

0 commit comments

Comments
 (0)