Linuxでは、2つのXMLファイル間の差分をどのように生成できますか?
理想的には、それを厳密なものに構成したり、空白や属性の順序などのいくつかを緩めたりできるようにしたいと思います。
ファイルが機能的に同じであることはよく気になりますが、それ自体ではdiffを使用するのは面倒です。特に、XMLファイルに多くの改行が含まれていない場合はそうです。
たとえば、次の例は本当に問題ないはずです。
<tag att1="one" att2="two">
content
</tag>
<tag att2="two" att1="one">
content
</tag>
1つのアプローチは、最初に両方のXMLファイルを Canonical XML に変換し、diff
を使用して結果を比較することです。たとえば、 xmllint を使用してXMLを正規化できます。
$ xmllint --c14n one.xml > 1.xml
$ xmllint --c14n two.xml > 2.xml
$ diff 1.xml 2.xml
またはワンライナーとして。
$ diff <(xmllint --c14n one.xml) <(xmllint --c14n two.xml)
Jukkaの答えは私には役に立ちませんでしたが、Canonical XMLを指し示していました。 -c14nも-c14n11も属性をソートしませんでしたが、-exc-c14nスイッチは属性をソートしました。 -exc-c14nはマニュアルページには記載されていませんが、コマンドラインでは「W3Cの排他的な正規形式」として記述されています。
$ xmllint --exc-c14n one.xml > 1.xml
$ xmllint --exc-c14n two.xml > 2.xml
$ diff 1.xml 2.xml
$ xmllint | grep c14
--c14n : save in W3C canonical format v1.0 (with comments)
--c14n11 : save in W3C canonical format v1.1 (with comments)
--exc-c14n : save in W3C exclusive canonical format (with comments)
$ rpm -qf /usr/bin/xmllint
libxml2-2.7.6-14.el6.x86_64
libxml2-2.7.6-14.el6.i686
$ cat /etc/system-release
CentOS release 6.5 (Final)
警告-exc-c14nはxmlヘッダーを削除しますが、-c14nは存在しない場合はxmlヘッダーを付加します。
@Jukka Matilainenの回答を使用しようとしましたが、空白に問題がありました(ファイルの1つが巨大な1行でした)。 --format
を使用すると、空白の違いをスキップできます。
xmllint --format one.xml > 1.xml
xmllint --format two.xml > 2.xml
diff 1.xml 2.xml
注:xmlを並べて比較するには、vimdiff
コマンドを使用します。
子要素の順序も無視したい場合は、単純なpythonと呼ばれるこのツールをxmldiffs
と呼びます。
要素と属性の順序を無視して、2つのXMLファイルを比較します。
使用法:
xmldiffs [OPTION] FILE1 FILE2
追加のオプションは
diff
コマンドに渡されます。
https://github.com/joh/xmldiffs で入手してください
My Python script xdiff.py XMLファイルを比較する場合、要素の順序とは対照的に、空白または属性の順序の違いは無視されます。
2つのファイル1.xml
と2.xml
を比較するには、次のようにスクリプトを実行します。
xdiff.py 1.xml 2.xml
OPの例では、何も出力せず、終了ステータス0
を返します(構造またはテキストの違いがない場合)。
1.xml
と2.xml
が構造的に異なる場合、GNU diffの統一された出力を模倣し、終了ステータス1
を返します。制御するためのさまざまなオプションがあります。すべてのコンテキストを出力するための-a
、コンテキストなしを出力するための-n
、出力を完全に抑制する(まだ終了ステータスを返す)ための-q
などの出力。
Beyond Compare を使用して、すべてのタイプのテキストベースのファイルを比較します。彼らはWindowsとLinux用のバージョンを生成します。