KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > echo2example > chatclient > ChatSession


1 /*
2  * This file is part of the Echo Web Application Framework (hereinafter "Echo").
3  * Copyright (C) 2002-2005 NextApp, Inc.
4  *
5  * Version: MPL 1.1/GPL 2.0/LGPL 2.1
6  *
7  * The contents of this file are subject to the Mozilla Public License Version
8  * 1.1 (the "License"); you may not use this file except in compliance with
9  * the License. You may obtain a copy of the License at
10  * http://www.mozilla.org/MPL/
11  *
12  * Software distributed under the License is distributed on an "AS IS" basis,
13  * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
14  * for the specific language governing rights and limitations under the
15  * License.
16  *
17  * Alternatively, the contents of this file may be used under the terms of
18  * either the GNU General Public License Version 2 or later (the "GPL"), or
19  * the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
20  * in which case the provisions of the GPL or the LGPL are applicable instead
21  * of those above. If you wish to allow use of your version of this file only
22  * under the terms of either the GPL or the LGPL, and not to allow others to
23  * use your version of this file under the terms of the MPL, indicate your
24  * decision by deleting the provisions above and replace them with the notice
25  * and other provisions required by the GPL or the LGPL. If you do not delete
26  * the provisions above, a recipient may use your version of this file under
27  * the terms of any one of the MPL, the GPL or the LGPL.
28  */

29
30 package echo2example.chatclient;
31
32 import java.io.IOException JavaDoc;
33 import java.util.ArrayList JavaDoc;
34 import java.util.Date JavaDoc;
35 import java.util.List JavaDoc;
36
37 import javax.xml.parsers.DocumentBuilder JavaDoc;
38 import javax.xml.parsers.DocumentBuilderFactory JavaDoc;
39 import javax.xml.parsers.ParserConfigurationException JavaDoc;
40
41 import nextapp.echo2.webcontainer.ContainerContext;
42 import nextapp.echo2.webrender.ClientProperties;
43 import nextapp.echo2.webrender.Connection;
44 import nextapp.echo2.webrender.WebRenderServlet;
45
46 import org.w3c.dom.Document JavaDoc;
47 import org.w3c.dom.Element JavaDoc;
48 import org.w3c.dom.NodeList JavaDoc;
49 import org.w3c.dom.Text JavaDoc;
50
51 /**
52  * Representation of a chat-room session for a single user.
53  * This object handles life-cycle of a user in the chat room and provides
54  * capability to post messages and retrieve messages from the chat room.
55  */

56 public class ChatSession {
57     
58     /**
59      * A representation of a single message posted in the chat session.
60      */

61     public static class Message {
62         
63         private String JavaDoc content;
64         private Date JavaDoc date;
65         private String JavaDoc userName;
66         
67         /**
68          * Creates a new <code>Message</code>.
69          *
70          * @param userName the name of the user posting the message
71          * (null for system announcements)
72          * @param date the time the message was posted
73          * @param content the content of the message
74          */

75         private Message(String JavaDoc userName, Date JavaDoc date, String JavaDoc content) {
76             super();
77             this.userName = userName;
78             this.date = date;
79             this.content = content;
80         }
81         
82         /**
83          * Returns the content of the message.
84          *
85          * @return the content
86          */

87         public String JavaDoc getContent() {
88             return content;
89         }
90         
91         /**
92          * Returns the time the message was posted
93          *
94          * @return the post time
95          */

96         public Date JavaDoc getDate() {
97             return date;
98         }
99
100         /**
101          * Returns the name of the user who posted the message
102          *
103          * @return the name of the user, or null in the case of a system
104          * announcement
105          */

106         public String JavaDoc getUserName() {
107             return userName;
108         }
109     }
110     
111     /**
112      * Factory method to create a new <code>ChatSession</code> for a user.
113      *
114      * @param userName the desired user name
115      * @return the <code>ChatSession</code> if one could be created or null
116      * otherwise (e.g., in the case the user name was taken)
117      */

118     public static ChatSession forUserName(String JavaDoc userName)
119     throws IOException JavaDoc {
120         ChatSession chatSession = new ChatSession(userName);
121         return chatSession.authToken == null ? null : chatSession;
122     }
123
124     /**
125      * The id of the last retrieved chat message.
126      */

127     private String JavaDoc lastRetrievedId;
128     
129     /**
130      * The authentication token associated with the user name. This token is
131      * used to authenticate in order to post messages with the user name and
132      * release the user name.
133      */

134     private String JavaDoc authToken;
135     
136     /**
137      * The name of the user.
138      */

139     private String JavaDoc userName;
140     
141     /**
142      * List of new messages recently retrieved from the chat server which have
143      * not yet been retrieved by the application.
144      */

145     private List JavaDoc newMessages = new ArrayList JavaDoc();
146     
147     /**
148      * The URI of the chat server's web service.
149      */

150     private String JavaDoc chatServerUri;
151     
152     /**
153      * Creates a new <code>ChatSession</code>.
154      * Attempts to connect to chat server and obtain lock / authentication token
155      * for user name.
156      *
157      * @param userName the desired user name for the session
158      */

159     private ChatSession(String JavaDoc userName)
160     throws IOException JavaDoc {
161         super();
162         this.userName = userName;
163         loadServerUri();
164         
165         Document JavaDoc requestDocument = createRequestDocument();
166         
167         Element JavaDoc userAddElement = requestDocument.createElement("user-add");
168         userAddElement.setAttribute("name", userName);
169         requestDocument.getDocumentElement().appendChild(userAddElement);
170         
171         Document JavaDoc responseDocument = XmlHttpConnection.send(this.chatServerUri, requestDocument);
172         NodeList JavaDoc userAuthNodes = responseDocument.getElementsByTagName("user-auth");
173         if (userAuthNodes.getLength() != 1) {
174             throw new IOException JavaDoc("Unexpected response.");
175         }
176         Element JavaDoc userAuthElement = (Element JavaDoc) userAuthNodes.item(0);
177         if ("true".equals(userAuthElement.getAttribute("failed"))) {
178         } else {
179             authToken = userAuthElement.getAttribute("auth-token");
180         }
181     }
182
183     /**
184      * Determines the URI of the chat server based on either
185      */

186     private void loadServerUri() {
187         Connection conn = WebRenderServlet.getActiveConnection();
188         String JavaDoc chatServerUri = conn.getServlet().getInitParameter("ChatServerURI");
189         if (chatServerUri != null && chatServerUri.trim().length() > 0) {
190             this.chatServerUri = chatServerUri;
191         } else {
192             this.chatServerUri = (conn.getRequest().isSecure() ? "https" : "http")
193                     + "://" + conn.getRequest().getServerName() + ":" + conn.getRequest().getServerPort() + "/ChatServer/app";
194         }
195     }
196     
197     /**
198      * Creates an XML DOM for a request to the Chat Server's Web Service.
199      * The returned DOM will contain a 'chat-server-request' document element.
200      *
201      * @return the created DOM
202      */

203     private Document JavaDoc createRequestDocument()
204     throws IOException JavaDoc {
205         try {
206             DocumentBuilderFactory JavaDoc factory = DocumentBuilderFactory.newInstance();
207             factory.setNamespaceAware(true);
208             DocumentBuilder JavaDoc builder = factory.newDocumentBuilder();
209             Document JavaDoc document = builder.newDocument();
210             Element JavaDoc rootElement = document.createElement("chat-server-request");
211             
212             ChatApp chatApp = ChatApp.getApp();
213             if (chatApp != null) {
214                 ContainerContext containerContext = (ContainerContext) chatApp.getContextProperty(
215                         ContainerContext.CONTEXT_PROPERTY_NAME);
216                 String JavaDoc remoteHost = containerContext.getClientProperties().getString(ClientProperties.REMOTE_HOST);
217                 rootElement.setAttribute("remote-host", remoteHost);
218             }
219             
220             if (lastRetrievedId != null) {
221                 rootElement.setAttribute("last-retrieved-id", lastRetrievedId);
222             }
223             document.appendChild(rootElement);
224             return document;
225         } catch (ParserConfigurationException JavaDoc ex) {
226             throw new IOException JavaDoc("Cannot create document: " + ex);
227         }
228     }
229     
230     /**
231      * Disposes of the <code>ChatSession</code>.
232      * This operation will make a request to the chat server to release the
233      * user name being used by the session.
234      */

235     public void dispose()
236     throws IOException JavaDoc {
237         Document JavaDoc requestDocument = createRequestDocument();
238         Element JavaDoc userRemoveElement = requestDocument.createElement("user-remove");
239         userRemoveElement.setAttribute("name", userName);
240         userRemoveElement.setAttribute("auth-token", authToken);
241         requestDocument.getDocumentElement().appendChild(userRemoveElement);
242         XmlHttpConnection.send(chatServerUri, requestDocument);
243     }
244     
245     /**
246      * Retrieves new messages that have been posted to the server but which
247      * were not previously retrieved.
248      *
249      * @return the new <code>Message</code>s
250      */

251     public Message[] getNewMessages() {
252         Message[] messages = (Message[]) newMessages.toArray(new Message[newMessages.size()]);
253         newMessages.clear();
254         return messages;
255     }
256     
257     /**
258      * Determines if any new messages have been posted to the chat server.
259      *
260      * @return true if any messages have been posted.
261      */

262     public boolean hasNewMessages() {
263         return newMessages.size() != 0;
264     }
265     
266     /**
267      * Returns the name of the user.
268      *
269      * @return the name of the user
270      */

271     public String JavaDoc getUserName() {
272         return userName;
273     }
274     
275     /**
276      * Contacts the chat server's web service and loads new messages.
277      *
278      * @throws IOException
279      */

280     public void pollServer()
281     throws IOException JavaDoc {
282         Document JavaDoc requestDocument = createRequestDocument();
283         Document JavaDoc responseDocument = XmlHttpConnection.send(chatServerUri, requestDocument);
284         updateLocalMessages(responseDocument);
285     }
286     
287     /**
288      * Posts a message to the chat server.
289      * Local messages will also be updated.
290      *
291      * @param content the content of the message
292      */

293     public void postMessage(String JavaDoc content)
294     throws IOException JavaDoc {
295         Document JavaDoc requestDocument = createRequestDocument();
296         
297         Element JavaDoc postMessageElement = requestDocument.createElement("post-message");
298         postMessageElement.setAttribute("user-name", userName);
299         postMessageElement.setAttribute("auth-token", authToken);
300         postMessageElement.appendChild(requestDocument.createTextNode(content));
301         requestDocument.getDocumentElement().appendChild(postMessageElement);
302         
303         Document JavaDoc responseDocument = XmlHttpConnection.send(chatServerUri, requestDocument);
304         updateLocalMessages(responseDocument);
305     }
306     
307     /**
308      * Retrieves messages from the chat's server's web service's response
309      * message and stores them in the chat session.
310      *
311      * @param responseDocument the response DOM from the web service
312      */

313     private void updateLocalMessages(Document JavaDoc responseDocument) {
314         NodeList JavaDoc newMessageElements = responseDocument.getDocumentElement().getElementsByTagName("message");
315         int length = newMessageElements.getLength();
316         for (int i = 0; i < length; ++i) {
317             Element JavaDoc messageElement = (Element JavaDoc) newMessageElements.item(i);
318             lastRetrievedId = messageElement.getAttribute("id");
319             String JavaDoc userName = messageElement.hasAttribute("user-name") ? messageElement.getAttribute("user-name") : null;
320             NodeList JavaDoc childNodes = messageElement.getChildNodes();
321             String JavaDoc content = null;
322             for (int j = 0; j < childNodes.getLength(); ++j) {
323                 if (childNodes.item(j) instanceof Text JavaDoc) {
324                     content = childNodes.item(j).getNodeValue();
325                     break;
326                 }
327             }
328             long timeMs = Long.parseLong(messageElement.getAttribute("time"));
329             Message message = new Message(userName, new Date JavaDoc(timeMs), content);
330             newMessages.add(message);
331         }
332     }
333 }
334
Popular Tags