我需要将XML无损转换为JSON,然后再使用Java。我使用了一个名为jsonxml的Javascript库,它正确地完成了它,但没有使用Java。
我似乎找到了最好的JSON-java,这在Stack Overflow中经常被提到,但它在太多方面都没有进行测试。
以下是我的测试用例代码......
//---------------------------------------------------
import org.json.*;
//---------------------------------------------------
public class rjx
{
//-----------------------------------------------
private String j2x(String json)
{
return(XML.toString(new JSONObject(json)));
}
//-----------------------------------------------
private String x2j(String xml)
{
return(XML.toJSONObject(xml).toString());
}
//-----------------------------------------------
//-----------------------------------------------
public static void main(String[] args)
{
//-------------------------------------------
rjx o = new rjx();
//-------------------------------------------
try
{
String xml = new String();
String reversed = new String();
System.out.println("=======");
xml = "<e/>";
System.out.println(xml);
reversed = o.j2x(o.x2j(xml));
System.out.println(reversed);
if (xml.equals(reversed))
System.out.println("PASS");
else
System.out.println("FAIL");
System.out.println("-------");
xml = "<e>text</e>";
System.out.println(xml);
reversed = o.j2x(o.x2j(xml));
System.out.println(reversed);
if (xml.equals(reversed))
System.out.println("PASS");
else
System.out.println("FAIL");
System.out.println("-------");
xml = "<e name='value' />";
System.out.println(xml);
reversed = o.j2x(o.x2j(xml));
System.out.println(reversed);
if (xml.equals(reversed))
System.out.println("PASS");
else
System.out.println("FAIL");
System.out.println("-------");
xml = "<e name='value'>text</e>";
System.out.println(xml);
reversed = o.j2x(o.x2j(xml));
System.out.println(reversed);
if (xml.equals(reversed))
System.out.println("PASS");
else
System.out.println("FAIL");
System.out.println("-------");
xml = "<e><a>text</a><b>text</b></e>";
System.out.println(xml);
reversed = o.j2x(o.x2j(xml));
System.out.println(reversed);
if (xml.equals(reversed))
System.out.println("PASS");
else
System.out.println("FAIL");
System.out.println("-------");
xml = "<e><a>text</a><a>text</a></e>";
System.out.println(xml);
reversed = o.j2x(o.x2j(xml));
System.out.println(reversed);
if (xml.equals(reversed))
System.out.println("PASS");
else
System.out.println("FAIL");
System.out.println("-------");
xml = "<e>text<a>text</a></e>";
System.out.println(xml);
reversed = o.j2x(o.x2j(xml));
System.out.println(reversed);
if (xml.equals(reversed))
System.out.println("PASS");
else
System.out.println("FAIL");
System.out.println("-------");
xml = "<a>hello</a>";
System.out.println(xml);
reversed = o.j2x(o.x2j(xml));
System.out.println(reversed);
if (xml.equals(reversed))
System.out.println("PASS");
else
System.out.println("FAIL");
System.out.println("-------");
xml = "<a x='y'>hello</a>";
System.out.println(xml);
reversed = o.j2x(o.x2j(xml));
System.out.println(reversed);
if (xml.equals(reversed))
System.out.println("PASS");
else
System.out.println("FAIL");
System.out.println("-------");
xml = "<a id='a'><b id='b'>hey!</b></a>";
System.out.println(xml);
reversed = o.j2x(o.x2j(xml));
System.out.println(reversed);
if (xml.equals(reversed))
System.out.println("PASS");
else
System.out.println("FAIL");
System.out.println("-------");
xml = "<a>x<c/>y</a>";
System.out.println(xml);
reversed = o.j2x(o.x2j(xml));
System.out.println(reversed);
if (xml.equals(reversed))
System.out.println("PASS");
else
System.out.println("FAIL");
System.out.println("-------");
xml = "<x u=''/>";
System.out.println(xml);
reversed = o.j2x(o.x2j(xml));
System.out.println(reversed);
if (xml.equals(reversed))
System.out.println("PASS");
else
System.out.println("FAIL");
System.out.println("-------");
xml = "<html><head><title>Xml/Json</title><meta name='x' content='y' /></head><body></body></html>";
System.out.println(xml);
reversed = o.j2x(o.x2j(xml));
System.out.println(reversed);
if (xml.equals(reversed))
System.out.println("PASS");
else
System.out.println("FAIL");
System.out.println("-------");
xml = "<ol class='xoxo'><li>Subject 1<ol><li>subpoint a</li><li>subpoint b</li></ol></li><li><span>Subject 2</span><ol compact='compact'><li>subpoint c</li><li>subpoint d</li></ol></li></ol>";
System.out.println(xml);
reversed = o.j2x(o.x2j(xml));
System.out.println(reversed);
if (xml.equals(reversed))
System.out.println("PASS");
else
System.out.println("FAIL");
System.out.println("-------");
xml = "<span class='vevent'><a class='url' href='http://www.web2con.com/'><span class='summary'>Web 2.0 Conference</span><abbr class='dtstart' title='2005-10-05'>October 5</abbr><abbr class='dtend' title='2005-10-08'>7</abbr><span class='location'>Argent Hotel, San Francisco, CA</span></a></span>";
System.out.println(xml);
reversed = o.j2x(o.x2j(xml));
System.out.println(reversed);
if (xml.equals(reversed))
System.out.println("PASS");
else
System.out.println("FAIL");
System.out.println("-------");
xml = "<e><![CDATA[ .. some data .. ]]></e>";
System.out.println(xml);
reversed = o.j2x(o.x2j(xml));
System.out.println(reversed);
if (xml.equals(reversed))
System.out.println("PASS");
else
System.out.println("FAIL");
System.out.println("-------");
xml = "<e><a /><![CDATA[ .. some data .. ]]><b /></e>";
System.out.println(xml);
reversed = o.j2x(o.x2j(xml));
System.out.println(reversed);
if (xml.equals(reversed))
System.out.println("PASS");
else
System.out.println("FAIL");
System.out.println("-------");
xml = "<e>some text<![CDATA[ .. some data .. ]]>more text</e>";
System.out.println(xml);
reversed = o.j2x(o.x2j(xml));
System.out.println(reversed);
if (xml.equals(reversed))
System.out.println("PASS");
else
System.out.println("FAIL");
System.out.println("-------");
xml = "<e>some text<![CDATA[ .. some data .. ]]><a /></e>";
System.out.println(xml);
reversed = o.j2x(o.x2j(xml));
System.out.println(reversed);
if (xml.equals(reversed))
System.out.println("PASS");
else
System.out.println("FAIL");
System.out.println("-------");
xml = "<e><![CDATA[ .. some data .. ]]><![CDATA[ .. more data .. ]]></e>";
System.out.println(xml);
reversed = o.j2x(o.x2j(xml));
System.out.println(reversed);
if (xml.equals(reversed))
System.out.println("PASS");
else
System.out.println("FAIL");
System.out.println("-------");
xml = "<e><![CDATA[ .. some data .. ]]><![CDATA[ .. & more data .. ]]></e>";
System.out.println(xml);
reversed = o.j2x(o.x2j(xml));
System.out.println(reversed);
if (xml.equals(reversed))
System.out.println("PASS");
else
System.out.println("FAIL");
System.out.println("-------");
xml = "<e><![CDATA[ .. some data .. ]]><![PCDATA[ .. & still more data .. ]]></e>";
System.out.println(xml);
reversed = o.j2x(o.x2j(xml));
System.out.println(reversed);
if (xml.equals(reversed))
System.out.println("PASS");
else
System.out.println("FAIL");
System.out.println("=======");
}
catch (Exception e)
{
System.err.println("error: rjx.main>>" + e.toString());
System.exit(1);
}
System.exit(0);
}
//-----------------------------------------------
}
//---------------------------------------------------
结果......
=======
<e/>
<e/>
PASS
-------
<e>text</e>
<e>text</e>
PASS
-------
<e name='value' />
<e><name>value</name></e>
FAIL
-------
<e name='value'>text</e>
<e><name>value</name>text</e>
FAIL
-------
<e><a>text</a><b>text</b></e>
<e><a>text</a><b>text</b></e>
PASS
-------
<e><a>text</a><a>text</a></e>
<e><a>text</a><a>text</a></e>
PASS
-------
<e>text<a>text</a></e>
<e><a>text</a>text</e>
FAIL
-------
<a>hello</a>
<a>hello</a>
PASS
-------
<a x='y'>hello</a>
<a><x>y</x>hello</a>
FAIL
-------
<a id='a'><b id='b'>hey!</b></a>
<a><b><id>b</id>hey!</b><id>a</id></a>
FAIL
-------
<a>x<c/>y</a>
<a><c/>x
y</a>
FAIL
-------
<x u=''/>
<x><u/></x>
FAIL
-------
<html><head><title>Xml/Json</title><meta name='x' content='y' /></head><body></body></html>
<html><head><meta><name>x</name>y</meta><title>Xml/Json</title></head><body/></html>
FAIL
-------
<ol class='xoxo'><li>Subject 1<ol><li>subpoint a</li><li>subpoint b</li></ol></li><li><span>Subject 2</span><ol compact='compact'><li>subpoint c</li><li>subpoint d</li></ol></li></ol>
<ol><class>xoxo</class><li><ol><li>subpoint a</li><li>subpoint b</li></ol>Subject 1</li><li><ol><compact>compact</compact><li>subpoint c</li><li>subpoint d</li></ol><span>Subject 2</span></li></ol>
FAIL
-------
<span class='vevent'><a class='url' href='http://www.web2con.com/'><span class='summary'>Web 2.0 Conference</span><abbr class='dtstart' title='2005-10-05'>October 5</abbr><abbr class='dtend' title='2005-10-08'>7</abbr><span class='location'>Argent Hotel, San Francisco, CA</span></a></span>
<span><a><href>http://www.web2con.com/</href><abbr><title>2005-10-05</title><class>dtstart</class>October 5</abbr><abbr><title>2005-10-08</title><class>dtend</class>7</abbr><class>url</class><span><class>summary</class>Web 2.0 Conference</span><span><class>location</class>Argent Hotel, San Francisco, CA</span></a><class>vevent</class></span>
FAIL
-------
<e><![CDATA[ .. some data .. ]]></e>
<e> .. some data .. </e>
FAIL
-------
<e><a /><![CDATA[ .. some data .. ]]><b /></e>
<e><a/><b/> .. some data .. </e>
FAIL
-------
<e>some text<![CDATA[ .. some data .. ]]>more text</e>
<e><array>some text</array><array> .. some data .. </array><array>more text</array></e>
FAIL
-------
<e>some text<![CDATA[ .. some data .. ]]><a /></e>
<e><a/>some text
.. some data .. </e>
FAIL
-------
<e><![CDATA[ .. some data .. ]]><![CDATA[ .. more data .. ]]></e>
<e><array> .. some data .. </array><array> .. more data .. </array></e>
FAIL
-------
<e><![CDATA[ .. some data .. ]]><![CDATA[ .. & more data .. ]]></e>
<e><array> .. some data .. </array><array> .. & more data .. </array></e>
FAIL
-------
<e><![CDATA[ .. some data .. ]]><![PCDATA[ .. & still more data .. ]]></e>
error: rjx.main>>org.json.JSONException: Expected 'CDATA[' at 41 [character 42 line 1]
是否有一个库,可能是JSON-java的一个分支,可以通过所有测试?
顺便说一句,我可以原谅订单不匹配的失败,这在我的规范中,但结构改变不是。
答案 0 :(得分:0)
这取决于您的确切要求。
例如,如果你看到
<p id="foo" class=' x '>Hello, <i>cruel</i> world.</p >
如果你得到以下回复,它会被视为“无损”吗?
<p class='x' id='foo'>, <i>cruel</i> world.</p>
如果不计算为无损,那么除了只是在XML中转义和引用并将整个事件调用为一个JSON字符串之外,进行无损往返将非常困难。这当然很容易,但JSON根本不知道里面的内容。
几乎任何XML解析器都会丢弃标签内部的空白区域差异;这是设计的行为。有些还返回属性而不考虑顺序。对JSON进行现成的转换可能会将属性放入JSON哈希,之后它们的原始顺序肯定会消失,因此无法恢复。还有一些其他问题,例如是否“&amp; #nbsp;” ==“&amp;#160;” ==“&amp;#xA0;”....使用“Canonical XML”(参见https://www.w3.org/TR/xml-c14n11/)将有助于避免此类问题。
但是,我有点困惑,因为我想不出没有XML解析器可用的环境。为什么不进行任何转换,只是在目的地解析XML?听起来好像目的地没有改变数据,因为如果它实际上是圆形跳闸显然根本不起作用。如果你发送XML,目的地更容易验证它以确保它没问题。另一方面,如果上面的示例为您的目的计算为“无损”,事情变得容易多了。由于XML元素具有重要的名称和 order ,您必须保留它们,无论您使用什么,都应该为每个元素创建JSON数组和JSON哈希。也许最简单的就是:
[ { "#":"p" "id":""foo"" "class":""x"" },
"Hello, ",
[ { "#":"i" },
"cruel"
],
"world."
]
我不知道那样做的Javascript或Java库。我有它的Python,但它只是粘贴在这里有点大。你可以非常接近:
sed -E \
-e 's@>([^<]+)@>"\1"<@g' \
-e 's@<([^\s/>]+)(\s+[^>]*)?/>@[{"#":"\1", \2}],@g' \
-e 's@<([^\s/>]+)(\s+[^>]*)?>@[{"#":"\1", \2},@g' \
-e 's@<\?(\w+)(\s+([^?]|\?[^>])*)?\?>@[{"#":"#PI", "#target":"\1", \2]}@g' \
-e 's@<!--(([^-]|-[^-]|--[^>])*)-->@/* \1 */@g' \
-e 's@\s+(\w+)\s*=\s*("[^"]*")@ "\1":"\2",@g' \
-e 's@</([^\s/>]+)\s*>@],@g' \
-e 's@&#[xX]([0-9a-fA-F]+);@\\u{\1}@g' \
-e 's@<@<@g' \
-e 's@>@>@g' \
-e 's@&@&@g' \
-e 's@[@[@g' \
-e 's@]@]@g' \
-e 's@"\s*([-+]?\d+(\.\d+)?([eE][-+?]\d+)?)\s*"@\1@g'