Superdynamical webs - interfaces
One of the main difficulties with whom developers of interfaces of webs - applications collide{face}, will be, that after the page appeared in a browser of the client, communication{connection} of a browser with the server comes to an end. Any action with an element of the interface demands the repeated reference{manipulation} to the server with repeated loading new page. Because of it the web - application loses the elegance and slowly works. In given clause{article} I shall tell about how the given problem can be solved with help JavaScript and object XMLHttpRequest.
I am confident, that the traditional model of the interface of webs - applications is familiar to you. The user requests page from the server which on the server is created, and then is sent a browser. The given page has the HTML-elements describing the form in which the user enters the data. After that the user sends the data on the server and receives the new page based on the entered data, and process repeats. All this process is defined{determined} by the nature of the HTTP-report and differs from how we work with usual applications which interface is inextricably related with program logic.
Let's take a simple example of input of serial number{room} in any Windows-application. According to rules after you stop to enter an intricate set of figures and letters into fields, near to them the green "tick" meaning will appear, that you have entered correct number{room}. She appears instantly, as result of logic "vshitoj" in the interface. As soon as you have stopped to dial the number, the program checks it and gives out the answer.
In the web - interface this standard behaviour looks completely in another way. Certainly, fields in which you enter serial number{room} look the same way, but after end of input, it is necessary to the user, having pressed the button to send page on the server which will check up the entered data. Back to the user the new page where the message on correct or wrong serial number{room} will be deduced{removed} will return. The user in case of failure should return on the previous page and again to repeat attempt. And so indefinitely.
Certainly not often the web - application demands from the user to enter serial number{room}, but there is a uncountable set of other examples where fast reaction of the interface to actions of the user very much would be useful. And as all program logic is on the server, to receive such result in the traditional web - application rather difficultly.
On a stage appears JavaScript
Thanking JavaScript it is possible to transfer the certain quantity{amount} of program logic to HTML-page that will allow to react to actions of the user quickly. However this decision has one main lack. The first problem consists that as soon as JavaScript gets in a browser of the user together with page, the program logic is browsable to the naked eye. In a case for example with check of correctness of entered e-mail address it can be and it is not terrible, but if check is connected to serial number{room}, the algorithm of check becomes accessible to everyone who has downloaded page, and it is unacceptable.
The second problem consists that serious program logic in page to place it is impossible, as the interface simply is not intended for this purpose. All logic should be at a level of the application, instead of the user interface, and it means - we again come back on the server. The problem is supplemented still with that, what not always with confidence it is possible to expect presence JavaScript in a browser of the client. While the majority of users leave support JavaScript in the browsers switched on, there is a significant amount of users which do not do{make} it, or use such browser where JavaScript is absent or is absolutely not necessary as a class. Hence all logic which does{makes} JavaScript on the party of the client, all the same it is necessary to check on the server just in case.
Object XMLHttpRequest
The decision of this problem can become object XMLHttpRequest. This object for the first time has been realized by company Microsoft as object ActiveX, but now he is accessible as the built - in object in all browsers Mozilla and Safari. This object allows JavaScript-T to carry out HTTP-searches to the removed server needlessly to reload page. As a matter of fact HTTP-searches are sent and turn out completely behind "side scenes" of page, and the user of them at all does not notice.
It is a huge step forward as allows the developer of the web - application to reach{achieve} that desired purpose - creation of the fast user interface with preservation thus of program logic on the server. With help JavaScript-b the data entered by the user, are sent on the server, there they are processed also the user practically there and then obtains the answer to the entered data.
Let's start with bases
Because of the inconsistent history object XMLHttpRequest yet is not a part of any standard (though something similar was already offered in specification W3C DOM Level 3 Load and Save). Therefore there are two excellent{different} from each other a method of a call of this object in a code of a script. In Internet Explorer object ActiveX is caused so:
var req = new ActiveXObject (" Microsoft. XMLHTTP ");
In Mozilla and Safari it is done{made} easier (as there it is the object which has been built - in in JavaScript):
var req = new XMLHttpRequest ();
Certainly because of such distinctions it is necessary for you to create in a code of a branch, each of which will be carried out depending on in what browser the script is loaded. There are some ways how to make it (including various odd khaki and a method of " conditional comments "). But I think what in the best way simply to check in a code, whether this or that object is supported by a browser. As a good example the code taken from site Apple where the documentation on this object is laid out can serve. Give them and we shall use:
var req;
function loadXMLDoc (url) {
// branch for native XMLHttpRequest object
if (window. XMLHttpRequest) {
req = new XMLHttpRequest ();
req.onreadystatechange = processReqChange;
req.open ("GET", url, true);
req.send (null);
// branch for IE/Windows ActiveX version
} else if (window. ActiveXObject) {
req = new ActiveXObject (" Microsoft. XMLHTTP ");
if (req) {
req.onreadystatechange = processReqChange;
req.open ("GET", url, true);
req.send ();
}
}
}
In this code it is especially important to pay attention to property onreadystatechange. See, as to him value of function processReqChange is appropriated{given}. This property - khendler events which is started every time when the status of object req varies. Statuses are designated by numbers{rooms} with 0 (object neinicializirovan) on 4 (the search is executed). Important it because our script will not look forward to hearing from the server to continue the job. The HTTP-search will be generated and sent on the server, but the script will be carried out further. That we have chosen such variant of behaviour, we cannot return simply at the end of function result of search as we do not know, we have received it by this time whether or not. For this purpose we also have provided function processReqChange which will trace a status of object req, and informs us during necessary time, that process of reception of the document is finished, and we can go further.
For this purpose function processReqChange needs to check two things. The first - to wait, when the status of object req will change on 4 (meaning, that process of reception of the document from the server is finished). The second, it to check up the HTTP-status of the answer. You know, that the code 404 means " a file is not found " and 500 - " there was a mistake on the server ". But the old kind code 200 (" all OK ") which means is necessary for us, that on the server our search has been successfully executed. If we have received both a status 4 and a code 200, we can continue performance of our script and process the results received from the server. Certainly otherwise we should process all mistakes, for example, if the code of the answer differs from 200.
function processReqChange ()
{
// only if req shows "complete"
if (req.readyState == 4) {
// only if "OK"
if (req.status == 200) {
//.. processing statements go here...
} else {
alert (" There was a problem retrieving
the XML data:n " + req.statusText);
}
}
}
In practice
I am going to create a working example for demonstration of the above-stated ideas. In many webs - applications there is a procedure when the new user is registered on the server and it is required to choose "nik" for registration. Very much often this "nik" should be unique and consequently after the user has chosen to itself "nik", on the server check on a database of users is carried out, is already such "nik" whether or not. If you were ever registered on any post web - server, you remember how tiresomely to look for "nik", which else nobody uses. It would be very good, if check was carried out needlessly every time to update page.
For the decision we shall use four key elements: the XHTML-form, function JavaScript specially written for the given situation, two our general{common} functions about which we spoke above, and at last a server script which will address to a database.
The form
It is the easiest part of job - the simple form with a field for input "nika". onblur we adhere our script of check to event. To deduce{remove} to the user the message on results of check, I have inserted it into the form and have hidden with help CSS. It is more elegant and polite way, than a standard dialog box of function alert ().
<input id = "username" name = "username" type = "text"
onblur = " checkName (this.value, ") "/>
<span class = "hidden" id = "nameCheckFailed">
This name is in use, please try another.
</span>
In CSS properties of a class hidden, and also one more class error which serves for a conclusion of messages on a mistake are declared.
span.hidden {
display: none;
}
span.error {
display: inline;
color: black;
background-color: pink;
}
Processing of the entered data
Function checkName serves for check of the data entered by the user the form. The problem of function - to take the data, to decide, to what server script these given to give, call other function which will make all "dirty" job with HTTP-searches and answers, and then to process the answer. This our function will consist of two parts. One part - takes the data from the form, and another - processes the answer from the server. I shall explain, what for it is made, hardly later.
function checkName (input, response)
{
if (response! = ") {
// Response mode
message = document.getElementById (' nameCheckFailed ');
if (response == ' 1 ') {
message.className = ' error ';
} else {
message.className = ' hidden ';
}
} else {
// Input mode
url = ' http: // localhost/xml/checkUserName.php? q = ' \
+ input;
loadXMLDoc (url);
}
}
The answer is processed simply - the answer which we shall receive from a server script, will be either 1, or 0.1 means, that such "nik" already by someone is used. Depending on the answer our function changes the name of a class of the message on a mistake - it either is shown, or hidden. As it is understandable from a code, job on the server is carried out with a script checkUserName.php.
Formation of HTTP-search and the answer
As you saw above, job with HTTP is carried out by two functions: loadXMLDoc and processReqChange. In the first practically anything to change it is not necessary, and in the second it is required to change something for job about a DOM-ohm.
As you remember, while the successful result of performance of search will not be transferred{handed} to function processReqChange, we cannot return any value from this function. Because of it we need to carry out an obvious call of function from other place of a code to use result. That is why function checkName is broken into two parts. Thus, the main task of function processReqChange will be to process the XML-answer received from the server, and to pass the certain value from this answer of function checkName.
We do not want to bring any specific code as these functions can be used and other elements of page for the reference{manipulation} to the server in these functions. Therefore we also did not enter in function processReqChange a name of function checkName. Instead of it we have decided, that the server itself in the answer will denominate function which to it addressed.
<? xml version = " 1.0" encoding = "UTF-8"
standalone = "yes"?>
<response>
<method> checkName </method>
<result> 1 </result>
</response>
Analysis of this simple answer is carried out without any problems.
function processReqChange ()
{
// only if req shows "complete"
if (req.readyState == 4) {
// only if "OK"
if (req.status == 200) {
//.. processing statements go here...
response = req.responseXML.documentElement;
method = response.getElementsByTagName (' method ') \
[0]. firstChild.data;
result = response.getElementsByTagName (' result ') \
[0]. firstChild.data;
eval (method + ' (", result) ');
} else {
alert (" There was a problem retrieving \
the XML data:n " + req.statusText);
}
}
}
Having addressed to property responseXML object XMLHttpRequest, we receive the XML-answer which has come from the server which we then assort with help DOM. Having taken from the answer the name of function which demanded this answer, we know, what function should pass the received value. After you finish testing, clean{remove} a condition else that the script did not disturb users the superfluous message on a mistake.
Server script
Last element of our mosaic is a server script which will receive search, to process it and to return the answer as XML. In our example the script will address to a database of users to define{determine}, whether is used already given "nik" whether or not. For brevity in my example the script does not use a database, and simply checks two names "Drew" and "Fred".
<? php
header (' Content-Type: text/xml ');
function nameInUse ($q)
{
if (isset ($q)) {
switch (strtolower ($q))
{
case ' drew ':
return ' 1 ';
break;
case ' fred ':
return ' 1 ';
break;
default:
return ' 0 ';
}
} else {
return ' 0 ';
}
}
?>
<? php echo ' <? xml version = " 1.0" encoding = "UTF-8"
standalone = "yes"?> ';?>
<response>
<method> checkName </method>
<result> <? php
echo nameInUse ($ _GET [' q '])?>
</result>
</response>
Certainly, the same procedure of check should be provided and in that server script which will be carried out when the user will press button " Submit " on the form of registration. It if at him in a browser has been switched - off JavaScript, or the user has intentionally entered "nik" which is already used. Except for that on the loaded sites can so to happen, that during a choice "nika" he was free, and at the moment of submission of it already someone has borrowed{occupied}.
As the following step expand functionality of a script. For example the server can return variants alternative "nikov" on a basis "nika", chosen the user, but already borrowed{occupied}.
In summary
This small example only slightly concerns a subject of use of object XMLHttpRequest. only some examples of his use: Google Suggest (http: // www.google.com/webhp? complete=1 <http: // www.internet-technologies.ru/? url=http%3A%2F%2Fwww.google.com%2Fwebhp%3Fcomplete%3D1>) where XMLHttpRequest is used to prompt required words, application Ta-da Lists (http: // www.tadalists.com/<http: // www.internet-technologies.ru/? url=http%3A%2F%2Fwww.tadalists.com%2F>) where the data move on the server besides with help XMLHttpRequest due to what the interface works very quickly. The most interesting here not to force a code to work, and in finding even any interesting ways of his use.
Drew McLellan
Drew is a web application developer and technical author from just West of London, UK. A keen standards advocate, Drew helps out at the Web Standards Project in addition to maintaining a personal web site at allinthehead.com. When he grows up, he'd like to be a helicopter pilot.
From edition
1) Some examples of applications and the websites using object XMLHttpRequest:
Google Suggest - a fast conclusion of variants of search
Map of Switzerland - fast podgruzka maps in a background
Live Google results - delivery of results of search with Google without perezagruzki pages (it is used also Google API)
Live Search - search on a site with instant delivery of result
2) XMLHttpRequest follows the following safety rule - he can send search only on a site from which there has come page, and to receive the answer only from the same site.

|