Вы находитесь на странице: 1из 16

Part 1.

Introduction to chat applications

As soon as the Internet developed, the means of communication over the Internet developed too.
However on the Internet we have the same two means of communication like on the traditional
communication: asynchronous communication and synchronous communication.

The asynchronous communication is done over a longer period of time and does not require that
the discussion partners take part to it in the same time. This kind of communication includes the
emails (someone is sending the message and the receiver will receive it after a period of time, he
will read it and eventually he will send another message as an answer and so on) and the
discussion forums (someone is posting a message and other persons at different moments of time
will post an answer message to the initial message or to another answer message of the initial

The alternative to asynchronous communication is the synchronous communication, in which

case all the discussion partners will take part to it in the same time. The chat is the main example
of this communication type. Two or more persons could enter a chat room to discuss on the same
time. One of the most popular chat systems was and still is the IRC. Other used chat programs
are those of messenger type such as ICQ, Yahoo Messenger, AOL Instant Messenger, MSN
Messenger, etc. As an alternative to all these methods to implement a chat, in this article I will
teach you how you can build your own web driven chat using ASP and pure HTML pages
(without applets or plug-ins).

Part 2.
Asp web based chats vs. chat programs

I am almost sure that everybody has entered at least once on a chat, if it is only for curiosity
purposes. To use a "classic" chat program this should be first downloaded from the Internet,
installed, eventually the system should be rebooted for the installation to be completed and
afterwards it could be used. This in case you have a computer directly connected to Internet.

Anyway, taking into consideration that today, due to security reasons, fewer and fewer users'
terminals are directly connected to Internet, probably as in your case, the Internet connection is
done over a proxy server or through a firewall. In this case, before you could use the chat
program you should provide information like the address of the proxy server, the port number
where the proxy is running and sometimes the proxy type (HTTP proxy, SOCKS proxy). In the
other hand if you are behind a firewall you can have a bad chances that the port where the chat
program is running to be already blocked. In this case you won't be able to use the program until
the firewall settings are changed.

A first step in solving some of the above inconveniences is to use a Java applet that is
implementing a chat room. This approach is eliminating the problem of explicit downloading and
application installation. The application will be still downloaded, but this operation will be
transparent for the user, because the browser will do that in background. However the problems
concerning the proxy and the firewall remain because the applet should communicate with the
chat server at a specified port number. Also the Java applet approach has the disadvantage that
they should be loaded (downloaded) each time when they are used and their dimension reaching
sometimes up to hundreds of kilobytes.

On the other hand, you need to use Java enabled browser and you need to wait until the browser
is starting the Java engine before running any Java applet. Even there are no problems with
proxy server and firewall configurations I know many people who don't like to wait a lot of time
until the applet is effectively started (download time + starting Java support time + initializing
applet time).

So, what you can do to make your chat users life easier? As you have probably guessed the
solution is to use a web-based chat system. A HTML driven chat could successfully pass over all
above problems. There is nothing to be downloaded or installed. There aren't any others
configurations required more then those that usually users need to setup before to browse the

Another big advantage of any web based chat system is that it's less expensive from the point of
view of the resources needed on the client side. All the necessary information is stored on the
server side (web server) and to the client side (web browser) will be sent only pure HTML pages
containing eventually some little pieces of JavaScript code. This means that anybody can connect
to such chat system event if this is happened from home, from his office, from an Internet cafe or
from any other place allowing access to Internet through a web browser.

Part 3.
Main areas of a chat application

To discuss on a chat is similar to discuss with more persons. To discuss with someone, firstly we
need to can talk. In chat terms, this means the possibility to write messages. So, the chat will
have an area where a user's messages are entered.

We cannot be part in a discussion with several people unless we hear what the others are saying
and of course what we are saying. In chat terms, this means the possibility to view both our own
messages and the others messages, in same order they were written. So, the chat should have a
display area of all the messages written on the chat.

Also, you could not talk with persons that you could not see. In other terms, if you are in a dark
room together with more persons it will be difficult to start talking with someone because you
don?t who is there. You should turn the light on. In chat terms we need a list with all connected
users at the talking time.

In conclusion, we could not talking about a chat without one of these 3 basic components:

• Area to enter the user's messages

• Area to display all the messages written on the chat
• Area to display all connected users
Each of those 3 components has its role but the most important is the one in the middle, that
displaying messages, because inside it is in fact the whole chat engine. Will be the best if we can
make this component to display every new entered message as soon as possible after the user
introduced the message. Anyway in a web based chat system is not possible to display a new
message instantly because the chat server who is, in fact a web server could not answer (send a
web page) if there is no previous request for it from a client (web browser). This inconvenience
could be partially avoided by making the client (web browser) to regularly request the messages
page. The less is the period between 2 successive requests, the better is the result, up to the limit
when a new message is displayed immediately. The period of time between 2 successive requests
is named refresh rate.

Part 4.
Database design

For the beginning I will try to keep the database structure as simple as possible in order to better
focus on the chat basic elements, following to increase the number of tables and fields as new
features are introduced. As we could see until now we have two big data collections: the users
and the users messages. Because the relationship between these two collections is "one to many"
type (one user can have many messages, a message is own by only one user) we need 2 different
tables to proper store all the information that we need.

The data regarding the users will be stored in the table called User. For each registered user we
will keep his Nickname and Password. Also, we will use a Boolean (Yes/No) field called
OnLine to know each moment the user's status (connected or not).

The second table will be named Message and will contain all the messages written on the chat.
In what concerning a message we need to know who has written the message (FromUser) and
what is the message (Message). We will store also the time stamp when the message was written
You'll need to notice that in the field FromUser will be stored the user's nickname and not his
User_ID. To uniquely identify users, their nicknames should be unique, this field being also a
candidate to the primary key of the User table. The only reason the user's nickname is used
instead of his User_ID (as it should be normal) is to avoid making a join query on both tables at
the displaying messages time, the data in the Message table being therefore enough to display
everything we are interested in, regarding the messages written on the chat.
I built this application using Access 2000 but there is no reason it should not work with any other
database engine. In order to ASP scripts can connect to the database you need to create a DNS
called cbwh_chat (cbwh_chat.dns).

Part 5.
Registration and login pages
Before connecting first time to the chat, any user should pass through the registration process,
the only information that he should provide being the nickname, under which he would like to
enter the chat and the password. This is necessary in order to avoid the situations when someone
could connect, voluntary or not, with other's nickname, and the others persons on the chat to
think that the one they are talking to is another person that he really is.
You can find the whole code for the registration page in the file called register.asp. As a general
habit, when someone should provide a password, at the registration time, he should enter it twice
to avoid the situation when it was wrongly introduced. Before to submit the form's content we
would use a script on the client side to verify if the same password was inserted in the both
registration form fields. If not we will prompt the user to enter the correct password once again.
The validation code below will check for a non-empty Nickname for a non-empty Password
and for the match of those 2 passwords provided.
<script language="JavaScript">
function isValid(form) {
if (!form.txtNickname.value) {
alert("Empty Nickname not allowed!");
return false;
else if (!form.txtPassword1.value) {
alert("Empty Password not allowed!");
return false;
else if (form.txtPassword1.value != form.txtPassword2.value) {
alert("Password don't match!");
return false;
return true;
The registration page posts the provided information to itself and the script for effective
registering a new user could be found at the beginning of the file. Before introducing the new
user in the users table we should insure that there is no user with the same nickname. If a
nickname was already registered an error message will be displayed and the user should specify
another nickname to complete the registration process. The nickname "System" is reserved to
displaying the system messages so registering by using this nickname is also restricted.
blnError = False

strNickname = Trim(Request("txtNickname"))
strPassword1 = Trim(Request("txtPassword1"))
strPassword2 = Trim(Request("txtPassword2"))

if strNickname <> "" then

strDSN = "FILEDSN=cbwh_chat.dsn"

Set cn = Server.CreateObject("ADODB.Connection")
Set rs = Server.CreateObject("ADODB.Recordset")

cn.Open strDSN

strSQL = "SELECT * FROM User WHERE Nickname = '" & strNickname & "';"
rs.Open strSQL, cn

if (rs.EOF) and (strNickname <> "System") then

strSQL = "INSERT INTO User (Nickname, Password) VALUES ('"_
& strNickname & "', '" & strPassword1 & "');"
cn.Execute strSQL

Response.Redirect "default.asp?txtNickname=" & strNickname

blnError = True
end if

Set rs = Nothing
Set cn = Nothing
end if
The login page

After a successful registration the user will be redirected to the login page. Because the most
common thing that is done when somebody is connecting to a chat is the login process the code
corresponding to the login page is located in the default.asp file. Both the login page and the
registration one post the form data to itself, the ASP script being located at the beginning of each
of those files.
blnError = False

strNickname = Trim(Request("txtNickname"))
strPassword = Trim(Request("txtPassword"))

if strNickname <> "" and strPassword <> "" then

strDSN = "FILEDSN=cbwh_chat.dsn"

Set cn = Server.CreateObject("ADODB.Connection")
Set rs = Server.CreateObject("ADODB.Recordset")

cn.Open strDSN
strSQL = "SELECT * FROM User WHERE Nickname = '"_
& strNickname & "' AND Password ='" & strPassword & "';"
rs.Open strSQL, cn

if not rs.EOF then

strSQL = "UPDATE User SET OnLine = True WHERE Nickname ='" &
strNickname & "';"
cn.Execute strSQL

strSQL = "INSERT INTO Message (FromUser, Message, Moment) VALUES ("_

& "'System', '<i>" & strNickname & "</i> just enter the chat', '" &
Now & "');"
cn.Execute strSQL

Session("s_Nickname") = strNickname

Response.Redirect "main.asp"
blnError = True
end if

Set rs = Nothing
Set cn = Nothing
end if

<title>ASP Chat - Login Page</title>
<link rel="stylesheet" type="text/css" href="chat.css">

<body bgcolor="#FFFFFF">
<b><font color="#FF0000"><%if blnError then%>Invalid Nickname or
<form method="post" action="default.asp">
<table border="0" width="200" cellspacing="1" cellpadding="4">
<td width="20%" align="right" bgcolor="#F2B425"><b>Nickname:</b></td>
<td width="80%" bgcolor="#F7D53E"><input type="text" name="txtNickname"
value="<%=strNickname%>" size="20"></td>
<td width="20%" align="right" bgcolor="#F2B425"><b>Password:</b></td>
<td width="80%" bgcolor="#F7D53E"><input type="password"
<td width="100%" colspan="2" align="center" bgcolor="#F2B425"><input
type="submit" value="Login" name="btnLogin"></td>
New user? <a href="register.asp">Sign up now</a>!

To get access to the chat a user must enter in the login form the same information (nickname and
password) that he provided at the registration time. If the information could not be found in the
users table an error message will be displayed and the user have the possibility to try to connect
once again.
Otherwise, if the combination nickname-password can be found in the users table, then the
nickname will be put in the s_Nickname session variable to be used in all the chat pages during
all the time the user will be connected. Also, the OnLine field should be turn to Yes and a
message on the system behalf will be inserted in the messages table. This message is announcing
that the user is just entering the chat. The last thing that you must do is to redirect the user to the
main page of the chat (main.asp).

Part 6.
The main page of the asp chat
Earlier, I underlined that we could not talk about a chat without taking in consideration one of
the 3 main elements. That mean, the main window of the chat should display 3 areas each of
them associated with one of these components. To carry out this thing you?ll need use the HTML
frames concept, the main page being split into 3 frames, one for each area. The main.asp file
contains only the definition of the 3 frames.
Frame for typing a message (frm_input.asp)
Frame for displaying messages (frm_messages.asp)
Frame for displaying the users list (frm_users.asp)
<!-- #include file="inc_session.asp" -->

<title>ASP Chat - Main Room</title>

<frameset cols="*,120">
<frameset rows="*,60">
<frame name="frm_messages" target="_self" src="frm_messages.asp" noresize>
<frame name="frm_input" target="_self" src="frm_input.asp" noresize
<frame name="frm_users" target="_self" src="frm_users.asp" noresize>

<p>This page uses frames, but your browser doesn't support them.</p>

Of course, like in any other application that suppose a login process, is a good practice to add at
the beginning of any asp file a piece of code that check if the user is logged on or not and if is
not redirect the user to the login page. We can test if a user is logged on by checking the
s_Nickname session variable that is filled with the user nickname at the login time. To avoid
enter the same code in many pages I will put the checking code in a separate file called
inc_session.asp that can be included at the beginning of every page that need to be password
if Session("s_Nickname") = "" then
Response.Redirect "default.asp"
end if

Part 7.
Entering messages
The code corresponding to the input of the user messages is located the frm_input.asp file. This
page sends also the content of the form (the message written by the user) to itself, the processing
script, being as you have already been used to, at the beginning of the file.
<!-- #include file="inc_session.asp" -->
strMessage = Server.HTMLEncode(Trim(Replace(Request("txtMessage"), "'",

if strMessage <> "" then

strDSN = "FILEDSN=cbwh_chat.dsn"

Set cn = Server.CreateObject("ADODB.Connection")
cn.Open strDSN

strSQL = "INSERT INTO Message (FromUser, Message, Moment) VALUES ('"_

& Session("s_Nickname") & "', '" & strMessage & "', '" & Now & "');"
cn.Execute strSQL

Set cn = Nothing
end if

<title>ASP Chat - Input Messages</title>
<script language="JavaScript">
window.parent.frm_messages.location.href += '';

<body bgcolor="#FFFFFF">
<table border="0" width="100%">
<td width="100%">
<form method="POST" action="frm_input.asp">
<table border="0" width="100%" cellspacing="0" cellpadding="0">
<td width="5%"><font face="Arial" size="2">Message:&nbsp;</font></td>
<td width="15%"><input type="text" name="txtMessage"
<td width="80%"><input type="submit" value="Send" name="btnSend"></td>

Before inserting a user message in the messages table we need to perform some validations and
modifications on it to avoid any problems. Because is well known that an INSERT statement
will raise an error if a text field contains an apostrophe (') character and people use to enter
messages like "That's really cool!" we will need to handle this kind of problem. The only thing
that we need to do to solve the problem is to replace each apostrophe character with other 2
apostrophe characters.
Replace(Request("txtMessage"), "'", "''")
Also, it might be possible that a user to introduce inside a message characters like "<" or ">" or
other characters having a certain signification in HTML. You should not forget that all the
messages introduced by the users will be displayed in a HTML page, and in case the messages
have fragments of HTML tags, it is possible that the page to be displayed in an improper way. To
prevent that kind of problem we can call the Server.HTMLEncode function for each message
before adding them in the messages table. So, if there is any HTML tag inside a message the
HTML code will be displayed and not the result of interpreting the HTML tag by the browser.
Because when we talk we are used to hear in the same time what we are saying, it is preferable
that this thing happens also in the chat case. This means to redisplay the messages list as soon as
possible after a user enter a new message. That could be implemented through a little piece of
JavaScript code like window.parent.frm_messages.location.href += ''.

Part 8.
Displaying messages
Displaying messages is the main component of any chat. It is necessary that all written messages
to be displayed as soon as they are introduced. For that we need to find a way to automatically
redisplaying messages without any user involving like press a button to get last messages. So, we
should solve the problem of repetitively updating the messages list.
It's well known that a web server cannot send a page if there is no web browser page request. It
results that the solution should be searched on the web browser client side and not on the web
server side. This means that will be the client job to request from time to time the last messages
list page. The simple way to solving that is to use a HTML meta tag, usually used for client side
page redirection. You can also imagine a little piece of JavaScript code based on a timer that
reloads the page every time the timer expired. Anyway I will focus here only in the HTML meta
tag solution.
<meta http-equiv="refresh" content="10; url=otherpage.htm">
The tag above placed in the <head> section of a HTML page has as effect the automatically
request of the otherpage.htm after 10 seconds from the moment that the page including the tag
was loaded. In case the url attribute is not specified, the page to be loaded after the end of the 10
seconds will be the current page itself. This means that the code bellow has as effect to reload the
page that contains the code every 10 second.
<meta http-equiv="refresh" content="10">
For updating the messages list using a 6 or 8 second refresh rate value can be a good option in
many cases. This make possible that all connected users to see new messages with no more than
6 or 8 seconds delay.
Now, after we found the way to refresh the messages list page, we need also to create the content
of this page. As we do not want to display all the messages available in the messages table, but
the ones quite recent, we have to decide how to filter messages to display only those that we
need. It?s a good practice to choose a criterion that combines the period of time after a message
become an old message and the maximum number of messages displayed at a certain moment.
This means that we will display only messages written in the last T minutes, but not more than M
messages. Personally, I consider that a combination like displaying the last 20 messages written
in the last 30 minutes could be a right choice in many cases.
<!-- #include file="inc_session.asp" -->

<meta http-equiv="Refresh" content="8">
<title>ASP Chat - Messages</title>

<body bgcolor="#FFFFFF">
<font face="Arial" size="2" color="#000000">
strDSN = "FILEDSN=cbwh_chat.dsn"

Set cn = Server.CreateObject("ADODB.Connection")
Set rs = Server.CreateObject("ADODB.Recordset")

cn.Open strDSN

strSQL = "SELECT * FROM Message WHERE " _

& "DateDiff('N', Moment, Now) < 30 ORDER BY Moment DESC;"
rs.Open strSQL, cn

n = 0
do while (not rs.EOF) and (n < 20)
strUser = rs("FromUser")
strMessage = ""

if strUser <> "System" then

strMessage = "<i>" & strUser & "</i>: "
end if

strMessage = strMessage & rs("Message") & " <small>(" _

& FormatDateTime(rs("Moment"), 3) & ")</small>"

if strUser = "System" then

strMessage = "<font color=""777777""><b><i>" _
& strMessage & "</i></b></font>"
end if

response.write strMessage & "<br>" &vbCRLF

n = n + 1


Set rs = Nothing
Set cn = Nothing

If you ever entered a web based chat system you probably already noticed that usually the
messages are displayed in reverse order, the most recent one being the first from above, and the
oldest message being the last from below. This solution is used in order to avoid the necessity of
scrolling the page manually by the user or automatically (using a piece of JavaScript code) to see
the last messages, in the case there is no available space to display all the messages in the visible
area of the frame. To implementing this we need to add an ORDER BY Moment DESC clause
at the end of SELECT statement.
Taking into consideration that in the message table we have two different types of messages,
some coming from the system (announcing the entrance of the users on the chat or their exit) and
others coming from the users, it result that in the messages list we need to have the same two
types of messages. In order to easy make a visual difference between them, the system messages
will be displayed with a distinct color. At the end of both types of messages will be attached a
time stamp like hh:mm:ss that is the moment of time in which the message was written. For a lot
of date and time formatting check the FormatDateTime VBScript function. To know each
message from which user is coming the user nickname will be also added at the beginning of any
user message.
Part 9.
Displaying the connected users list
To discuss with people on the chat it's necessary to knowing them (their nicknames). So, the list
of the connected users should be displayed. This could be solved by displaying nicknames of all
registered user for which the OnLine field value is True (SELECT * FROM User WHERE
Because the events of enter/exit the chat are producing themselves with a lower frequency than
those of inserting new messages, it results that for displaying the list of connected users we could
use a bigger period of time between two successive display operations. I think it is a good idea to
use a double value of the refresh rate than that used to display messages. Therefore, if the
messages will be redisplayed every 6 or 8 seconds, could be fine to update the users list every 12
or 16 seconds.
<!-- #include file="inc_session.asp" -->

<meta http-equiv="Refresh" content="12">
<title>ASP Chat - Users List</title>

<body bgcolor="#FFFFFF">
<font face="Arial" size="2" color="#000000">
strDSN = "FILEDSN=cbwh_chat.dsn"

Set cn = Server.CreateObject("ADODB.Connection")
Set rs = Server.CreateObject("ADODB.Recordset")

cn.Open strDSN

strSQL = "SELECT * FROM User WHERE OnLine"

rs.Open strSQL, cn

do while not rs.EOF

strNickname = rs("Nickname")
if Session("s_Nickname") = strNickname then
strNickname = "<b>" & strNickname & "</b>"
end if

response.write "" & strNickname & "<br>" & vbCRLF



Set rs = Nothing
Set cn = Nothing


Part 10.
Logout the asp chat
In order to display a system message like "Mary just left the chat" (supposing that the user Mary
has left the chat) it is necessary to catch that moment in which the user has left the chat. For
handling that we could make a LogOut button. The best place to put this button is the bottom
frame (the input messages frame). So you will need to add the following piece of HTML code to
the frm_input.asp page and split the main column of the table in two different columns. The
code below will be the new right column.
<td width="50%" align="right">
<form method="POST" action="logout.asp" target="_top">
<input type="submit" value="Logout" name="btnLogout">
Anyway the user could not be obliged to push this button before he leaves the chat. For example,
the user could close the browser window or enter another URL in the address bar and browse that
site. In both cases the code beyond the LogOut button will be never run, because the button will
be not pressed and the user still looks like is connected but in fact he is not.
To avoid these types of problems we will use the Session_OnEnd event handler, which reside in
the global.asa file. The time after which a session expires and the Session_OnEnd event is fired
is given by the value specified by the Session.TimeOut. By default this value is 20, meaning that
the Session_OnEnd event will be fired 20 minutes after the user has accessed the last page in the
current site. In the case of a chat application a period of 2 minutes is enough to consider that a
user is not longer connected (Session.TimeOut = 2). To run this piece of code for each user, we
could put it in the Session_OnStart event body, found also in global.asa file.
As soon as a user leaves the chat we have to do 2 operations. The first one is to display a
message on behalf of the system, announcing the user has left the chat and the second one is
about to change the user status to OffLine (set the Boolean OnLine field to "No" in users table).
<script language="VBScript" runat="Server">
sub Session_OnStart
Session.Timeout = 2
end sub

sub Session_OnEnd
if Session("s_Nickname") <> "" then
strDSN = "FILEDSN=cbwh_chat.dsn"

Set cn = Server.CreateObject("ADODB.Connection")
cn.Open strDSN

strSQL = "UPDATE User SET OnLine = False WHERE Nickname ='" _

& Session("s_Nickname") & "';"
cn.Execute strSQL

strSQL = "INSERT INTO Message (FromUser, Message, Moment) VALUES (" _

& "'System', '<i>" & Session("s_Nickname") _
& "</i> just left the chat', '" & Now & "');"
cn.Execute strSQL

Set cn = Nothing
end if
end sub
For that kind of users who wish explicitly leave the chat, by using the LogOut button, we could
call the Session.Abandon method. This will have as result the end of the current session and the
fire of Session_OnEnd event. By pushing the LogOut button a submit query will be sent to the
logout.asp page, its code being shown below. Finally, the user could be redirected to the login
page again or to any other page.
<!-- #include file="inc_session.asp" -->
Response.Redirect "default.asp"
Even if the user will push or not the LogOut button before leaving the chat, the same piece of
code will be executed: Session_OnEnd event handler. The only difference between those two
situations is that in the first case (pushing the LogOut button) the Session_OnEnd event will be
called instantly, as in the second case (close the browser window, enter another URL, etc) the call
will be after the expiration of the time out period (2 minutes in our case).

Part 11.
Several suggestions on how to use this asp chat
This chat system could be used as well both at the Internet level and the intranet level. In the case
that you have a site and you want more traffic on it, set upping one or more chat rooms could be
a good idea to successfully increase the number of visitors. Also, you could be almost sure that
they will come back in the next days to meet again the new friends made on your chat.
The chat could be also used successfully at the corporation level or at the department of a
company level to communicate rapidly and efficiently on different subjects. There are a lot of
advantages among the most obvious I can mention the elimination of the necessity to gather
together, in the same room, all the participants to the discussion and the possibility of continuing
the work or other activities during the hole debate period. The benefits could be even bigger if
there is a company with offices located in different cities or countries and with the frequent on-
line communication needs between the employees from different places.

Part 12.
Full source code
Such a chat system is a solution at hand to everyone and could be implemented with minimum
costs and has the chance to be in many situations of a real use. The main advantage of this way
of implementing a chat is that it's based only on HTML and JavaScript and it requires only a web
browser for anybody who wishes to connect to.
On the negative aspects side we can put the use of an unsuitable refresh rate in comparison with
connection's quality between the web browser and the chat server (web server). Also, in case of a
bad connection, it's possible that a user send by mistake the same message many times (by
pressing the Send button twice or more). Because sometimes the Session_OnEnd event handler
is never fired it's also possible to appear the situation called "users hang up".
I hope that I will get the chance to write a second part of this article and than I will show you
how the above problems could be solved and how you can improve the chat performances by
properly configuration of some running parameters. I will also show you how you can add a lot
of new features like more then one chat room per chat, private messages, users ignoring, black
words list and how you can change some emoticons with small funny images.

ASP Chat Code