Start a thread as soon as a long post request comes in - servlets

I am trying to upload an image. I need to start a synchronising thread as soon as the http request comes in. Presently my Grails code starts only after the entire post data has been received.

The controller is in fact invoked as soon as the request comes in. Only when the image data is fetched from the http request body does the code stall and wait for the upload to finish.

Related

How can a server handle HTTP requests in the order in which they were sent?

I'm building a simple CRUD application where there is a client, a server, and a database.
The client can send two types of requests to the server:
POST requests that update a row in the database.
GET requests that retrieve a row in the database.
One requirement of my application is that the requests have to be handled in the order in which they were sent from the client. For example, if the user makes a POST request to update row 1 in the database, then they make a GET request to retrieve row 1 in the database, the response to GET request must reflect the changes made by the previous POST request. One issue is that there is no guarantee that the server will receive the requests in the same order that the requests went sent. Therefore, in the example above, it is possible that the server might receive the GET request first, then the POST request later, which makes the response to the GET request not able to reflect the changes made by the previous POST request.
Another requirement of the application is that the client should not have to wait for the server's response before sending another request (this constraint is to allow for faster runtime). So in the example above, one possible solution is let the client wait for the server response to the POST request, and then it can send the GET request to retrieve the updated row. This solution is not desirable under this constraint.
My current solution is as follows:
Maintain a variable on the client that keeps track of the count of all the requests a user has sent so far. And then append this variable to the request body once the request is sent. So if the user makes a POST request first, the POST request's body will contain count=1, e.g. And then if they make a GET request, the GET request's body will contain count=2. This variable can be maintained using localStorage on the client, so it guarantees that the count variable accurately reflects the order in which the request was made.
On the server side, I create a new thread every time a new request is received. Let's say that this request has count=n. This thread is locked until the request that contains count=n-1 has been completed (by another thread). This ensures that the server also completes the requests in the order maintained by the count variable, which was the order in which the request was made in the client.
However, the problem with my current solution is that once the user clears their browsing data, localStorage will also be cleared. This results in the count getting reset to 0, which makes subsequent requests be placed in a weird order.
Is there any solution to this problem?

Simple HTTP call without opening Browser

Hello everybody I'm trying to do a simple HTTP call to a Tomcat Server running on my server from my Android App. The server will then execute a certain command to my website. I created a button that when I click it runs the HTTP call from the App.
If I use the approach below, it opens the browser on my phone to run this HTTP. Is it possible to do something similar but not have my app open the browser???
Intent browserIntent = new Intent(Intent.ACTION_VIEW, Uri.parse("http://" + IP + ":8080/server/run.jsp"));
startActivity(browserIntent);
thank you so much in advance :D
Of course it starts your browser. Your code is explicitly asking Android to launch an app that can "view" the URL.
If you want your app to access the URL directly, use HttpURLConnection instead:
1.Obtain a new HttpURLConnection by calling URL.openConnection() and casting the result to HttpURLConnection.
2.Prepare the request. The primary property of a request is its URI. Request headers may also include metadata such as credentials, preferred content types, and session cookies.
3.Optionally upload a request body. Instances must be configured with setDoOutput(true) if they include a request body. Transmit data by writing to the stream returned by getOutputStream().
4.Read the response. Response headers typically include metadata such as the response body's content type and length, modified dates and session cookies. The response body may be read from the stream returned by getInputStream(). If the response has no body, that method returns an empty stream.
5.Disconnect. Once the response body has been read, the HttpURLConnection should be closed by calling disconnect(). Disconnecting releases the resources held by a connection so they may be closed or reused.

Is it possible to send partial reply to the client and later send complete response?

I use a payment gateway which uses the relay response url of my web application to return the transaction response or receipt information. The problem is that it uses a timeout i.e if it is 10 seconds since it made the request to the relay response url and if the relay response url didn't respond within that time then it will timeout. The problem i am trying to avoid or minimize is for the url to respond within the timeout period. One thing i have noticed is that this method that relay response url points to over the time has gotten bulkier and this may amount to the occasional timeouts that is happening. One solution i think could be to render partial response quickly like "Please wait...". If the payment gateway receives something from the relay response url then it shouldn't timeout. After that when the heavy processing is complete then the relay method sending full response which will be receipt in most cases. Is there a way to achieve this? I appreciate any help! The framework i am using for my application is grails 2.0.
I thought something like this would work but i was wrong.
def receiptFinal(){
...
}
def receipt(){
render "Please wait..."
redirect(controller: 'payment', action: 'receiptFinal')
}
Yes,it is quite possible I guess. Your payment gateway has to make two requests. One is to confirm whether validation/payment is all right or not. And, Second request to the client would be final response (like receipt etc)
It would totally depend on payment gateway.
--
Jitendra

What is the response received by IE for a duplicate post?

If you visit an aspx web form, and click the submit button causing a POST to the server, then click submit again causing a second POST before receiving a response from the first POST, what happens in terms of the response? Does the server process both requests simultaneously or serially? Does the server send both responses? Does the browser ignore one of the responses? This may be self explanatory after an answer to the previous questions, but if I were to call Response.Clear(); Response.End(); for the second request, what would happen on the browser end?
If there are no special means at the server side to handle multiple POSTs, the server will handle both requests independently. Whether or not the processing is concurrent - it depends:
if your first POST causes the whole page to reload then it is impossible to trigger the second POST before the page is processed at the server side (because your second click is made from the page which is already at the client side)
if your first POST causes an AJAX POST to the server and the processing takes some time at the server then it is possible that you end up with two POSTS from the same page processed concurrently at the server side
The server always sends responses and browsers do not ignore them. It is your code, at the server side or at the client side, to prevent such unintended multiple POSTs, for example by 302ing the response to another location which doesn't allow the user to rePOST the form.
Specifically, if you just clear the response (send an empty content) and the content type is text/html then the browser will render an empty page.
I would say just about any of those things could happen, depending on the exact timing.
I believe calling Response.Clear(); Response.End(); on the second request would cause an empty response which the browser would receive, possibly after receiving the results of the first request.

Iframe keep-alive function - what is needed to reset the session timeout?

I have a hidden iframe that refreshes every now and then, in order to keep the ASP.NET session up and running, for as long as the user is online.
However, I have been getting reports of users experiencing session timeouts, so now I am in doubt of what is needed to reset the session timer.
The hidden iframe's content page (simple html page) refreshes itself at a certain interval, which is significantly less than the session timeout.
My question is: Is it enough (for the session timer to reset) to let the page refresh itself, even when the server responds with a HTTP/1.x 304 Not Modified?
Is it simply the GET request itself that tells the webserver to reset the session timer?
Or do I need to make sure to actually fetch the page and receive a HTTP/1.x 200 OK response?
All you have to do to keep the session alive is send a request to a page from the current session. You can do this via iframes, or via ajax.
If you simply refresh the page in the IFrame, the response may be a cached one - thus the 304. You have to send a fresh request every time -
var url = "http://domain.com/defibrillator.aspx?" + (new Date()).getTime();
E.g.
http://domain.com/defibrillator.aspx?1556467987987
http://domain.com/defibrillator.aspx?5448796497878
http://domain.com/defibrillator.aspx?4123165487987
....
EDIT 1
Or you can use the Refresh HTTP header attribute.
EDIT 1.1
If you are using the codeproject article mentioned above, then try to model it using AJAX instead of iframes - it would save you a few bytes of extra iframe markup.
EDIT 2 - About HTTP 304 Not Modified
If the client has performed a
conditional GET request and access is
allowed, but the document has not been
modified, the server SHOULD respond
with this status code. The 304
response MUST NOT contain a
message-body, and thus is always
terminated by the first empty line
after the header fields.
This means that the request hasn't reached the ASP.NET pipeline, and has directly been served by IIS itself. ASP.NET environment doesn't know that a request has been made. So, it won't perform the session renewal.

Resources