我有一个 XML 文件,其中包含一些我想忽略的 SOAP 标记。
我正在使用 pull-parser 解析 XML 文件,但自从出现 SOAP 标记后它就停止工作了。
XML 文件类似于:
<?xml version="1.0" encoding="UTF-8"?>
<soap:Envelope xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
<soap:Body>
<ns1:getAllUsersListResponse xmlns:ns1="http://webservice.business.ese.wiccore.myent.com/">
<return xsi:type="xs:string" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xs="http://www.w3.org/2001/XMLSchema"><![CDATA[<User>
在标签内 <User>
来所有我想解析的标签(我知道如何使用 pull-parser)然后
</User>]]></return>
<return xsi:type="xs:string" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xs="http://www.w3.org/2001/XMLSchema"><![CDATA[<User>
直到
</User>]]></return>
</ns1:getAllUsersListResponse>
</soap:Body>
</soap:Envelope>
问题是,我知道如何解析普通标签,但我不想解析这个 Soap 标签,我想忽略 SOAP 标签!任何人都知道如何实现这一点?
最佳答案
不太熟悉拉式解析(我通常是 SAX 专家),我可能不是此类事情的最权威来源,但这里是......
我相信大多数(如果不是全部)Java 拉式解析器应该使用特定的 CDATA 节点公开 CDATA 部分(我相信 StAX,例如,相关事件类型是 XMLStreamConstants.CDATA
)。因此,您需要解析文档并提取 CDATA 部分(在 SOAP <return>
元素内)并提取其内容。
该部分的内容是您感兴趣的文档,因此您需要依次对刚刚提取的内容运行新的拉式解析。
很抱歉,我不能提供更多帮助。希望会有其他人可以为您充实更多细节。
编辑:作为对评论的回应,您可以使用 SAX 实现这一点(为简洁起见,省略了异常处理):
import org.xml.sax.ext.DefaultHandler2;
import org.xml.sax.helpers.XMLReaderFactory;
import org.xml.sax.XMLReader;
class MyParsingApp extends DefaultHandler2 // see note 1
{
private boolean inCdata, parsingSubDocument;
private String subDocument;
public static void main (String args[])
{
InputStream stream = ... // see note 2
XMLReader reader = XMLReaderFactory.createXMLReader(); // see note 3
reader.setContentHandler (new MyParsingApp ( ));
reader.parse (new InputSource(stream));
parsingSubDocument = true;
reader.parse (new InputSource(new StringReader(subDocument)));
...
}
public MyParsingApp ( )
{
inCdata = parsingSubDocument = false;
subDocument = "";
}
@Override
public void startCDATA() throws SAXException
{
inCdata = true;
}
@Override
public void endCDATA() throws SAXException
{
inCdata = false;
}
@Override
public void characters(char[] ch, int start, int length) throws SAXException
{
if (inCdata)
subDocument += new String(ch, start, length); // see note 4
}
}
一些重要的注意事项:
- 通常您会使用一个单独的类作为您的内容处理程序,一个可能用于“主”文档(包括 SOAP 元素),另一个用于您的“目标”文档(在 CDATA 部分)。我在这里没有这样做只是为了尽可能简短。
- 我不确定您的 XML 是什么格式,但我假设它是
InputStream
这里。InputSource
类将愉快地使用InputStream
, 一个Reader
或String
指定要读取的文件名。使用最适合您的方式。 - 您需要使用 SAX2 阅读器才能处理 CDATA 内容。您的默认 SAX 阅读器可能符合也可能不符合 SAX2。因此,您可能需要(例如)手动创建特定 SAX2 解析器的实例。您可以找到一些 SAX2 解析器的列表 here ,如果是这样的话。
- 可能还有更有效的方法(
StringBuffer
/StringBuilder
可能是选项)。同样,我这样做只是为了简单起见。 - 我还没有真正测试过这段代码。您的里程可能会有所不同。
如果您以前没有使用过 SAX,可能也值得浏览一下 SAX Quickstart Guide .
关于java - 忽略 XML 文件中的 SOAP 标记,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/5998817/