Ajax
Progress Bar Using ajax:design Details
The sequence diagram below details the participants on both the client and server needed to provide an AJAX progress bar. The details are explained in further detail in the remainder of this document.
Tracking the progress of a server-side operation by a client requires two the operations which include:
- negotiate a task ID: This ID was used by the polling loop to track the progress of the task.
- Polling Loop: The Polling Loop would continue until the task is complete.
Now let us review each of the above operations in the more detail.
Negotiate a Task Id
An HTML form button onClick
event calls a JavaScript function which in turn'll create an object and the URL and call XMLHttpRequest
The back function as May is seen in the JavaScript code snippet below.
function Submittask () {
var url = "Task?action=starttask";
var bttn = window.document.getElementById ("Taskbutton");
Bttn.disabled = true;
Initrequest (URL);
Set callback function
Req.onreadystatechange = Processinitialrequest;
Req.send (NULL);
}
function initrequest (URL) {
if (window. XMLHttpRequest) {
req = new XMLHttpRequest ();
else if (window. ActiveXObject) {
Isie = true;
req = new ActiveXObject ("Microsoft.XMLHTTP");
}
Req.open ("Get", url, True);
}
The in the url
code above includes a URL parameter action
which are set to "StartTask." When req.send(null);
the ' statement is ' is executed the ' request is ' sent to the URL ' task ' the Client continues processing page Events Bec Ause the interaction is configured to be a asynchronous HTTP get with the req.open("GET", url, true);
statement.
On the server, a servlet are TaskServlet
mapped to the URL "task." When the Taskservlet receive a request containing a parameter ' action ' with the ' value of ' StartTask, "a new is Task
creat Ed as can is seen in the code snippet below.
if (action!= null) && action.equals ("StartTask")) {
//This task would take 1 5 cycles of the counter to complete
Task T = new Task (counter);
taskcounter++;
Tasks.put (Taskcounter + "", t);
//Return intial content
Response.setcontenttype ("Text/xml");
Response.setheader ("Cache-control", "No-cache");
PrintWriter pw = Response.getwriter ();
Pw.write ("<message&qt;" + taskcounter + "</message>");
Pw.flush ();
}
The snippet of code from the TaskServlet
above shows the TaskServlet
creating a new Task
object and placing it in a with java.util.HashMap
a uniq UE identifier. For this example, A is int
taskCounter
used to identify each Task
.
The taskCounter
increments a new is Task
created. In cases where the progress is tracked in a environment outside the firewall, more a unique identifiers May is Necessa Ry to prevent nefarious user from tracking operations they did not initiate.
The is the unique ID of this is returned to the taskCounter
XMLHttpRequest
XML document. This ID was later used to track the progress of the Task
"the" when the client polls the TaskServlet
. In this example, the TaskServlet
has a internal timer running on a thread which sleeps for 2 seconds and increments the VARIABL E counter
. To simulate a server-side operation This example sets the duration of increments Task
counter
S total).
On the client, the response from is TaskServlet
received by the XMLHttpRequest
object which calls the processIntialRequest()
callback function shown Below.
The //callback function for intial the request to schedule a task
Function processinitialrequest () {
if (req.ready state = = 4 {
if (Req.status =] {
var item = req.responseXML.getElementsByTagName ("message" ) [0];
var message = Item.firstChild.nodeValue;
//The initial requests gets the Targetid
Targetid = message;
Messagehash = 0;
Window.status = "";
Createprogressbar ();
ShowProgress (0);
}
var idiv = window.document.getElementById ("task_id");
idiv.innerhtml = "Task id=" + targetid;
//Do the initial poll in 2 seconds
settimeout ("Polltaskmaster ()");
}
}
This processInitialRequest()
function extracts the "task ID" from the XML document and assigns it to the variable targetId
. The function would then initialize the progress bar in the HTML DOM and show the initial progress of 0. The statement is setTimeout("pollTaskmaster()", 2000);
then executed to start the polling loop.
Polling Loop
The polling loop polls the TaskServet
using the task ID store in the targetId
variable until the server-side operation is complete D (a response is returned).
function Polltaskmaster () {
var url = "Task?messagehash=" + Escape (Messagehash) + "&targetid=" + targetid;
Initrequest (URL);
Req.onreadystatechange = Processpollrequest;
Req.send (NULL);
}
The
The polltaskmaster ()
function configures the Xmlhttrequest object with a URL and callback function. The request is sent to the URL "task" which be mapped on the server to the taskservlet
. The following code in the Taskservlet
are responsible for processing the request.
int percentage = 0;
if (Tasks.get (Targetid)!= null) {
Percentage = ((Task) Tasks.get (Targetid)). Get Precentcomplete (counter);
}
if ((Messagehash!=null) &&
(Integer.valueof (M Essagehash). Intvalue ()) = = percentage) {
//Nothing has changed
Response.set Status (httpservletresponse.sc_no_content);
} else {
Response.setcontenttype ("Text/xml");
Response.setheader ("Cache-control", "No-cache");
PrintWriter pw = Response.getwriter ();
if (percentage &qt; mb) percentage = 100;
Pw.write ("
" + percentage + "");
Pw.flush ();
}
In the code above, the Task
object was looked up using the unique ID ( Targetid
) provided in th E request. The Task getprecentcomplete
method was called with the current counter
to calculate the progress The operation and the results are returned in an XML document. Note this if the Messagehash
representing the current percentage of completion being displayed by the client Matches the percentage complete of the operation in the Task
(indicating no change) the Taskservlet 'll return a HTTP response code 304
( No Content
). This saves time for post processing of the "the" by "the client, time to message generation" by the Taskservlet, and bandwidth for transmitting.
Upon receiving the response from the object would call the TaskServlet
XMLHttpRequest
"do post processing of the processPollRequest()
" request.
function Processpollrequest () {
if (req.readystate = = 4) {
if (Req.status = = 200) {
var item = req.responseXML.getElementsByTagName ("message") [0];
var message = Item.firstChild.nodeValue;
ShowProgress (message);
Messagehash = message;
} else {
Window.status = "No Update for" + Targetid;
}
if (Messagehash < 100) {
SetTimeout ("Polltaskmaster ()", 5000);
} else {
SetTimeout ("complete ()", 2500);
}
}
}
The HTML DOM is updated by showProgress()
function if the req.status
HTTP status code is 200
. This function would detect if the percentage from the the ' server is complete ' and stop the polling loop by calling the function. Otherwise, the polling would continue to loop by executing the statement following setTimeout("pollTaskmaster()", 5000);
a 5 second.
<