我的服务器正在使用XFire处理Web服务请求
但是它的CPU占用了100%甚至是1000%
当我重新启动服务器并经过一些请求后,这个奇怪的问题再次出现
我扫描线程转储,占用CPU的线程是这样的:
httpWorkerThread-18028-39" daemon prio=10 tid=0xa0832800 nid=0x1d89 runnable [0x99e69000]
java.lang.Thread.State: RUNNABLE
at com.sun.xml.stream.XMLDocumentScannerImpl$PrologDriver.next(XMLDocumentScannerImpl.java:892)
at com.sun.xml.stream.XMLDocumentScannerImpl.next(XMLDocumentScannerImpl.java:362)
at com.sun.xml.stream.XMLReaderImpl.next(XMLReaderImpl.java:568)
at org.codehaus.xfire.soap.handler.ReadHeadersHandler.invoke(ReadHeadersHandler.java:44)
at org.codehaus.xfire.handler.HandlerPipeline.invoke(HandlerPipeline.java:131)
at org.codehaus.xfire.transport.DefaultEndpoint.onReceive(DefaultEndpoint.java:64)
at org.codehaus.xfire.transport.AbstractChannel.receive(AbstractChannel.java:38)
at org.codehaus.xfire.transport.http.XFireServletController.invoke(XFireServletController.java:304)
at org.codehaus.xfire.transport.http.XFireServletController.doService(XFireServletController.java:129)
at org.codehaus.xfire.transport.http.XFireServlet.doPost(XFireServlet.java:116)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:753)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:846)
似乎XFire正在解析XML文件,但是随着时间的流逝,线程转储完全没有区别,线程就像在无限循环中一样。
但是,我对XFire的经验不足,无法弄清楚是什么原因引起的
我在Google上搜索了很多,并发现了这个topic的现象就像我的
但是,本主题建议这可能是JVM错误,并且使用JDK5而不是JDK6。我正在尝试使用JDK5来查看它是否有帮助
有没有人遇到这样的问题?是什么原因导致此问题以及如何解决?
多谢。
最佳答案
最后,我解决了这个问题。
如topic所述,导致此问题的原因是JDK6 XMLStreamReader实现的错误。
如何解决?
我阅读了XFire的源代码,答案在以下代码中:
XMLStreamReader reader =
STAXUtils.createXMLStreamReader(request.getInputStream(),
charEncoding,
context);
STAXUtils.createXMLStreamReader将创建XMLInputFactory以生成XMLStreamReader。
public static XMLInputFactory getXMLInputFactory(MessageContext ctx)
{
if (ctx == null) return xmlInputFactory;
Object inFactoryObj = ctx.getContextualProperty(XFire.STAX_INPUT_FACTORY);
if (inFactoryObj instanceof XMLInputFactory)
{
return (XMLInputFactory) inFactoryObj;
}
else if (inFactoryObj instanceof String)
{
String inFactory = (String) inFactoryObj;
XMLInputFactory xif = (XMLInputFactory) factories.get(inFactory);
if (xif == null)
{
xif = (XMLInputFactory) createFactory(inFactory, ctx);
configureFactory(xif,ctx);
factories.put(inFactory, xif);
}
return xif;
}
if(!inFactoryConfigured){
configureFactory(xmlInputFactory,ctx);
inFactoryConfigured=true;
}
return xmlInputFactory;
}
在此代码中,您可以配置“ xfire.stax.input.factory” XFire属性来生成XMLInputReader,该XMLInputFactory的XMLStreamReader没有错误,但是,我不知道如何设置此属性。
在我的项目中,xmlInputFactory是JDK的默认xmlInputFactory。
/**
* Create a new instance of the factory.
* This static method creates a new factory instance.
* This method uses the following ordered lookup procedure to determine
* the XMLInputFactory implementation class to load:
* Use the javax.xml.stream.XMLInputFactory system property.
* Use the properties file "lib/stax.properties" in the JRE directory.
* This configuration file is in standard java.util.Properties format and contains
* the fully qualified name of the implementation class with the key being the system property defined above.
* Use the Services API (as detailed in the JAR specification), if available, to determine the classname.
* The Services API will look for a classname in the file META-INF/services/javax.xml.stream.XMLInputFactory
* in jars available to the runtime.
* Platform default XMLInputFactory instance.
* Once an application has obtained a reference to a XMLInputFactory
* it can use the factory to configure and obtain stream instances.
*
* @throws FactoryConfigurationError if an instance of this factory cannot be loaded
*/
public static XMLInputFactory newInstance()
throws FactoryConfigurationError
{
return (XMLInputFactory) FactoryFinder.find(
"javax.xml.stream.XMLInputFactory",
"com.sun.xml.internal.stream.XMLInputFactoryImpl");
}
因此,您可以使用javax.xml.stream.XMLInputFactory系统属性来使用另一个XMLInputFactroy,例如wstx lib。