Shoobx / xmldiff

A library and command line utility for diffing xml

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

Compare fails with default namespaces

Julius2342 opened this issue · comments

Problem description

First thank you for your library! It is a great help within my unit tests!

I'm creating XML via lxml.etree and compare it with XML parsed from a string. The xmldiff is - other then expected - not empty:

from lxml import etree as ET
from xmldiff import formatting, main


left = ET.XML('<fnord xmlns="https://example.org/schema.xsd"><head/></fnord>')

right = ET.Element("fnord", nsmap={None: "https://example.org/schema.xsd"},)
ET.SubElement(right, "head")

print(ET.tostring(right, pretty_print=True).decode("utf8"))
print(ET.tostring(left, pretty_print=True).decode("utf8"))
diff = main.diff_trees(left, right, formatter=formatting.DiffFormatter(),)
print(diff)

The output is:

<fnord xmlns="https://example.org/schema.xsd">
  <head/>
</fnord>

<fnord xmlns="https://example.org/schema.xsd">
  <head/>
</fnord>

[rename, /*[1], fnord]
[rename, /fnord/*[1], head]

Used Versions

lxml-4.7.1
xmldiff-2.4
Python 3.7.5

After digging around in the code, i found an approach which mitigates this problem:

NS_URL = "https://example.org/schema.xsd"
right = ET.Element(f"{{{NS_URL}}}fnord", nsmap={None: NS_URL},)
ET.SubElement(right, f"{{{NS_URL}}}head")

.... but that does not feel right ...

I think that is correct. The tag for the parsed code will include the full namespace, so that's how it should be generated as well.