我尝试将我的应用程序部署到带有Metro / Jersey和Glassfish 3.1.2的Tomcat 6,但是当我使用测试应用程序时,访问WebServiceContext资源总是会导致空指针异常,除了自动生成的Glassfish测试门户网站。
这是我编写的一个简单的测试方法来验证这一点:
import javax.annotation.Resource;
import javax.jws.WebService;
import javax.xml.ws.WebServiceContext;
import javax.xml.ws.handler.MessageContext;
import javax.servlet.ServletContext;
import javax.ws.rs.GET;
import javax.ws.rs.Path;
import javax.ws.rs.Produces;
@WebService
@Path("/test")
public class Test {
@Resource
WebServiceContext wsContext;
@GET
@Produces("text/plain")
@Path("/hello")
public String hello() {
MessageContext mc = wsContext.getMessageContext(); // NULL POINT HAPPENS HERE!
ServletContext servletContext = (ServletContext)
mc.get(
MessageContext.SERVLET_CONTEXT);
String s = servletContext.getRealPath("/WEB-INF");
return "Real Path: " + s;
}
}
这里是相应的web-xml(主要由Eclipse自动生成):
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://java.sun.com/xml/ns/javaee" xmlns:web="http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd" id="WebApp_ID" version="3.0">
<display-name>WebApp</display-name>
<welcome-file-list>
<welcome-file>index.html</welcome-file>
<welcome-file>index.htm</welcome-file>
<welcome-file>index.jsp</welcome-file>
<welcome-file>default.html</welcome-file>
<welcome-file>default.htm</welcome-file>
<welcome-file>default.jsp</welcome-file>
</welcome-file-list>
<servlet>
<description>JAX-RS Tools Generated - Do not modify</description>
<servlet-name>JAX-RS Servlet</servlet-name>
<servlet-class>com.sun.jersey.spi.container.servlet.ServletContainer</servlet-class>
<load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
<servlet-name>JAX-RS Servlet</servlet-name>
<url-pattern>/jaxrs/*</url-pattern>
</servlet-mapping>
</web-app>
最有趣的是,当我通过访问Glassfish生成的URL测试TestService时:
http://localhost:8080/WebApp/TestService?Tester
我可以通过提交表单来测试/调用“hello”方法,并获得一个生成相应文件路径的有效WebServiceContext对象。不幸的是,实际执行HTTP GET请求,如
$curl -H "Accept: text/plain" http://localhost:8080/WebApp/jaxrs/test/hello
导致空指针堆栈跟踪指向Test类中的第22行(WebServiceContext)。
为什么Web服务在Glassfish测试工具中工作,而不是来自实际的HTTP请求?
更新
如果您将GlassFish默认XML SOAP请求用于GlassFish默认URL,我能够确认Web服务是否正常工作(WebServiceContext已正确注入):
$curl -X POST -d @req.xml http://localhost:8080/ZlotyGlassfish/TestService --header "Content-Type:text/xml"
其中文件“req.xml”的内容是与WSDL定义匹配的请求:
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/" xmlns:impl="http://impl.rest.webservice.webapp.com/">
<soapenv:Header/>
<soapenv:Body>
<impl:hello/>
</soapenv:Body>
</soapenv:Envelope>
我的主要问题仍然是为什么通过默认的GlassFish实现完美地工作,但@GET和@Path表示法生成的端点无法注入适当的WebServiceContext对象?
答案 0 :(得分:5)
不同之处在于默认的GlassFish实现是一个JAX-WS 基于SOAP的 Web服务。对于JAX-RS Web服务,您应该使用以下注释来注入上下文。
@Context
private ServletContext sc;
还有其他类型可以使用@Context注释来注入,例如UriInfo
,HttpHeaders
。有关详细信息,请参阅Jersey documentation。 WebServiceContext
和MessageContext
是在JAX-RS上下文中没有意义的JAX-WS对象。