As you may have guessed, in this article I’ll
attempt to develop a chat application by using AJAX as the workhorse
for sending out http requests without involving page reloading.
Building an AJAX-Based Chat: The Barebones Structure Chat
programs are common on the web these days. HTTP-based versions were
often built as Java applets, but today, developers have a wider range
of options when building chat programs. This article gets you started
with building one that uses AJAX as the workhorse for sending out http
requests without the need for page reloading.
You’ve been seen it
hundreds, if not thousands of times before. You’ve surfing the Web,
looking for a website that offers the possibility of meeting people and
talking in real time, and certainly many times during your exhaustive
search, you’ve been confronted with the user interface of an IRC
(Internet Relay Chat) application, most of the time developed in Java.
Let’s
be honest, people are made to talk. And that’s precisely the reason for
the massive proliferation of software aimed at providing real time
communication between users. Instant messaging programs rule all the
way, when it comes to being in touch with other people. However, for
fully web-based applications, things have been a little different. As I
mentioned before, http-based chat programs were most of the time built
as old Java applets, because of their relative ease to be included
within web pages, simply by fetching the appropriate Java files and
wrapping them into deprecated tags.
Fortunately,
on today’s Web, developers have a wider range of options for developing
chat applications, without the need to be a seasoned Java programmer.
Server-side scripting languages such as PHP
or ASP make it fairly easy to build chatters with a decent level of
responsiveness. Of course, the major drawback with using these
languages in developing pseudo real-time communication programs was the
natural inability to make http requests in the background,
without dealing with page reloads. As a result, most of these
applications involved the use of refresh meta tags for updating the
contents of the chat.
As you may have guessed, in this article
I’ll attempt to develop a chat application by using AJAX as the
workhorse for sending out http requests without involving page
reloading. Through this first tutorial, I’ll draw the general
guidelines for building this application, along with writing down some
of the JavaScript functions that will compose the complete program.
Hopefully, by the end of this series, you will have a pretty clear idea
of how the chat works, and certainly of the possible improvements that
can be introduced into the original application.
Defining the application’s core logic: working with requester objects
(Page 2 of 5 )
Before
I start defining the core functions that work with requester objects,
let’s pause for a moment and have a look at the basic appearance of the
chat application, depicted in the following screenshot:
In
the simplest terms, the chat application that I plan to develop is
based on common sense rather than on complicated programming logic. Due
to the limitations imposed by XMLHtttpRequest objects (or an ActiveX
control for Internet Explorer), which can handle only one request at a
time, I’ll use two independent requester objects, in order to get the
application to work. According to this, the first object will be
responsible for pushing user messages into a message stack, stored in a
simple MySQL database table, while the second object will be tasked with pulling a
given number of messages from the database table, to be displayed on a
message containing section.
What comes next, though? Since I’ll
need to handle two separate objects for handling http requests across
the application, the first step in building the chat will be defining
an object factory function, which will allow the instantiation of as
many requester objects as required. The pertinent function, not
surprisingly called “getXMLHttpRequestObject()”, looks like this:
function getXMLHttpRequestObject(){
var xmlobj;
// check for existing requests
if(xmlobj!=null&&xmlobj.readyState!=0&&xmlobj.readyState!=4){
xmlobj.abort();
}
try{
// instantiate object for Mozilla, Nestcape, etc.
xmlobj=new XMLHttpRequest();
}
catch(e){
try{
// instantiate object for Internet Explorer
xmlobj=new ActiveXObject('Microsoft.XMLHTTP');
}
catch(e){
// Ajax is not supported by the browser
xmlobj=null;
return false;
}
}
return xmlobj;
}
As
shown in the function above, different requester objects will be
instantiated and returned to calling code each time the function is
invoked. Aside from coding the lines where actual object instantiation
takes place, I’ve included some “try-catch” blocks for solving browser
incompatibilities, particularly due to the absence of native support
for XMLHttpRequest objects in Internet Explorer (hopefully this issue
will be fixed in IE 7).
Now, I’ve defined a function which allows
you to create the two requester objects required for sending out and
getting chat messages. Since the chat application can be divided into
two different programming modules –- sender and receiver -- where the
first one will insert new user messages into a MySQL database table,
and the second one will fetch messages for being displayed on the
browser, let’s focus our attention on developing the functions that
comprise the first module, for sending and stacking messages within the
database table. Just click below and keep on reading.
Sending chat messages: defining the “sendMessage()” function
As
you know, a typical chat application provides users with the ability to
send out messages through a simple form, and then display them on a
generic containing section where all online users communicate with each
other. For this reason, I’ll begin developing the “sender” module of
the application, by defining the “sendMessage()” function. It uses a
“sender” XMLHttpRequest object for triggering a post request to a given
file, and passes into it the user’s nickname, together with the
corresponding message. Here’s what it looks like:
function sendMessage(){
var user='php echo $user?>';
var message=document.getElementsByTagName('form')[0].elements
[0].value;
if(message.length>100){message=message.substring(0,100)};
// open socket connection
senderXMLHttpObj.open('POST','sendchatdata.php',true);
// set form http header
senderXMLHttpObj.setRequestHeader('Content-
Type','application/x-www-form-urlencoded');
senderXMLHttpObj.send('user='+user+'&message='+message);
senderXMLHttpObj.onreadystatechange=senderStatusChecker;
}
In
the simplest sense, the above function makes a post request to the
“sendchatdata.php” file, and sends as parameters the pair of
“user&message” variables, for pushing directly into the database
table. Of course, there are a few things worth noting here. As you may
have guessed, the backend of the chat will sit on a simple MySQL
database, which will be accessed with PHP. But fear not. Considering
the ease of querying the database, you can use another RDBMS (for
example MS Access) and work with ASP.
By returning to the
function’s code, you can see that I use a “senderXMLHttpRequest” object
for sending the request header, conjunctly with the pair of
parameters mentioned above. For the moment, I’m assuming that this
object has been previously instantiated by the
“getXMLHttpRequestObject()” function, so this will be discussed later,
when I explain the set of functions that initialize the chat.
Notice
right at the very beginning of the function how the lengths of messages
are checked in, by limiting the amount of characters to 100, as well
as how the user’s nickname is obtained. The line listed below:
var user='';
demonstrates
how to populate the “user” JavaScript variable with the contents of the
“$user” PHP variable. I’ve deliberately done this in order to use PHP
sessions for registering the nickname chosen by the user and for using
it during the chat session. Obviously, the entire registration process
will be done through a simple login page, which will be coded at a
later time. For the moment, after the message has been sent by using a
text input box, the “senderStatusChecker()” function is tied up to the
“onreadystatechange” handler, so it’s possible to check for the
progress of the request and insert the data into the database table.
Since
“senderXMLHttpRequest” objects are checked by the
“senderStatusChecker()” function, the next step in developing the chat
is looking at its corresponding definition.
Checking for the progress of sender requests: defining the “senderStatusChecker()” function
Once
a user has submitted a message, the application needs to determine
whether the post request has been successfully completed. If it has,
the display of messages will be immediately updated, which translates
into a faster visual response for the user that originally sent the
message. Therefore, considering that updating the messages currently
displayed can be easily handled after the insertion of a new message in
the database table, here is the definition for the
“senderStatusChecker()” function:
function senderStatusChecker(){
// check if request is completed
if(senderXMLHttpObj.readyState==4){
if(senderXMLHttpObj.status==200){
// if status == 200 display chat data
displayChatData(senderXMLHttpObj);
}
else{
alert('Failed to get response :'+
senderXMLHttpObj.statusText);
}
}
}
As
you can see, this function is a lot simpler than it really seems. What
it does essentially is check the status of the post request responsible
for inserting a new message into the database. In that case, the
display of messages needs to be quickly updated. If you study the above
code, you’ll see that the updating process is performed by the
“displayChatData()” function, which accepts a requester object as the
unique incoming parameter.
Having illustrated how the progress of
the requests made by the “sender” object is checked in, let’s now take
a look at the “displayChatData()” function, and see how the display of
chat messages is properly updated. Just keep reading.
Updating the display of messages: coding the “displayChatData()” function
(Page 5 of 5 )
As
I mentioned before, the list of the messages being displayed on the
chat page needs to be refreshed each time a new message is added to the
database table. Keeping this condition in mind, the chat application
uses the “displayChatData()” function, in order to perform the message
updating process. Here is the definition for the pertinent function:
function displayChatData(reqObj){
// remove previous messages
var mdiv=document.getElementById('messages');
if(!mdiv){return};
mdiv.innerHTML='';
var messages=reqObj.responseText.split('|');
// display messages
for(var i=0;i
var p=document.createElement('p');
p.appendChild(document.createTextNode(messages
[(messages.length-1)-i]));
mdiv.appendChild(p);
}
}
By
analyzing the source code for the function above, it’s pretty easy to
understand its operation. First, it removes all the messages previously
displayed and then obtains a new list. The following fragment of code
illustrates these processes:
// remove previous messages
var mdiv=document.getElementById('messages');
if(!mdiv){return};
mdiv.innerHTML='';
var messages=reqObj.responseText.split('|');
As
you can see, the function cleans up a “messages”
containing
element by resetting its “innerHTML” property. After all the messages
have been removed from the container, the new list of messages is
obtained by reading the value for the “responseText” property,
belonging to the requester object passed in as a parameter.
Since
all the messages will be fetched from the database first, and then
delimited by a pipe (“|”) character, for transmitting back to the
client, the below expression:
var messages=reqObj.responseText.split('|');
stores the messages in the “messages” array. This is handy for processing and displaying with a simple loop, like this:
for(var i=0;i
var p=document.createElement('p');
p.appendChild(document.createTextNode(messages
[(messages.length-1)-i]));
mdiv.appendChild(p);
}
As
you may have guessed, each message will be placed within the container
as a paragraph element, and displayed in descending order,
assuming that the last inserted message will be shown at the bottom of
the containing
.
By this point, I’ve provided you with
all the JavaScript functions that compose the “sender” module for the
chat application. Of course, the functions that you just saw seem
rather like isolated pieces, unconnected to the whole application due
to the fact that the remaining “receiver” module hasn’t been coded yet.
Moreover, there is much of the server-side processing left to be
developed, including insertion and retrieval of messages. So, bear with
me and wait for the next part of this series, where I’ll be writing the
rest of the AJAX-based chat.
Wrapping up
Over the
first part of this series, I’ve demonstrated how to build the barebones
of a web-based chat system, by utilizing AJAX as the trusty workhorse
for sending, retrieving and updating user messages, without the need to
appeal to “refresh” meta tags, and certainly keeping all the
programming requirements under the scope of JavaScript and PHP.
However,
exciting things are just around the corner. As I said before, in the
next tutorial, I’ll write the “receiver” JavaScript module, useful for
fetching messages from the database table, together with some
additional functions for building the layout of the chat page.
|