some small changes delting unneeded imports. two new exceptions in mir.storage. usage...
[mir.git] / source / mir / storage / store / StoreContainer.java
1 /*
2  * Copyright (C) 2001, 2002  The Mir-coders group
3  *
4  * This file is part of Mir.
5  *
6  * Mir is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License as published by
8  * the Free Software Foundation; either version 2 of the License, or
9  * (at your option) any later version.
10  *
11  * Mir is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with Mir; if not, write to the Free Software
18  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
19  *
20  * In addition, as a special exception, The Mir-coders gives permission to link
21  * the code of this program with the com.oreilly.servlet library, any library
22  * licensed under the Apache Software License, The Sun (tm) Java Advanced
23  * Imaging library (JAI), The Sun JIMI library (or with modified versions of
24  * the above that use the same license as the above), and distribute linked
25  * combinations including the two.  You must obey the GNU General Public
26  * License in all respects for all of the code used other than the above
27  * mentioned libraries.  If you modify this file, you may extend this exception
28  * to your version of the file, but you are not obligated to do so.  If you do
29  * not wish to do so, delete this exception statement from your version.
30  */
31
32 package mir.storage.store;
33
34 /**
35  * Title:         StoreContainer
36  *
37  * Description:   This is the bucket object for one type of StorableObjects,
38  *                mainy a linked list of StoreIdenfiers. On use or creation
39  *                an object stored in StoreIdentifier is put to head of the
40  *                list. if maximum size of the list is reached, the
41  *                StoreIdentifier at the end of the list is released.
42  *
43  * Copyright:     Copyright (c) 2002
44  * Company:       indy
45  * @author        //rk
46  * @version 1.0
47  */
48
49 import java.util.LinkedList;
50 import java.util.ListIterator;
51
52 import javax.servlet.http.HttpServletRequest;
53
54 import mir.misc.Logfile;
55 import mir.misc.StringUtil;
56
57 public class StoreContainer {
58
59         private final static int    DEFAULT_SIZE=10;
60         private static Logfile      storeLog;
61         private static int          uniqueCounter=10000;
62
63         private LinkedList          container;
64         private StoreContainerType  stocType;
65         private int                 maxSize=DEFAULT_SIZE, uniqueId;
66   private int                 addCount=0,removeCount=0,storeOutCount;
67   private int                 hitCount=0,missCount=0;
68   private static ObjectStore  o_store = ObjectStore.getInstance();
69
70         // avoid construction without parameters
71   private StoreContainer() {};
72
73         public StoreContainer(StoreContainerType stoc_type) {
74                 this.uniqueId=++uniqueCounter;
75                 this.stocType=stoc_type;
76                 this.container=new LinkedList();
77     int defaultSize = stoc_type.getDefaultSize();
78     String confProperty = stoc_type.getConfPrefix()+".DefaultSize";
79     String confedSize = o_store.getConfProperty(confProperty);
80     if ( confedSize!=null ) {
81       this.maxSize = StringUtil.parseInt (confedSize, defaultSize);
82     }
83         }
84
85         public StoreContainer(StoreContainerType stoc_type, int maxSize) {
86                 this();
87                 this.maxSize=maxSize;
88         }
89
90
91
92         public synchronized StorableObject use(StoreIdentifier sid) {
93     int hit = container.indexOf(sid);
94     if (hit>=0) {
95       StoreIdentifier hitSid = (StoreIdentifier)container.get(hit);
96                   if ( hitSid!=null ) {
97          hitCount++;
98          return hitSid.use();
99                   }
100     }
101     missCount++;
102     return null;
103         }
104
105         public boolean has(StoreIdentifier sid) {
106                 return container.contains(sid);
107         }
108
109         public void add(StoreIdentifier sid) {
110                 if ( sid != null && sid.hasReference() ) {
111                         if ( has(sid) ) {
112                           moveToHead(sid);
113                           System.err.println("OBJECTStore: tried to add sid " + sid.toString() +
114                             " that was already in store.");
115       }
116                         else {
117                                 container.addFirst(sid);
118         shrinkIfNecessary();
119         addCount++;
120                         }
121                 }
122         }
123
124         /**
125          *  Method:       invalidate(StorableObject sto)
126          *  Description:  finds @see StorableObject, propagates invalidation to
127          *                @see StoreIdentifier and removes StoreIdentifier from
128          *                list.
129          */
130         public synchronized void invalidate(StoreIdentifier search_sid) {
131     if (search_sid!=null) {
132       int hit = container.indexOf(search_sid);
133       if (hit >0 ) {
134         StoreIdentifier sid = (StoreIdentifier)container.get(hit);
135         container.remove(sid);
136         sid.invalidate();
137         removeCount++;
138       }
139     }
140         }
141
142   public synchronized void invalidate() {
143     StoreIdentifier sid;
144     while (container.size() > 0) {
145       sid=(StoreIdentifier)container.getLast();
146       container.removeLast();
147       sid.invalidate();
148     }
149   }
150
151         /**
152          *  Method:       setSize
153          *  Description:  readjusts StoreContainer size to value.
154          *
155          */
156         public void setSize(int size) {
157                 if (size <0) return;
158     shrinkToSize(size);
159                 this.maxSize=size;
160         }
161
162         private void shrinkIfNecessary() { shrinkToSize(maxSize); }
163
164   private void shrinkToSize(int size) {
165     if ( size < container.size() ) {
166                         // shrink
167                         while (size < container.size() ) {
168                                 StoreIdentifier sid = (StoreIdentifier)container.getLast();
169                                 container.remove(sid);
170         sid.release();
171         storeOutCount++;
172                         }
173                 }
174   }
175
176   private synchronized void moveToHead(StoreIdentifier sid) {
177     if ( sid!=null ) {
178       container.remove(sid);
179       container.addFirst(sid);
180     }
181   }
182
183         /**
184          *  Method:       toString()
185          *  Description:  gives out statistical Information, viewable via
186          *                @see ServletStoreInfo.
187          *
188          *  @return       String
189          */
190         public String toString() {
191     return toHtml(null);
192         }
193
194   public String toHtml(HttpServletRequest req) {
195     boolean showingContent=false;
196     float hitRatio=0;
197     long divisor=hitCount+missCount;
198     if (divisor>0) hitRatio=(float)hitCount/(float)divisor;
199     hitRatio*=100;
200
201                 StringBuffer sb = new StringBuffer("StoreContainer id: ");
202                 sb.append(uniqueId).append(" for ");
203                 sb.append(stocType.toString());
204     if ( req!=null ) {
205       String show = req.getParameter("stoc_show");
206       if ( show!=null && show.equals(""+uniqueId) ) {
207         // show all entries in container
208         sb.append(" [<b>showing</b>]");
209         showingContent=true;
210       }
211       else
212         sb.append(" [<a href=\"?stoc_show="+uniqueId+"\">show</a>]");
213     }
214     sb.append("\n  [current/maximum size: ");
215                 sb.append(container.size()).append("/").append(maxSize);
216                 sb.append("]\n  [added/stored out/removed: ").append(addCount).append("/");
217     sb.append(storeOutCount).append("/").append(removeCount).append("]\n  [hit/miss/ratio: ");
218     sb.append(hitCount).append("/").append(missCount).append("/");
219     sb.append(hitRatio).append("%]\n");
220
221     if (showingContent) {
222       sb.append("  <b>Container contains following references:</b>\n  ");
223       ListIterator it = container.listIterator();
224       while ( it.hasNext() ) {
225         StoreIdentifier sid = (StoreIdentifier)it.next();
226         sb.append(sid.toString()).append("\n  ");
227       }
228       sb.append("<b>End of List</b>\n\n");
229
230     }
231
232                 return sb.toString();
233         }
234
235 }