views:

2412

answers:

5

Similar to How can I access the ServletContext from within a JAX-WS web service?, is there a way to access applicationContext, easier than this?

import javax.annotation.Resource;
import javax.jws.WebService;
import javax.servlet.ServletContext;
import javax.xml.ws.WebServiceContext;
import javax.xml.ws.handler.MessageContext;

import org.springframework.web.context.WebApplicationContext;
import org.springframework.web.context.support.WebApplicationContextUtils;

@WebService
public class MyWebService {
    // boilerplate code begins :(

    @Resource
    private WebServiceContext context;
    private WebApplicationContext webApplicationContext = null;

    /**
     * @return
     * @throws IllegalStateException
     */
    private WebApplicationContext getWebApplicationContext()
      throws IllegalStateException {
     if (webApplicationContext != null)
      return webApplicationContext;
     ServletContext servletContext =
       (ServletContext) context.getMessageContext().get(
         MessageContext.SERVLET_CONTEXT);
     webApplicationContext =
       WebApplicationContextUtils.getRequiredWebApplicationContext(servletContext);
     return webApplicationContext;
    }
}
A: 

I would install a Filter that saves ServletContext before chaining in a ThreadLocal

Maurice Perry
+1  A: 

I don't think that the web service should have to know about web or servlet contexts or its application context. I don't see why it should have to know any of that. Shouldn't it be far more passive? Inject what it needs and let it do its work. The service interactions with a client should be based on a contract defined up front. If it has to get unknown values from a context of some kind, how will clients know what needs to be set or how to set it?

I'd go further and say that a web service should be a wrapper for a Spring service interface. It's just one more choice among all the possible ways to expose it. Your web service should do little more than marshal and unmarshal the XML request/response objects and collaborate with Spring services.

duffymo
Well, then how can I collaborate with Spring services, if I cannot say: appContext.getBean('myBean')?
pihentagy
Inject it in via setter or constructor. Dependency injection means "don't call us; we'll call you." Your objects don't have to have the app context to get what they need.
duffymo
You cannot. If I test my web service under glassfish, a new webservice is created, and it is not configured :-o That was a one-day-long debugging to get this knowledge :(
pihentagy
I'm writing Spring web services that I'm deploying under WebLogic, and I don't have to supply the application context. They're working fine for me - SOAP UI clients have no problems working with them. I think you're doing something else wrong.
duffymo
So, you autowired the required beans in your Service class?
pihentagy
Yes, that's right.
duffymo
A: 

Hi Folks,

I have the same problem in weblogic using the jax-ws and spring. Every time I call my webservice a new instance is created with with elements equals to NULL. So i m getting always a NullPointerException. could you please tell me how to solve this? Thanks a lot,

Baazizi.

If you want to ask a new question you should use the "Ask Question" button in the top right, not post it as an answer to an old question. Many more people will see it if you start a new question. If you think your problem is related to this question you can of course always add a link to this thread.
sth
A: 

Make your web service bean extend a spring bean.

like this

Michael Wiles
+2  A: 
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.web.context.support.SpringBeanAutowiringSupport;


@WebService( 
    endpointInterface = "Bla", 
    targetNamespace = "http://bla/v001", 
    wsdlLocation = "WEB-INF/wsdl/bla.wsdl",    
    serviceName = "BlaService",
    portName = "BlaPort")
public class BlaWs extends SpringBeanAutowiringSupport implements BlaPort {

  @Autowired
  @Qualifier("dao") 
  private Dao dao;
  ...
}
maximdim
+1 Thanks for pointing me in the direction of `SpringBeanAutowiringSupport`. I had been struggling with getting Glassfish to relinquish its management of JAX-WS and letting Spring to it. This is a much easier solution and lets Spring stay focused on the things that it is good at.
Matthew T. Staebler