I currently have a GWT application which uses the RequestBuilde to
send messages to a servlet I have (using POST and GET), and my servlet
(in doPost and doGet) "pauses" the request (this is done by using
Servlets 3.0 spec) and adds it to a queue.
Additionally I have a
Daemon thread which runs in the background and "plays" the request
when there is new data.
This works great for me apart from the fact that I'm just sending
strings for now and I'd like to utilize the RPC mechanism to send
Objects.
My question is this: If I create my myServiceImpl class which extends
RemoteServiceServlet how should I handle the doPost and doGet if at all? I need to pause my request to utilize the asynchronous support, where should this be accomplished? I though maybe to call this.getThreadLocalRequest() method in my RPC method in myServiceImpl class but I'm not sure how wise that will be. I'm not
sure I even understand how GWT handles the call from the client side
of that asynchronous interface.
Does it by any chance call the doGet for example of the servlet and
makes sure it calls the required RPC method?
I'm sorry if I made a mess of things it's just that I can't find more
detailed technical information as exactly how this RPC business works.
Appreciate any lending hand
Ittai
To understand RPC forget about POST and GET it works differently (that is from a programming perspective. Internally it does use it, but you don't see or need to understand it, unless you want to do something exotic). A good starting point is on RPC is the GWT docs: http://code.google.com/webtoolkit/tutorials/1.6/RPC.html
To give you a summary. When using RPC your servlet myServiceImpl needs to implement the methods of an interface named myService, besides extending the RemoveServiceServlet. The methods get as arguments the data you want to send to the server.
Next to the myService interface you need to create an myServiceAsync interface (both interface's should be in a client subpackage). This myServiceAsync inteface should contain the same methods as the myService interface except each method returns void and has an additional last argument AsyncCallback callback.
In you client you need to instrument GWT to generate the RPC via GWT.create (see the documentation for the details.
To use RPC, call the methods on the myServiceAsync interface in your client code and GWT takes care of sending it to the servlet. The servlet will then call the matching method with the arguments you passed on the client. This is done asynchronous. Thus the client return directly from the call.
When the server sends the result back the callback you passed myServiceAsync is used or OnError or OnSuccess is called. OnError if the method on the server side threw an error, else OnSuccess. The OnSuccess will have as argument the return value from what you returned in the method implemented by your servlet.
I think the main misunderstanding I had at the time was related to the fact that GWT RPC builds on the servlet mechanism (internally) and so trying to use that mechanism with asynchronous servlets was, at the time, impossible since GWT RPC was built on servlets 2.5 (again, at the time).
Related
I have this situation:
A third-party library that has a method with an abstract class as parameter:
On server side I could call this third-party method with
public void save(){
ThirdParty.doSomethingBackground(new Callback() {
public void done(Exception e) {
//SOMETHING TO DO
}
});
}
I could call this method on client doing something like:
ServerSide.save() and passing my implementation of CallBack, but I donĀ“t want to see Third-party library from my client, I need to do this transparent for the situation when I change my third-party library.
What is the best practice to do so?
Tks
Create a custom intermediary object that holds all information needed to create your custom Callback implementation. It would resemble a simple DTO. If you are using some sort of remoting, then the object would be serializable.
Pass this intermediary object from client to server. On the server, transform the intermediary object to your Callback implementation before making the call to the ThirdParty.
It's not clear from your question if your ThirdParty library call is asynchronous. If you want the ServerSide.save call to be synchronous, and the ThirdParty library call is asynchronous, then you would want to block the server thread and wait on the ThirdParty result before returning. One way of doing that would be to use Java 6/7's FutureTask class.
If you did not want the ServerSide.save call to be synchronous, then you would either need to have the client poll the server looking for the result in another server call, or devise two-way communication. Two-way communication is usually much more complex though, and heavily dependent on whatever platform/protocol/technology you are using.
I'd like to know what the expected lifecycle behavior is for a class that responds to REST requests.
I have a class that's derived from javax.ws.rs.core.Application that identifies another class for responding to requests.
In that other class, it is annotated with #Path("foo") and methods within this class are annotated with #Path("bar"). When a request is made to foo/bar, I can see that the constructor is executed, then the PostConstruct method is properly called. After the method returns a response to the client, I can see that PreDestroy is called and then the class is squashed. On the next request, the process repeats.
Is this the correct behavior? Or is there a way that this class can remain in memory so that it doesn't need to go through the constructor and PostConstruct each time a request is made? This method relies on JAXB marshalling and various XSL transformations - I would like to cache the compiled XSLT transformation objects as well as the results of some transformations, but if the class is reinstantiated each time it is called, it makes it impossible for local caching.
This is running with Java 7, Wink, and Tomcat 7. Can someone please let me know if this is the expected behavior, or am I missing something that will just keep this class alive?
Thanks.
By JAX-RS specification, the Resources (the classes annotated with #Path) are created per request.
There are several ways to override this behavior.
The simplest way that can be used according to the JAX-RS specification, is to create a resource instance yourself (you are responsible to call the PostConstruct, not sure when and how you call to PostDestroy in this case) and return it using javax.ws.rs.core.Application.getSingletons()
Alternately, you can put #org.apache.wink.common.annotations.Scope(ScopeType.SINGLETON) annotation on your resource.
If you use Spring, Wink has a neat Spring integration module, so the Spring's lifecycle will be used. See http://incubator.apache.org/wink/1.0/html/5.5%20Spring%20Integration.html
I really like functional programming, I like its immutability concepts and also it's no side-effects concepts for functions.
I'm trying to take some of these concepts into java.
Now I have some kind of a servlet which receives a request and if browser did not send a cookie to server then i would like to create a cookie with a certain path to the user.
now inside the servlet i don't want to hold that logic because its common to multiple servlets.
so i extract it into some kind of a cookie manager which will do that:
CookieManager.java.handleCookies(request, response)
Check if browser sent cookie.
If not set cookie with new session cookie value with certain path.
however i don't like it because now the servlet will call the CookieManager.java.handleCookie will have a side effect I would rather it to return some kind of a response and further use it in my servlet wihtout having it effect its parameters that i'm passing into it.
anyone can suggest a solution which would both be elegant, no side effects, and excellent in performance?
thanks
You can make use of servlet filter. It would be well suited for your case. You can map your filter to URL pattern and write your code inside dofilter method. Filters are recommended if you want to have pre and post prcoess of request/response. Since you are doing preprocess for you request it would fit in your case. If is also loosely coupled, because you can remove it, modify it, or add another rule anytime without modifying the core servlet code.
One good solution is to use create a servlet which will act as a parent class for all other servlets.
Now in this servlet put this logic of cookie handling in a common function say handlecookie.
In your get and post APIs of this servlet first call this handleCookie and then service API of servlet (keep this empty)
In al child servlet classes you can only override the service class inherited from the parent class and things should work fine for you
Servlet filters are other solution that you can make use of.
Is there a way to get a list of all SOAP headers in a web method with plain JAX-WS? I know this can be done by using Metro specific classes (HeaderList hl = messageContext.get(JAXWSProperties.INBOUND_HEADER_LIST_PROPERTY)). However I'm not sure if I can rely on having that implementation at runtime so I'd like to stick to JAX-WS.
I also know about the header attribute of the #WebParam annotation. I'd prefer not having to specify the header parameter there. The reason is that my web service has some IDs that are common to all web methods and this would pollute the interface. Also in case another ID comes along or one gets removed again (the spec is not final yet) I'd have to modify every single web method. Also there would be no reason anymore for using a header - it could be a normal method parameter.
The third way I know of is using a handler via #HandlerChain but then I have no way of connecting the headers with the executed web method. The IDs I mentioned are important for further processing - they are not just access control that can work independently of the method.
If you implement a request handler, you can store the headers in a thread local, static variable and implement some kind of access mechanism to it for your service method implementation.
I have two servlets A & B.
On B i intend to have a a method isAvailable() which A will call to check the status. If this method returns true then im going to pass it an object to B.
On doing a bit of reading i'm seeing a couple of options non of which im that familar with. JNDI with remote EJB , RMI or simple HTTP (not sure how youd do the last)
What do you guys think ? Any other options ?
Why not make use of the fact that your infrastructure is already talking HTTP ?
So servlet A can perform an HTTP GET on a particular path to check a status (either sending back an object or checking an HTTP response code - this latter method seems a misuse of status codes, however), and PUT/POST an object if required. I note that you're running across multiple hosts, and this will work in your scenario.
The objects can be serialised using standard Java, or via a representation such as XML - perhaps serialised using XStream).
That would seem to me a pretty straightforward way to leverage off the infrastructure you have.
Are your servlets running in the same application server? If so, you might like to use Spring to inject B into A so that the method can be called directly.
Even if the servlets are running in different containers, you can expose them (using Spring again) as Remote objects and similarly inject B into A (except that this will mean that the Spring container will inject a proxy for the remote object). This has zero footprint in your code (i.e. it's all defined by config files and Spring takes care of everything for you)
It looks like this isAvailable() method in Servlet B accesses some kind of "global" data which is stored in the Servlet. Could you extract this object to a separate Singleton which then is available for both Servlets?
There is one instance of Servlet A on a master host and many of Servlet B each on its own host with its own tomcat instances.
You can use java.net.URLConnection to programmatically fire a HTTP request. You can find here a simple tutorial.
Let A fire a HTTP request to B and have in B a servlet which listens on those requests and returns the response accordingly. This can be a simple response.getWriter().write("ok"); or so. You can even return a XML string and so on. In A you can then read this value from the InputStream of the URLConnection.