| 1 18 package freecs.core; 19 20 import freecs.*; 21 import freecs.auth.AuthManager; 22 import freecs.content.*; 23 import freecs.external.AccessForbiddenException; 24 import freecs.external.IRequestHandler; 25 import freecs.external.StateRequestHandler; 26 import freecs.external.StaticRequestHandler; 27 import freecs.external.UserlistRequestHandler; 28 import freecs.external.WebadminRequestHandler; 29 import freecs.interfaces.*; 30 import freecs.util.CookieGenerator; 31 import freecs.layout.TemplateSet; 32 import java.nio.channels.SelectionKey ; 33 import java.util.HashMap ; 34 35 42 public class RequestEvaluator { 43 private MessageParser mp; 44 private short parserID; 45 private RequestReader req; 46 private HashMap requestHandlers; 47 48 public RequestEvaluator (RequestReader r) { 49 parserID = r.getID(); 50 mp = new MessageParser (r); 51 req=r; 52 requestHandlers = new HashMap (); 53 requestHandlers.put("/userlist", new UserlistRequestHandler("/USERLIST")); 54 requestHandlers.put("/state", new StateRequestHandler("/STATE")); 55 requestHandlers.put("/admin", new WebadminRequestHandler("/ADMIN")); 56 requestHandlers.put("/static", new StaticRequestHandler("/static")); 57 } 58 59 63 public void evaluate(IRequest cReq) { 64 if (cReq==null) 65 return; 66 SelectionKey key = cReq.getKey (); 67 if (!CentralSelector.isSkValid(key)) { 68 Server.log(this, "evaluate: request has invalid key", Server.MSG_STATE, Server.LVL_VERBOSE); 69 return; 70 } 71 ConnectionBuffer rb = cReq.getConnectionBuffer (); 72 if (rb == null) { 74 Server.log (this, "ConnectionBuffer was empty", Server.MSG_ERROR, Server.LVL_MAJOR); 75 CentralSelector.dropKey(key); 76 return; 77 } 78 req.currPosition = RequestReader.EVALUATING; 79 try { 80 String action = cReq.getAction (); 81 byte method = cReq.getMethod (); 82 String cookie = cReq.getCookie (); 83 84 rb.addLog (method == IRequest.METHOD_GET ? "GET" : "POST"); 86 rb.addLog (action); 87 rb.addLog (((HTTPRequest) cReq).isHTTP11 () ? "HTTP/1.1" : "HTTP/1.0"); 88 if (cookie == null) 89 rb.addLog ("NO-COOKIE"); 90 else 91 rb.addLog (cookie); 92 rb.addLog (" "); 93 rb.addLog (cReq.getUserAgent()); 94 95 User u = (cookie == null ? null : UserManager.mgr.getUserByCookie (cookie)); 97 boolean isHTTP11 = ((HTTPRequest) cReq).isHTTP11 (); 98 99 TemplateSet ts = null; 101 String templateset = cReq.getValue ("templateset"); 102 if (templateset != null) { 103 ts = Server.srv.templatemanager.getTemplateSet (templateset); 104 } else if (u != null) { 105 ts = u.getTemplateSet (); 106 } 107 108 ContentContainer c = new ContentContainer (); 109 ((ContentContainer) c).setHTTP11 (isHTTP11); 110 if (ts != null) { 111 c.useTemplateSet (ts); 112 } 113 if (cookie == null) { 114 c.setCookie (CookieGenerator.generateCookie ()); 115 } 116 if (cookie != null && "/SEND".equals(action)) { 117 RequestMonitor.instance.addMonitor(Thread.currentThread(), System.currentTimeMillis() + Server.srv.READER_TIMEOUT); 118 if (!handleSend(u, rb, key, cReq, isHTTP11)) 119 return; 120 c.wrap ("dummy"); 121 } else if (action.toLowerCase().startsWith("/static/")) { 122 RequestMonitor.instance.addMonitor(Thread.currentThread(), System.currentTimeMillis() + Server.srv.READER_TIMEOUT); 123 try { 124 IRequestHandler reqHandler = (IRequestHandler) requestHandlers.get("/static"); 125 reqHandler.handle(cReq, c); 126 } catch (AccessForbiddenException noAccess) { 127 if (noAccess.hidePage() == true) { 128 c.setTemplate("not_found"); 129 } 130 } 131 } else if (requestHandlers.containsKey(action.toLowerCase())) { 132 RequestMonitor.instance.addMonitor(Thread.currentThread(), System.currentTimeMillis() + Server.srv.READER_TIMEOUT); 134 try { 135 IRequestHandler reqHandler = ((IRequestHandler)requestHandlers.get(action.toLowerCase())); 136 reqHandler.handle(cReq, c); 137 } catch (AccessForbiddenException noAccess) { 138 if (noAccess.hidePage() == true) { 139 c.setTemplate("not_found"); 140 } 141 } 142 } else if (method==IRequest.METHOD_GET) { 143 req.currPosition=RequestReader.EVAL_GET; 144 if ("/".equals(action)) { 145 RequestMonitor.instance.addMonitor(Thread.currentThread(), System.currentTimeMillis() + Server.srv.READER_TIMEOUT); 146 c.setTemplate ("start"); 147 } else if (cookie != null && "/LOGIN".equals (action)) { 148 RequestMonitor.instance.addMonitor(Thread.currentThread(), System.currentTimeMillis() + Server.srv.LOGIN_TIMEOUT); 149 if (u!=null) { 150 softCloseMessagesConnection(u, u.getKey()); 151 } 152 if (UserManager.mgr.tryLogin(null,null,null,ts,req,u) == UserManager.LOGIN_RELOAD) { 153 c.setTemplate ("frameset"); 154 if (ts != null) { 155 u.setTemplateSet (ts); 156 } 157 } else { 158 AuthManager.instance.doLogin(cReq, key, cookie, c, ts, u, isHTTP11, req); 159 } 160 } else if ("/INPUT".equals(action)) { 161 RequestMonitor.instance.addMonitor(Thread.currentThread(), System.currentTimeMillis() + Server.srv.READER_TIMEOUT); 162 c.setTemplate ("input"); 163 } else if ("/MESSAGES".equals(action)) { 164 RequestMonitor.instance.addMonitor(Thread.currentThread(), System.currentTimeMillis() + Server.srv.READER_TIMEOUT); 165 handleMessagesConnection(c, u, cReq, key, isHTTP11, rb); 166 return; 167 } else if ("/DUMMY".equals(action)) { 168 c.wrap ("dummy"); 169 } else { 171 RequestMonitor.instance.addMonitor(Thread.currentThread(), System.currentTimeMillis() + Server.srv.READER_TIMEOUT); 172 if (ts == null) ts = Server.srv.templatemanager.getTemplateSet("default"); 173 String tname = action.substring (1).toLowerCase (); 174 if (tname != null && tname.length () > 1) { 175 c.setTemplate (tname); 176 } else { 177 c.setTemplate ("not_found"); 178 } 179 } 180 } else if (method==IRequest.METHOD_POST) { 181 RequestMonitor.instance.addMonitor(Thread.currentThread(), System.currentTimeMillis() + Server.srv.LOGIN_TIMEOUT); 182 req.currPosition=RequestReader.EVAL_POST; 183 if (cookie != null && "/LOGIN".equals (action)) { 184 req.currPosition=RequestReader.EVAL_POST_LOGIN; 185 if (u!=null) { 186 softCloseMessagesConnection(u, u.getKey()); 187 } 188 AuthManager.instance.doLogin(cReq, key, cookie, c, ts, u, isHTTP11, req); 189 } else { 190 c.setTemplate ("not_found"); 191 } 192 } else { 193 c.setTemplate ("not_found"); 194 } 195 req.currPosition=RequestReader.EVAL_PREP4SEND; 196 if (c.prepareForSending (cReq)) { 197 if (!rb.isValid()) { 198 rb.logError("ConnectionBuffer was invalidated"); 199 CentralSelector.dropKey (key); 200 return; 201 } 202 req.currPosition=RequestReader.EVAL_SENDFINAL; 203 rb.addToWrite (c.getByteBuffer()); 204 if (c.closeSocket()) 205 rb.addToWrite(Responder.CLOSE_CONNECTION); 206 } else Server.log (this, "evaluate: prepareForSending failed", Server.MSG_ERROR, Server.LVL_VERY_VERBOSE); 207 } catch (Exception e) { 208 CentralSelector.dropKey (key); 209 Server.debug (this, "evaluate: drop key", e, Server.MSG_ERROR, Server.LVL_MAJOR); 210 rb.logError(e.getMessage()); 211 } 212 } 213 214 221 private void handleMessagesConnection(ContentContainer c, User u, IRequest cReq, SelectionKey key, boolean isHTTP11, ConnectionBuffer rb) { 222 req.currPosition=RequestReader.EVAL_GET_MESSAGES; 223 if (u != null 224 && (u.isJoining() 225 || u.isLoggedIn() 226 || u.isRemoving())) { 227 Connection conn = cReq.getConnectionObject(); 228 if (!u.wasActive ()) { 229 rb.logError("flooded"); 230 return; 231 } 232 if (!rb.isValid()) { 233 CentralSelector.dropKey(key); 234 rb.logError("ConnectionBuffer was invalidated"); 235 return; 236 } 237 synchronized (rb) { 238 rb.conn = conn; 239 rb.setIsMessageFrame(true); 240 } 241 SelectionKey oldKey; 242 synchronized (u) { 243 oldKey = u.getKey(); 244 u.setKey(key); 245 } 246 if (oldKey != null) { 247 softCloseMessagesConnection(u, oldKey); 249 } 250 u.setHTTP11 (isHTTP11); 251 c.setNoCache (); 252 c.setNoStore (); 253 c.setIsMessages (); 254 c.setTemplate ("welcome"); 255 if (!c.prepareForSending (cReq)) { 256 Server.log (this, "evaluate: unable to init /MESSAGES: prepareForSending failed", Server.MSG_TRAFFIC, Server.LVL_MAJOR); 257 rb.logError("/MESSAGE prepare for sending failed"); 258 CentralSelector.dropKey(key); 259 return; 260 } 261 req.currPosition=RequestReader.EVAL_GET_MESSAGES_APND2WRITE; 262 rb.addToWrite (c.getByteBuffer()); 263 if (c.closeSocket()) 264 rb.addToWrite(Responder.CLOSE_CONNECTION); 265 req.currPosition=RequestReader.EVAL_GET_MESSAGES_SND_MSGS; 266 u.sendScheduledMessages(); 267 return; 268 } else { 269 Server.log (this, "evaluate: bogous cookie or expired", Server.MSG_STATE, Server.LVL_MINOR); 270 if (u==null) 271 c.setTemplate ("no_cookie"); 272 else 273 c.setTemplate("login_missing"); 274 } 275 } 276 277 285 private boolean handleSend(User u, ConnectionBuffer rb, SelectionKey key, IRequest cReq, boolean isHTTP11) { 286 req.currPosition=RequestReader.EVAL_SEND; 287 if (u == null) { 288 CentralSelector.dropKey (key); 289 rb.logError("/send without user"); 290 return false; 291 } else if (!u.isLoggedIn()) { 292 CentralSelector.dropKey (key); 293 rb.logError("/send from logged-out user"); 294 return false; 295 } 296 if (!u.wasActive ()) { 297 rb.logError("flooded"); 298 return false; 299 } 300 if (Server.srv.isBanned (u.conn)) { 301 rb.logError("User Ip isBanned"); 302 mp.setSender(u); 303 mp.getSender().sendQuitMessage (false); 304 return false; 305 } 306 String msg = cReq.getValue ("message"); 307 if (msg == null || msg.length () < 1) { 308 Server.log (this, "evaluate: message too short", Server.MSG_TRAFFIC, Server.LVL_MINOR); 309 rb.logError("message too short"); 310 return false; 311 } 312 mp.clear (); 313 mp.setConnectionBuffer (rb); 314 mp.setRawMessage (msg); 315 mp.setHTTP11 (isHTTP11); 316 mp.setSender (u); 317 mp.parseAndSendMessage (); 318 return true; 319 } 320 321 324 private void softCloseMessagesConnection(User u, SelectionKey sk) { 325 try { 327 if (!CentralSelector.isSkValid(sk)) 328 return; 329 ConnectionBuffer cb = (ConnectionBuffer) sk.attachment(); 330 cb.setUser(null); 331 String msgTpl = u.getTemplateSet().getMessageTemplate("message.softClose"); 332 StringBuffer sb = new StringBuffer ( 333 MessageRenderer.renderTemplate(new MessageState(null), msgTpl)); 334 sb.append ("<body></html>"); 335 cb.addToWrite(MessageRenderer.encode(sb.toString())); 336 cb.addToWrite(Responder.CLOSE_CONNECTION_IGNORE); 337 } catch (Exception e) { 338 } 340 } 341 342 public String toString () { 343 StringBuffer tsb = new StringBuffer ("[RequestEvaluator ").append (parserID).append ("]"); 344 return (tsb.toString ()); 345 } 346 347 public int hashCode () { return (int) parserID; } 348 public short getID () { return (short) parserID; } 349 public boolean equals (RequestEvaluator rp) { return (parserID == rp.getID ()); } 350 351 } | Popular Tags |