Reputation: 65
I am using eclipse axis2 to create web service client from wsdl.
My impl method is:
public Output[] startProcess(Message[] Messages){
MyApplicationBean managementBean = (MyApplicationBean) FacesContext.getCurrentInstance().getExternalContext().getApplicationMap().get("myapp");
...
}
However when I execute:
http://localhost:8080/MyProject/services/portStartProcessService with method startProcess
I see in tomcat debug that it reaches my method, however the FacesContext.getCurrentInstance()
returns null.
My web.xml (part of it)
<servlet-mapping>
<servlet-name>Faces Servlet</servlet-name>
<url-pattern>*.jsf</url-pattern>
<url-pattern>/services/*</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>AxisServlet</servlet-name>
<url-pattern>/servlet/AxisServlet</url-pattern>
</servlet-mapping>
How can I use JSF beans (like application scope) in web services call?
Upvotes: 2
Views: 1203
Reputation: 12505
I know you do not want to hear this just yet, but you got the architecture wrong. JSF application context is useless with web service calls, because the whole idea of JSF is that GUI is built of stateful components stored:
Since neither session nor forms are available to web service calls, JSF does not apply here. You might as well ask how to make a web service that presses a JButton or inserts a CD into your CD-ROM.
I understand that you do not need the JSF components, but rather need some application logic that resides inside one of the managed beans, right?
Well, The easiest solution is to get a time machine, go back in time to when the project was planned and tell the architect that YOU NEVER PUT APPLICATION LOGIC INTO MANAGED BEANS. One of the reason is that they are unavailable to web service calls. Your application logic should reside in the service layer, provided by Spring or EJB.
Both Spring beans and EJBs are easy to reach from Axis services and from managed beans, and so you never need to access JSF managed beans from any place else than JSF front-end. If you do not like Spring and can't use EJB for some reason, build your service layer from POJOs, set it up in ApplicationContextListener and register in the application scope.
If such clean solution is unavailable and refactoring is impossible, you have two choices:
if the managed beans you try to reach are application scoped and eager, then they can be accessed in a JSP way, from the application context, using the venerable getAttribute method (you can access application context through the servlet context, which afaik you access through the message context, which in turn you access by the static MessageContext.getCurrentMessageContext method in Axis).
if the managed beans you want to use are request scoped and require some JSF plumbing (so you can not instantiate them by yourself) then you can pretend to be a FacesServlet and create the faces context by yourself; it is tricky but doable, a good and quite famous description is here: http://www.thoughtsabout.net/blog/archives/000033.html. You need will need servletrequest and servletresponse (from MessageContext). You can probably skip the parts required to pass the FacesContext on, because you will not require it to process any views.
Disclaimer: I never tried the last solution - it seems to work, although it is pretty dirty (and actually causes your web services to depend on JSF, which is bizzare).
Upvotes: 2