比较 java 单元文本中的 Xml,忽略节点中的属性

Compare Xml in java unit text, ignoring an attribute in a node

我必须比较 2 xml 个字符串。

实际

<?xml version="1.0" encoding="utf-8"?>
    <entry xmlns="http://www.w3.org/2005/Atom"
        xmlns:m="http://schemas.microsoft.com/ado/2007/08/dataservices/metadata"
        xmlns:d="http://schemas.microsoft.com/ado/2007/08/dataservices"
        xml:base="http://localhost:49531/ODataV2.svc/ODataV2.svc/">
        <content type="application/xml">
            <m:properties>
                <d:ID>2000</d:ID>
                <d:ReleaseDate>1992-01-01T00:00:00</d:ReleaseDate>
                <d:Rating>4</d:Rating>
                <d:Price>2.5</d:Price>
            </m:properties>
        </content>
    </entry>

预计

<?xml version="1.0" encoding="utf-8"?>
<entry xmlns="http://www.w3.org/2005/Atom"
    xmlns:m="http://schemas.microsoft.com/ado/2007/08/dataservices/metadata"
    xmlns:d="http://schemas.microsoft.com/ado/2007/08/dataservices"
    xml:base="http://localhost:55615/ODataV2.svc/ODataV2.svc/">
    <content type="application/xml">
        <m:properties>
            <d:ID>2000</d:ID>
            <d:ReleaseDate>1992-01-01T00:00:00</d:ReleaseDate>
            <d:Rating>4</d:Rating>
            <d:Price>2.5</d:Price>
        </m:properties>
    </content>
</entry>

以下代码失败,因为属性 xml:base 中的端口号在根节点中不同。

XMLAssert.assertXMLEqual(Actual, Expected);

Expected attribute value 'http://localhost:55615/ODataV2.svc/ODataV2.svc/' but was 'http://localhost:49531/ODataV2.svc/ODataV2.svc/'

单元测试中的端口号在运行时发生变化。 有没有办法忽略特定属性并比较 xml.

我知道这不会是最酷或最奇特的解决方案,但您可以 'parse' 两者 XML 在比较它们之前删除或更改该属性的值或将两者的值更改为类似的东西,所以当您稍后比较它们你确定这不会影响结果

也许您可以配置命名空间上下文:

http://xmlunit.sourceforge.net/api/org/custommonkey/xmlunit/XMLUnit.html#getXpathNamespaceContext()

XMLUnit 2.x 具有 NodeFilters 和 AttributeFilters 的概念,它们很简单 Predicates.

assertThat(Actual, isIdenticalTo(Expected)
    .withAttributeFilter(a -> !"base".equals(a.getName())))

可能会起作用。

找到解决方案。我使用 custommonkey 库进行 xml 比较。 而不是 XMLAssert.assertXMLEqual(Actual, Expected);

我使用下面的代码来决定差异。

Diff diff=XMLUnit.compareXML(Expected,Actual);
    diff.overrideDifferenceListener(new DifferenceListener() {
       public void skippedComparison(Node arg0, Node arg1) {
       }

       public int differenceFound(Difference difference) {
        if (difference.getControlNodeDetail().getXpathLocation().contains("entry")) {
            return DifferenceListener.RETURN_IGNORE_DIFFERENCE_NODES_IDENTICAL;
        } else {
            return DifferenceListener.RETURN_ACCEPT_DIFFERENCE;
        }
        }
    });
XMLAssert.assertXMLIdentical(diff,true);