KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > com > rift > coad > lib > httpd > HttpRequestManager


1 /*
2  * CoadunationLib: The coaduntion implementation library.
3  * Copyright (C) 2006 Rift IT Contracting
4  *
5  * This library is free software; you can redistribute it and/or
6  * modify it under the terms of the GNU Lesser General Public
7  * License as published by the Free Software Foundation; either
8  * version 2.1 of the License, or (at your option) any later version.
9  *
10  * This library is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13  * Lesser General Public License for more details.
14  *
15  * You should have received a copy of the GNU Lesser General Public
16  * License along with this library; if not, write to the Free Software
17  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
18  *
19  * HttpRequestManager.java
20  *
21  * This object is responsible for queuing the http requests.
22  */

23
24 // the package path
25
package com.rift.coad.lib.httpd;
26
27 // java imports
28
import java.util.Vector JavaDoc;
29
30 // log 4 j imports
31
import org.apache.log4j.Logger;
32
33 // coadunation imports
34
import com.rift.coad.lib.thread.BasicThread;
35 import com.rift.coad.lib.thread.CoadunationThreadGroup;
36 import com.rift.coad.lib.thread.ThreadStateMonitor;
37 import com.rift.coad.lib.security.ThreadsPermissionContainer;
38 import com.rift.coad.lib.configuration.Configuration;
39 import com.rift.coad.lib.configuration.ConfigurationFactory;
40
41 /**
42  * This object is responsible for queuing the http requests.
43  *
44  * @author Brett Chaldecott
45  */

46 public class HttpRequestManager {
47     
48     // the http request queue
49
public class HttpRequestQueue {
50         // the classes private member variables
51
private Vector JavaDoc requestQueue = new Vector JavaDoc();
52         
53         /**
54          * The constructor of the http request queue.
55          */

56         public HttpRequestQueue() {
57             
58         }
59         
60         
61         /**
62          * This method adds a new request to the request queue.
63          *
64          *
65          * @param requestInterface The reference to the http service handler object.
66          * @exception HttpdException
67          */

68         public synchronized void pushRequest(
69                 RequestInterface requestInterface) throws HttpdException {
70             processorPoolManager.notifyThread();
71             requestQueue.add(requestInterface);
72         }
73         
74         
75         /**
76          * This method will pop a request of the queue.
77          */

78         public synchronized RequestInterface popRequest() {
79             if (requestQueue.size() == 0) {
80                 return null;
81             }
82             RequestInterface requestInterface =
83                     (RequestInterface)requestQueue.get(0);
84             requestQueue.remove(0);
85             return requestInterface;
86         }
87         
88         
89         /**
90          * This method returns the size of the http request manager.
91          *
92          * @return The size of the http request manager.
93          */

94         public synchronized int size() {
95             return requestQueue.size();
96         }
97     }
98     
99     
100     /**
101      * This thread is responsible controlling the http processing required by
102      * clients.
103      */

104     public class HttpProcessor extends BasicThread {
105         
106         // The classes private member variables
107
private ThreadStateMonitor threadStateMonitor =
108                 new ThreadStateMonitor();
109         
110         /**
111          * The constructor of the http processor.
112          */

113         public HttpProcessor() throws Exception JavaDoc {
114             
115         }
116         
117         
118         /**
119          * This method replaces the run method in the BasicThread.
120          *
121          * @exception Exception
122          */

123         public void process() throws Exception JavaDoc {
124             log.debug("Process.");
125             while(threadStateMonitor.isTerminated() == false) {
126                 log.debug("Wait for request.");
127                 if (processorPoolManager.monitor() == false) {
128                     break;
129                 }
130                 log.debug("Get a request.");
131                 RequestInterface requestInterface =
132                         requestQueue.popRequest();
133                 if (requestInterface != null) {
134                     try {
135                         log.info("Process a new http request.");
136                         requestInterface.handleRequest();
137                     } catch (Exception JavaDoc ex) {
138                         log.error("Failed to process an HTTP request [" +
139                                 ex.getMessage() + "].",ex);
140                     } finally {
141                         requestInterface.destroy();
142                     }
143                 }
144             }
145             log.debug("Http Processor exiting.");
146         }
147         
148         
149         /**
150          * This method will be implemented by child objects to terminate the
151          * processing of this thread.
152          */

153         public void terminate() {
154             log.debug("Terminate called on Http Processor");
155             threadStateMonitor.terminate(true);
156         }
157     }
158     
159     
160     /**
161      * This object is responsible for controlling the processors. It
162      */

163     public class ProcessorPoolManager {
164         
165         // the private member variables
166
private boolean running = true;
167         private CoadunationThreadGroup threadGroup = null;
168         private int min = 0;
169         private int max = 0;
170         private int currentSize = 0;
171         private int waitingThreads = 0;
172         private int requestCount = 0;
173         private String JavaDoc username = null;
174         
175         
176         /**
177          * The constructor of the thread group object.
178          *
179          * @param threadGroup The reference to the thread group.
180          * @param min The minimum value.
181          * @param max The maximum value.
182          * @param username The guest username.
183          */

184         public ProcessorPoolManager(CoadunationThreadGroup threadGroup,int min, int max,
185                 String JavaDoc username)
186                 throws HttpdException {
187             try {
188                 this.threadGroup = threadGroup.createThreadGroup();
189                 this.min = min;
190                 this.max = max;
191                 this.username = username;
192             } catch (Exception JavaDoc ex) {
193                 throw new HttpdException(
194                         "Failed to instanciate the processor pool manager : " +
195                         ex.getMessage(),ex);
196             }
197         }
198         
199         
200         /**
201          * This method terminates the waiting threads
202          */

203         public void shutdown() {
204             synchronized (this) {
205                 running = false;
206                 notifyAll();
207             }
208             log.debug("Terminate the thread group");
209             threadGroup.terminate();
210         }
211         
212         
213         /**
214          * This method will notify a waiting thread if one is available
215          * otherwise it will instanciate a new one.
216          */

217         public synchronized void notifyThread() throws HttpdException {
218             if (running) {
219                 requestCount++;
220                 if (waitingThreads > 0) {
221                     log.debug("Notify a waiting thread 2");
222                     notify();
223                 } else if (currentSize < max) {
224                     try {
225                         log.debug("Add a thread");
226                         // instanciate the deployment thread
227
HttpProcessor httpProcessor = new HttpProcessor();
228                         threadGroup.addThread(httpProcessor,username);
229                         httpProcessor.start();
230                         currentSize++;
231                     } catch (Exception JavaDoc ex) {
232                         throw new HttpdException
233                                 ("Failed create a thread to process task : " +
234                                 ex.getMessage(),ex);
235                     }
236                 }
237             } else {
238                 throw new HttpdException
239                         ("Shut Down can handle not more requests");
240             }
241         }
242         
243         
244         /**
245          * This method will be called a thread to either wait untill there are
246          * requests, get an exit notice if not require any more or start
247          * processing.
248          *
249          * @return TRUE if processing is required, FALSE if the thread must exit.
250          */

251         public synchronized boolean monitor() {
252             if (running == false) {
253                 currentSize--;
254                 return false;
255             } else if (requestCount > 0) {
256                 requestCount --;
257                 return true;
258             } else if (currentSize > min) {
259                 currentSize--;
260                 return false;
261             }
262             try {
263                 waitingThreads++;
264                 wait();
265                 waitingThreads--;
266             } catch (Exception JavaDoc ex) {
267                 // do nothing
268
}
269             return running;
270         }
271     }
272     
273     // class constants
274
private final static String JavaDoc MIN_KEY = "pool_min";
275     private final static long MIN_DEFAULT = 10;
276     private final static String JavaDoc MAX_KEY = "pool_max";
277     private final static long MAX_DEFAULT = 20;
278     
279     // static member variables
280
private Logger log =
281             Logger.getLogger(HttpRequestManager.class.getName());
282     
283     // the privat emember variables
284
private Configuration configuration = null;
285     private HttpRequestQueue requestQueue = new HttpRequestQueue();
286     private ProcessorPoolManager processorPoolManager = null;
287     
288     
289     /**
290      * Creates a new instance of HttpRequestManager
291      *
292      *
293      * @param threadGroup The reference to the thread group object.
294      * @exception HttpdException
295      */

296     public HttpRequestManager(CoadunationThreadGroup threadGroup) throws HttpdException {
297         try {
298             configuration = ConfigurationFactory.getInstance().getConfig(
299                     this.getClass());
300             processorPoolManager = new ProcessorPoolManager(threadGroup,
301                     (int)configuration.getLong(MIN_KEY,MIN_DEFAULT),
302                     (int)configuration.getLong(MAX_KEY,MAX_DEFAULT),
303                     configuration.getString(HttpDaemon.USERNAME_KEY));
304         } catch (Exception JavaDoc ex) {
305             throw new HttpdException(
306                     "Failed to instanciate the http request manager : " +
307                     ex.getMessage(),ex);
308         }
309     }
310     
311     
312     /**
313      * This method stores the http service handler requests.
314      *
315      *
316      * @param requestInterface The reference to the new request to add.
317      * @exception HttpdException
318      */

319     public void addRequest(RequestInterface requestInterface)
320     throws HttpdException {
321         requestQueue.pushRequest(requestInterface);
322     }
323     
324     
325     /**
326      * This mehtod will shut down this object
327      */

328     public void shutdown() {
329         processorPoolManager.shutdown();
330     }
331 }
332
Popular Tags