开发者

Why is JAXB trying to bind Spring's ApplicationContext?

开发者 https://www.devze.com 2023-03-14 15:29 出处:网络
I\'m working on a Spring application that exposes a JAX-WS web service. The web service implementation has a dependency on some spring-managed object in my service-layer and looks like this

I'm working on a Spring application that exposes a JAX-WS web service. The web service implementation has a dependency on some spring-managed object in my service-layer and looks like this

@WebService
public class BlahService {
    ...
    public void setFooService(FooService f) {
        ...
    }
}

where FooService is defined in the application context and is injected into BlahService during webapp startup. FooService on its part depends on BarService that is again defined in the application context and injected at startup, hence BlahService above transitively depends on BarService.

Here goes he tricky part. BarService implements ApplicationContextAware, so its code resembles the usual

public class BazService implements ApplicationContextAware {

    private ApplicationContext applicationContext;

    public final void setApplicationContext(ApplicationContext ctx) {
        this.applicationContext = ctx;
    }
    ...
}

Now unless I annotate setApplicationContext with @XmlTransient the application won't start, complaining on applicationContext being an interface and therefore being impossible to bind to JAXB. What am I missing? Why is JAXB trying to bind ApplicationContext to XML?

Stacktrace or it didn't happen

####<Jun 22, 2011 7:28:31 PM CEST> <Info> <ServletContext-/MyApp> <duck> <myserver> <[ACTIVE] ExecuteThread: '0' for queue: 'weblogic.kernel.Default (self-tuning)'> <<WLS Kernel>> <> <> <1308763711259> <BEA-000000> <Initializing Spring root WebApplicationContext> 
####<Jun 22, 2011 7:28:32 PM CEST> <Error> <HTTP> <duck> <myserver> <[ACTIVE] ExecuteThread: '0' for queue: 'weblogic.kernel.Default (self-tuning)'> <<WLS Kernel>> <> <> <1308763712595> <BEA-101216> <Servlet: "myApp-jax-ws-servlet" failed to preload on startup in Web application: "MyApp.war".
javax.xml.ws.WebServiceException: Unable to create JAXBContext
    at com.sun.xml.ws.model.AbstractSEIModelImpl.createJAXBContext(AbstractSEIModelImpl.java:164)
    at com.sun.xml.ws.model.AbstractSEIModelImpl.postProcess(AbstractSEIModelImpl.java:94)
    at com.sun.xml.ws.model.RuntimeModeler.buildRuntimeModel(RuntimeModeler.java:281)
    at com.sun.xml.ws.server.EndpointFactory.createSEIModel(EndpointFactory.java:363)
    at com.sun.xml.ws.server.EndpointFactory.createEndpoint(EndpointFactory.java:202)
    at com.sun.xml.ws.api.server.WSEndpoint.create(WSEndpoint.java:496)
    at com.sun.xml.ws.api.server.WSEndpoint.create(WSEndpoint.java:539)
    at weblogic.wsee.jaxws.JAXWSDeployedServlet.getEndpoint(JAXWSDeployedServlet.java:183)
    at weblogic.wsee.jaxws.JAXWSServlet.registerEndpoint(JAXWSServlet.java:135)
    at weblogic.wsee.jaxws.JAXWSServlet.init(JAXWSServlet.java:64)
    at weblogic.wsee.jaxws.JAXWSDeployedServlet.init(JAXWSDeployedServlet.java:54)
    at javax.servlet.GenericServlet.init(GenericServlet.java:241)

    ... lots of weblogic stuff ...

Caused By: java.security.PrivilegedActionException: com.sun.xml.bind.v2.runtime.IllegalAnnotationsException: 2 counts of IllegalAnnotationExceptions
org.springframework.context.ApplicationContext is an interface, and JAXB can't handle interfaces.
    this problem is related to the following location:
        at org.springframework.context.ApplicationContext
        at public final org.springframework.context.ApplicationContext my.package.myApp.service.db.DBManager.getApplicationContext()
        at my.package.myApp.service.db.DBManager
        at public my.package.myApp.service.db.DBManager my.package.myApp.service.sso.SSOInterface.getDBManager()
        at my.package.myApp.service.sso.SSOInterface
        at public my.package.myApp.service.sso.SSOInterface my.package.myApp.ws.inBound.jaxws.SetSsoInterface.arg0
        at my.package.myApp.ws.inBound.jaxws.SetSsoInterface
org.springframework.context.ApplicationContext does not have a no-arg default constructor.
    this problem is related to the following location:
        at org.springframework.context.ApplicationContext
        at public final org.springframework.context.ApplicationContext my.package.myApp.service.db.DBManager.getApplicationContext()
        at my.package.myApp.service.db.DBManager
  开发者_Go百科      at public my.package.myApp.service.db.DBManager my.package.myApp.service.sso.SSOInterface.getDBManager()
        at my.package.myApp.service.sso.SSOInterface
        at public my.package.myApp.service.sso.SSOInterface my.package.myApp.ws.inBound.jaxws.SetSsoInterface.arg0
        at my.package.myApp.ws.inBound.jaxws.SetSsoInterface

    at java.security.AccessController.doPrivileged(Native Method)
    at com.sun.xml.ws.model.AbstractSEIModelImpl.createJAXBContext(AbstractSEIModelImpl.java:151)
    at com.sun.xml.ws.model.AbstractSEIModelImpl.postProcess(AbstractSEIModelImpl.java:94)
    at com.sun.xml.ws.model.RuntimeModeler.buildRuntimeModel(RuntimeModeler.java:281)
    at com.sun.xml.ws.server.EndpointFactory.createSEIModel(EndpointFactory.java:363)
    at com.sun.xml.ws.server.EndpointFactory.createEndpoint(EndpointFactory.java:202)
    at com.sun.xml.ws.api.server.WSEndpoint.create(WSEndpoint.java:496)
    at com.sun.xml.ws.api.server.WSEndpoint.create(WSEndpoint.java:539)
    at weblogic.wsee.jaxws.JAXWSDeployedServlet.getEndpoint(JAXWSDeployedServlet.java:183)
    at weblogic.wsee.jaxws.JAXWSServlet.registerEndpoint(JAXWSServlet.java:135)
    at weblogic.wsee.jaxws.JAXWSServlet.init(JAXWSServlet.java:64)
    at weblogic.wsee.jaxws.JAXWSDeployedServlet.init(JAXWSDeployedServlet.java:54)
    at javax.servlet.GenericServlet.init(GenericServlet.java:241)

        ... lots of weblogic stuff again ...

Caused By: com.sun.xml.bind.v2.runtime.IllegalAnnotationsException: 2 counts of IllegalAnnotationExceptions
org.springframework.context.ApplicationContext is an interface, and JAXB can't handle interfaces.
    this problem is related to the following location:
        at org.springframework.context.ApplicationContext
        at public final org.springframework.context.ApplicationContext my.package.myApp.service.db.DBManager.getApplicationContext()
        at my.package.myApp.service.db.DBManager
        at public my.package.myApp.service.db.DBManager my.package.myApp.service.sso.SSOInterface.getDBManager()
        at my.package.myApp.service.sso.SSOInterface
        at public my.package.myApp.service.sso.SSOInterface my.package.myApp.ws.inBound.jaxws.SetSsoInterface.arg0
        at my.package.myApp.ws.inBound.jaxws.SetSsoInterface
org.springframework.context.ApplicationContext does not have a no-arg default constructor.
    this problem is related to the following location:
        at org.springframework.context.ApplicationContext
        at public final org.springframework.context.ApplicationContext my.package.myApp.service.db.DBManager.getApplicationContext()
        at my.package.myApp.service.db.DBManager
        at public my.package.myApp.service.db.DBManager my.package.myApp.service.sso.SSOInterface.getDBManager()
        at my.package.myApp.service.sso.SSOInterface
        at public my.package.myApp.service.sso.SSOInterface my.package.myApp.ws.inBound.jaxws.SetSsoInterface.arg0
        at my.package.myApp.ws.inBound.jaxws.SetSsoInterface

    at com.sun.xml.bind.v2.runtime.IllegalAnnotationsException$Builder.check(IllegalAnnotationsException.java:102)
    at com.sun.xml.bind.v2.runtime.JAXBContextImpl.getTypeInfoSet(JAXBContextImpl.java:478)
    at com.sun.xml.bind.v2.runtime.JAXBContextImpl.<init>(JAXBContextImpl.java:308)
    at com.sun.xml.bind.v2.runtime.JAXBContextImpl$JAXBContextBuilder.build(JAXBContextImpl.java:1149)
    at com.sun.xml.bind.v2.ContextFactory.createContext(ContextFactory.java:169)
    at com.sun.xml.bind.api.JAXBRIContext.newInstance(JAXBRIContext.java:160)
    at com.sun.xml.ws.developer.JAXBContextFactory$1.createJAXBContext(JAXBContextFactory.java:74)
    at com.sun.xml.ws.model.AbstractSEIModelImpl$1.run(AbstractSEIModelImpl.java:159)
    at com.sun.xml.ws.model.AbstractSEIModelImpl$1.run(AbstractSEIModelImpl.java:151)
    at java.security.AccessController.doPrivileged(Native Method)
    at com.sun.xml.ws.model.AbstractSEIModelImpl.createJAXBContext(AbstractSEIModelImpl.java:151)
    at com.sun.xml.ws.model.AbstractSEIModelImpl.postProcess(AbstractSEIModelImpl.java:94)
    at com.sun.xml.ws.model.RuntimeModeler.buildRuntimeModel(RuntimeModeler.java:281)
    at com.sun.xml.ws.server.EndpointFactory.createSEIModel(EndpointFactory.java:363)
    at com.sun.xml.ws.server.EndpointFactory.createEndpoint(EndpointFactory.java:202)
    at com.sun.xml.ws.api.server.WSEndpoint.create(WSEndpoint.java:496)
    at com.sun.xml.ws.api.server.WSEndpoint.create(WSEndpoint.java:539)
    at weblogic.wsee.jaxws.JAXWSDeployedServlet.getEndpoint(JAXWSDeployedServlet.java:183)
    at weblogic.wsee.jaxws.JAXWSServlet.registerEndpoint(JAXWSServlet.java:135)
    at weblogic.wsee.jaxws.JAXWSServlet.init(JAXWSServlet.java:64)
    at weblogic.wsee.jaxws.JAXWSDeployedServlet.init(JAXWSDeployedServlet.java:54)
    at javax.servlet.GenericServlet.init(GenericServlet.java:241)

    ... more weblogic stuff ...


By default JAXB implementations will map all public fields and properties. You can use the @XmlTransient annotation to prevent properties for being mapped:

@XmlTransient
public void setFooService(FooService f) {
    ...
}


JAXB takes all bean properties (accessed by getters/setters) and tries to marshal or unmarshal it.

One things I don't understand - are you trying to marshal BazService? Isn't is a singleton service?


Another option is to inject fooService via constructor arg

BlahService { ... public BlashService(FooService f) { this.fooService=f; }

0

精彩评论

暂无评论...
验证码 换一张
取 消