KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > freecs > core > MessageParser


1 /**
2  * Copyright (C) 2003 Manfred Andres
3  *
4  * This program is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU General Public License
6  * as published by the Free Software Foundation; either version 2
7  * of the License, or (at your option) any later version.
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12  * GNU General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program; if not, write to the Free Software
16  * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
17  */

18 /**
19  * the command set is inside here
20  */

21 package freecs.core;
22
23 import freecs.*;
24 import freecs.layout.*;
25 import freecs.commands.CommandSet;
26 import freecs.content.*;
27 import freecs.interfaces.*;
28
29 import java.nio.charset.Charset JavaDoc;
30 import java.nio.charset.UnmappableCharacterException JavaDoc;
31 import java.nio.ByteBuffer JavaDoc;
32 import java.nio.CharBuffer JavaDoc;
33 import java.util.HashMap JavaDoc;
34
35 /**
36  * constructed with a sender (possible null) and a raw message, this
37  * message-container is responsible for parsing the message. if the message
38  * was parsed successfully, the apropriate flags get set and the parsing
39  * thread decides what to do with this message.
40  */

41 public class MessageParser implements IContainer {
42     private MessageState msgState;
43     private ByteBuffer JavaDoc bBuff = null;
44     private HashMap JavaDoc renderCache;
45     private boolean isHTTP11 = true;
46     private CommandSet cs;
47     private RequestReader req;
48
49     public MessageParser () {
50         renderCache = new HashMap JavaDoc ();
51         msgState = new MessageState(this);
52         cs = CommandSet.getCommandSet ();
53         clear ();
54         if (Server.TRACE_CREATE_AND_FINALIZE)
55             Server.log (this, "++++++++++++++++++++++++++++++++++++++++CREATE", Server.MSG_STATE, Server.LVL_VERY_VERBOSE);
56     }
57    public MessageParser (RequestReader r) {
58       renderCache = new HashMap JavaDoc ();
59       msgState = new MessageState(this);
60       cs = CommandSet.getCommandSet ();
61       clear ();
62       req=r;
63       if (Server.TRACE_CREATE_AND_FINALIZE)
64           Server.log (this, "++++++++++++++++++++++++++++++++++++++++CREATE", Server.MSG_STATE, Server.LVL_VERY_VERBOSE);
65    }
66
67     /**
68      * clear the state of this messagparser
69      */

70     public void clear () {
71         msgState.clear();
72         renderCache.clear ();
73         isHTTP11 = true;
74     }
75
76     /**
77      * set the http/1.1-capability for this message
78      * @param b if true HTTP1.1 is enabled, if false it will be disabled
79      */

80    public void setHTTP11 (boolean b) {
81       isHTTP11 = b;
82    }
83
84     public void setConnectionBuffer (ConnectionBuffer cb) {
85         msgState.cb = cb;
86     }
87
88    /**
89     * set the target to the given String
90     * @param target the target
91     */

92    public void setParam (String JavaDoc target) {
93       msgState.param = target;
94    }
95
96    
97    public void setTargetGroup (Group target) {
98        msgState.targetGroup = target;
99    }
100
101    /**
102     * set the source of this message to the given String
103     * @param source the source
104    public void setSource (String source) {
105       msgState.source = source;
106    }
107     */

108
109    /**
110     * set the sender of this message
111     * @param s the user which sent this message
112     */

113    public void setSender (User s) {
114       msgState.sender = s;
115    }
116    
117    public void setUsercontext (User s) {
118       msgState.usercontext = s;
119    }
120
121     /**
122      * set the message
123      * @param msg the raw message
124      */

125    public void setRawMessage (String JavaDoc msg) {
126       msgState.msg = msg.trim ();
127    }
128
129    public MessageState getMessageState() {
130        return msgState;
131    }
132     /**
133      * return the sender of this message
134      * @return the sender of this message
135      */

136    public User getSender () {
137       return msgState.sender;
138    }
139
140     /**
141      * interface contentcontainer deffines the following
142      * @return the ByteBuffer containing the bytes to send
143      */

144    public ByteBuffer JavaDoc getByteBuffer () {
145       if (bBuff != null)
146           bBuff.rewind ();
147       return (bBuff);
148    }
149
150    /**
151     * returns always false for this, because the message-window doesn't get closed
152     * except the user loggs out
153     */

154    public boolean closeSocket () {
155       return false;
156    }
157
158     /**
159      * checks if there is actual some content to send
160      * @return true if there is content to send, false if not
161      */

162    public boolean hasContent () {
163       return (bBuff != null && bBuff.limit () > 0);
164    }
165
166     /**
167      * set the messagetemplate which should be used
168      * @param tplName the name of the message-template
169      */

170    public void setMessageTemplate (String JavaDoc tplName) {
171       msgState.msgTemplate = tplName;
172    }
173
174     /**
175      * get the personalized message for this user
176      * @param u the user to personalize the message for
177      * @return the IContainer containing the personalized message
178      */

179    public boolean addPersonalizedMessage (User u, ConnectionBuffer cb) {
180       StringBuffer JavaDoc result = new StringBuffer JavaDoc ();
181       TemplateSet ts = u.getTemplateSet ();
182       StringBuffer JavaDoc tsb = new StringBuffer JavaDoc (ts.getName ()).append ("/").append (msgState.msgTemplate).append ("/").append (isHTTP11);
183       String JavaDoc rcKey = tsb.toString ();
184       // check if the wanted message is contained within the render-cache
185
if (!Server.srv.USE_MESSAGE_RENDER_CACHE
186               || !msgState.useRenderCache
187               || !renderCache.containsKey (rcKey)) {
188          String JavaDoc msgTpl = ts.getMessageTemplate (msgState.msgTemplate);
189          if (msgTpl == null || msgTpl.length () < 1) {
190             tsb = new StringBuffer JavaDoc ("Message-Template ").append (msgState.msgTemplate).append (" was not found");
191             Server.log ("MessageParser", tsb.toString (), Server.MSG_STATE, Server.LVL_VERBOSE);
192             if (Server.srv.DEBUG_TEMPLATESET) msgTpl = tsb.toString ();
193             else return false;
194          }
195          String JavaDoc showTime = ts.getMessageTemplate ("status.showtime");
196          if (showTime != null && (showTime.equals ("true") || showTime.equals("1"))) {
197             String JavaDoc tf = ts.getMessageTemplate ("status.showtime.timeformat");
198             if (tf != null) result.append (MessageRenderer.renderTemplate (msgState, tf, false));
199             else {
200                result.append ("[");
201                result.append (Server.srv.getFormatedTime ("HH:mm"));
202                result.append ("] ");
203             }
204          }
205          result.append (MessageRenderer.renderTemplate (msgState, msgTpl));
206          renderCache.put (rcKey, result);
207       } else {
208          result.append (renderCache.get(rcKey));
209       }
210       if (result.length() < 1) return false;
211       CharBuffer JavaDoc cbuf = CharBuffer.wrap (result);
212       try {
213         if (cbuf.length() < 2) {
214             if (msgState.msgTemplate.equals ("message.q")
215                 || msgState.msgTemplate.equals ("message.server.shutdown")
216                 || msgState.msgTemplate.equals ("message.kh.personal")) {
217                     msgState.sender.removeNow();
218                     CentralSelector.dropKey(u.getKey());
219             }
220             return false;
221         }
222         if ((msgState.msgTemplate.equals ("message.q")
223                 || msgState.msgTemplate.equals ("message.server.shutdown")
224                 || msgState.msgTemplate.equals ("message.kh.personal"))) {
225             Object JavaDoc[] o = new Object JavaDoc[2];
226             cb.addToWrite(Charset.forName (Server.srv.DEFAULT_CHARSET).newEncoder ().encode (cbuf));
227             cb.addToWrite(Responder.CLOSE_CONNECTION);
228             return true;
229         }
230         cb.addToWrite(Charset.forName (Server.srv.DEFAULT_CHARSET).newEncoder ().encode (cbuf));
231         return true;
232       } catch (UnmappableCharacterException JavaDoc uce) {
233          Server.debug (this, "getPersonalizedMessage: ", uce, Server.MSG_ERROR, Server.LVL_MINOR);
234          byte[] b = result.toString ().getBytes ();
235          ByteBuffer JavaDoc bb = ByteBuffer.wrap (b);
236          if ((msgState.msgTemplate.equals ("message.q")
237                  || msgState.msgTemplate.equals ("message.server.shutdown")
238                  || msgState.msgTemplate.equals ("message.kh.personal"))) {
239              cb.addToWrite(bb);
240              cb.addToWrite(Responder.CLOSE_CONNECTION);
241              return true;
242          }
243          cb.addToWrite(bb);
244          return true;
245       } catch (Exception JavaDoc e) {
246          Server.debug (this, "getPersonalizedMessage: ", e, Server.MSG_ERROR, Server.LVL_MAJOR);
247          return false;
248       }
249    }
250
251    public boolean prepareForSending () {
252       if (this.bBuff != null) return true;
253       return false;
254    }
255
256 /* public void finalize () {
257       Server.log ("MessageParser FINALIZED*******************************", Server.MSG_STATE, Server.LVL_VERY_VERBOSE);
258    } */

259
260    /**
261     *--------------------- MESSAGE-PARSING -------------------
262     * this is where the parsing of the message happens.
263     */

264     public void parseAndSendMessage () {
265         if (req!=null) req.currPosition = RequestReader.PARSE_MSG;
266         if (msgState.msg == null
267             || msgState.msg.length () < 1
268             || msgState.sender == null
269             || !msgState.cb.isValid()) {
270             clear ();
271             return;
272         }
273         // check if user was in away-state
274
if (msgState.sender.isAway ()) {
275             msgState.msgTemplate="message.away.off";
276             msgState.message=msgState.sender.getAwayMessage();
277             Group sg = msgState.sender.getGroup ();
278             if (sg != null)
279                 sg.sendMessage (this);
280             else
281                 msgState.sender.sendMessage (this);
282             msgState.sender.setAway (false);
283         }
284
285         if (!msgState.msg.startsWith ("/") || msgState.sender == null) {
286             if (msgState.sender != null
287                     && msgState.sender.isPunished()) {
288                 msgState.msgTemplate = "error.user.punished";
289                 msgState.sender.sendMessage(msgState.mp);
290                 clear ();
291                 return;
292             }
293             Group sg = msgState.sender.getGroup ();
294             int timelocksec = sg.getTimelockSec();
295             if (msgState.sender.getGroup().hasState(IGroupState.MODERATED)
296                     && !msgState.sender.hasRight(IUserStates.IS_MODERATOR)
297                     && !msgState.sender.hasRight(IUserStates.IS_GUEST)) {
298                 // check the timelock if group is moderated and sender isn't guest nore moderator
299
if (msgState.sender.lastSentMessage > System.currentTimeMillis() - 1 * timelocksec * 1000) {
300                     msgState.msgTemplate = "error.moderated.timelock";
301                     msgState.param = "" + ((msgState.sender.lastSentMessage - System.currentTimeMillis() + (1 * timelocksec * 1000)) / 1000);
302                     msgState.message = msgState.msg;
303                     msgState.sender.sendMessage(this);
304                     clear();
305                     return;
306                 } else {
307                     msgState.sender.lastSentMessage = System.currentTimeMillis();
308                     msgState.msgTemplate = "message.send.moderated";
309                     msgState.message = msgState.msg;
310                     msgState.sender.getGroup().sendMessage(this);
311                     msgState.msgTemplate = "message.send.moderated.personal";
312                     msgState.message = msgState.msg;
313                     msgState.sender.sendMessage(this);
314                     clear();
315                     return;
316                 }
317             } else {
318                 msgState.sender.lastSentMessage = System.currentTimeMillis();
319                 msgState.msgTemplate = "message.send";
320                 msgState.message = msgState.msg;
321                 msgState.sender.getGroup().sendMessage(this);
322                 clear();
323                 return;
324             }
325                 
326         }
327
328         if (req!=null) {
329             req.currPosition = RequestReader.EVALUATE_COMMAND;
330             req.currCommand = msgState.msg;
331         }
332         // retrieve the command-token
333
int pos = msgState.msg.indexOf (" ");
334         String JavaDoc cmd, param;
335         if (pos > -1) {
336             cmd = msgState.msg.substring(0,pos).toLowerCase();
337             param = msgState.msg.substring (pos).trim ();
338         } else {
339             cmd = msgState.msg;
340             param = "";
341         }
342         // "/.... text" is used for whispering to user ...
343
if (param.length() > 0) {
344             if (cmd.equals("/q")) {
345                 cmd = "/m";
346                 param = "q " + param;
347             } else if (cmd.equals("/time")) {
348                 cmd = "/m";
349                 param = "time " + param;
350             } else if (cmd.equals("/raq")) {
351                 cmd = "/m" ;
352                 param = "raq " + param;
353             } else if (cmd.equals("/mycol")) {
354                 cmd = "/m";
355                 param = "mycol " + param;
356             } else if (cmd.equals("/fl")) {
357                 cmd = "/m";
358                 param = "fl " + param;
359             } else if (cmd.equals("/a")) {
360                 cmd = "/m";
361                 param = "a " + param;
362             } else if (cmd.equals("/l")) {
363                 cmd = "/m";
364                 param = "l " + param;
365             } else if (cmd.equals("/ul")) {
366                 cmd = "/m";
367                 param = "ul " + param;
368             }
369         }
370         byte result = cs.evaluate(cmd, msgState, param);
371         if (result == CommandSet.UNKNOWN_COMMAND) {
372             cs.evaluate("/m", msgState, msgState.msg.substring (1));
373         } else if (result==CommandSet.INTERRUPTED) {
374             msgState.cb.logError("ConnectionBuffer was invalidated");
375         }
376         clear ();
377     }
378     
379     private volatile String JavaDoc strgVal;
380     public String JavaDoc toString () {
381         if (strgVal==null) {
382             StringBuffer JavaDoc sb = new StringBuffer JavaDoc("[MessageParser ");
383             if (req != null)
384                 sb.append (this.req.toString());
385             sb.append ("]");
386         }
387         return strgVal;
388         
389     }
390     /**
391      * @param msg
392      */

393     public void setMessage(String JavaDoc msg) {
394         msgState.message = msg;
395     }
396
397     public void finalize() {
398         if (Server.TRACE_CREATE_AND_FINALIZE)
399             Server.log(this, "----------------------------------------FINALIZED", Server.MSG_STATE, Server.LVL_VERY_VERBOSE);
400     }
401 }
Popular Tags