KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > com > sun > ejb > base > sfsb > store > FileStoreManager


1 /*
2  * The contents of this file are subject to the terms
3  * of the Common Development and Distribution License
4  * (the License). You may not use this file except in
5  * compliance with the License.
6  *
7  * You can obtain a copy of the license at
8  * https://glassfish.dev.java.net/public/CDDLv1.0.html or
9  * glassfish/bootstrap/legal/CDDLv1.0.txt.
10  * See the License for the specific language governing
11  * permissions and limitations under the License.
12  *
13  * When distributing Covered Code, include this CDDL
14  * Header Notice in each file and include the License file
15  * at glassfish/bootstrap/legal/CDDLv1.0.txt.
16  * If applicable, add the following below the CDDL Header,
17  * with the fields enclosed by brackets [] replaced by
18  * you own identifying information:
19  * "Portions Copyrighted [year] [name of copyright owner]"
20  *
21  * Copyright 2006 Sun Microsystems, Inc. All rights reserved.
22  */

23
24 package com.sun.ejb.base.sfsb.store;
25
26 import java.io.BufferedInputStream JavaDoc;
27 import java.io.BufferedOutputStream JavaDoc;
28 import java.io.File JavaDoc;
29 import java.io.FileInputStream JavaDoc;
30 import java.io.FileOutputStream JavaDoc;
31 import java.io.IOException JavaDoc;
32 import java.io.ObjectInputStream JavaDoc;
33 import java.io.ObjectOutputStream JavaDoc;
34 import java.io.PrintWriter JavaDoc;
35 import java.io.StringWriter JavaDoc;
36
37 import java.util.HashMap JavaDoc;
38 import java.util.Iterator JavaDoc;
39 import java.util.Map JavaDoc;
40
41 import java.util.logging.*;
42
43 import com.sun.ejb.spi.monitorable.sfsb.MonitorableSFSBStore;
44
45 import com.sun.ejb.spi.stats.MonitorableSFSBStoreManager;
46
47 import com.sun.ejb.spi.sfsb.store.SFSBBeanState;
48 import com.sun.ejb.spi.sfsb.store.SFSBStoreManager;
49 import com.sun.ejb.spi.sfsb.store.SFSBStoreManagerException;
50
51 import com.sun.logging.*;
52
53 /**
54  * An implementation of SFSBStoreManager that uses file system to
55  * persist SFSB state.
56  *
57  * @author Mahesh Kannan
58  */

59  
60 public class FileStoreManager
61     implements SFSBStoreManager, MonitorableSFSBStoreManager
62 {
63     protected static Logger _logger =
64         LogDomains.getLogger(LogDomains.EJB_LOGGER);
65
66     protected String JavaDoc clusterId = "";
67     protected long containerId;
68
69     protected File JavaDoc baseDir;
70     protected String JavaDoc storeName;
71
72     protected int passivationTimeoutInSeconds;
73
74     private int loadCount;
75     private int loadSuccessCount;
76     private int loadErrorCount;
77     private int storeCount;
78     private int storeSuccessCount;
79     private int storeErrorCount;
80     private int expiredSessionCount;
81
82     private boolean shutdown;
83
84     private Level TRACE_LEVEL = Level.FINE;
85
86     private int gracePeriodInSeconds;
87
88     /**
89      * No arg constructor
90      */

91     public FileStoreManager() {
92     }
93
94     /****************************************************/
95     /**** Implementation of SFSBStoreManager methods ****/
96     /****************************************************/
97
98     public void checkpointSave(SFSBBeanState beanState)
99     throws SFSBStoreManagerException
100     {
101         saveState(beanState, false);
102     if (_logger.isLoggable(TRACE_LEVEL)) {
103         _logger.log(TRACE_LEVEL, storeName + "Checkpoint saved: "
104         + beanState.getId());
105     }
106     }
107
108     public SFSBBeanState createSFSBBeanState(Object JavaDoc sessionId,
109         long lastAccess, boolean isNew, byte[] state)
110     {
111     return new SFSBBeanState(clusterId, containerId,
112         sessionId, lastAccess, isNew, state, this);
113     }
114     
115     public SFSBBeanState getState(Object JavaDoc sessionKey) {
116
117         String JavaDoc fileName = sessionKey.toString();
118         SFSBBeanState beanState = null;
119
120     if(_logger.isLoggable(TRACE_LEVEL)) {
121         _logger.log(TRACE_LEVEL, storeName + "Attempting to load session: "
122                 + sessionKey);
123     }
124
125         File JavaDoc file = new File JavaDoc(baseDir, fileName);
126         if (file.exists()) {
127             int dataSize = (int) file.length();
128             byte[] data = new byte[dataSize];
129             BufferedInputStream JavaDoc bis = null;
130             FileInputStream JavaDoc fis = null;
131             try {
132                 loadCount++;
133                 fis = new FileInputStream JavaDoc(file);
134                 bis = new BufferedInputStream JavaDoc(fis);
135                 int offset = 0;
136                 for (int toRead = dataSize; toRead > 0; ) {
137                     int count = bis.read(data, offset, toRead);
138                     offset += count;
139                     toRead -= count;
140                 }
141         
142         beanState = new SFSBBeanState("", -1, sessionKey, -1,
143             false, data, this);
144
145                 loadSuccessCount++;
146         if(_logger.isLoggable(TRACE_LEVEL)) {
147             _logger.log(TRACE_LEVEL, storeName
148                 + " Successfully loaded session: " + sessionKey);
149         }
150             } catch (Exception JavaDoc ex) {
151                 loadErrorCount++;
152                 _logger.log(Level.WARNING,
153                     "ejb.sfsb_storemgr_loadstate_failed",
154                     new Object JavaDoc[] {fileName});
155                 _logger.log(Level.WARNING,
156                     "ejb.sfsb_storemgr_loadstate_exception", ex);
157             } finally {
158                 try {
159             bis.close();
160         } catch (Exception JavaDoc ex) {
161             _logger.log(Level.FINEST, storeName + " Error while "
162                 + "closing buffered input stream", ex);
163         }
164                 try {
165             fis.close();
166         } catch (Exception JavaDoc ex) {
167             _logger.log(Level.FINEST, storeName + " Error while "
168                 + "closing file input stream", ex);
169         }
170             }
171         } else {
172         if(_logger.isLoggable(TRACE_LEVEL)) {
173         _logger.log(Level.WARNING, storeName + "Could not find passivated "
174             + "file for: " + sessionKey);
175         }
176     }
177         return beanState;
178     }
179      
180     public void initSessionStore(Map JavaDoc storeEnv) {
181
182         this.storeName = (String JavaDoc) storeEnv.get(
183         FileStoreManagerConstants.STORE_MANAGER_NAME);
184         try {
185         Long JavaDoc cId = (Long JavaDoc) storeEnv.get(
186             FileStoreManagerConstants.CONTAINER_ID);
187         this.containerId = cId.longValue();
188     } catch (Exception JavaDoc ex) {
189         _logger.log(Level.WARNING, "Couldn't get containerID", ex);
190     }
191
192         String JavaDoc baseDirName = (String JavaDoc) storeEnv.get(
193                 FileStoreManagerConstants.PASSIVATION_DIRECTORY_NAME);
194
195         this.baseDir = new File JavaDoc(baseDirName);
196
197         try {
198         Integer JavaDoc sessionTimeout = (Integer JavaDoc) storeEnv.get(
199         FileStoreManagerConstants.SESSION_TIMEOUT_IN_SECONDS);
200         if (sessionTimeout != null) {
201         this.passivationTimeoutInSeconds = sessionTimeout.intValue();
202         }
203     } catch (Exception JavaDoc ex) {
204         _logger.log(Level.WARNING, "Couldn't get session timeout", ex);
205     }
206
207         try {
208         Integer JavaDoc graceTimeout = (Integer JavaDoc) storeEnv.get(
209         FileStoreManagerConstants.GRACE_SESSION_TIMEOUT_IN_SECONDS);
210         if (graceTimeout != null) {
211         this.gracePeriodInSeconds = graceTimeout.intValue();
212         }
213     } catch (Exception JavaDoc ex) {
214         _logger.log(Level.WARNING, "Couldn't get session timeout", ex);
215     }
216
217         try {
218             if ((baseDir.mkdirs() == false) && (!baseDir.isDirectory())) {
219         _logger.log(Level.WARNING, "ejb.sfsb_storemgr_mdirs_failed",
220             new Object JavaDoc[] {baseDirName});
221         //TODO: Log storeName also
222
} else {
223         if (_logger.isLoggable(TRACE_LEVEL)) {
224             _logger.log(TRACE_LEVEL, "Successfully Initialized "
225                 + "FileStoreManager for: " + storeName);
226         }
227         }
228         } catch (Exception JavaDoc ex) {
229         _logger.log(Level.WARNING, "ejb.sfsb_storemgr_init_failed",
230                     new Object JavaDoc[] {baseDirName});
231         _logger.log(Level.WARNING, "ejb.sfsb_storemgr_init_exception", ex);
232         }
233
234     }
235
236     public void passivateSave(SFSBBeanState beanState)
237     throws SFSBStoreManagerException
238     {
239         saveState(beanState, true);
240     }
241
242     public void remove(Object JavaDoc sessionKey) {
243         try {
244             removeFile(new File JavaDoc(baseDir, sessionKey.toString()));
245         } catch (Exception JavaDoc ex) {
246             _logger.log(Level.WARNING,
247                 "ejb.sfsb_storemgr_removestate_failed",
248                 new Object JavaDoc[] {sessionKey.toString()});
249             _logger.log(Level.WARNING,
250                 "ejb.sfsb_storemgr_removestate_exception", ex);
251         }
252     }
253       
254     public void removeAll() {
255         try {
256         String JavaDoc[] fileNames = baseDir.list();
257         for (int i=0; i<fileNames.length; i++) {
258                 remove(fileNames[i]);
259         }
260
261         if (baseDir.delete() == false) {
262         if (baseDir.exists()) {
263             Object JavaDoc[] params = {baseDir.getAbsolutePath()};
264             _logger.log(Level.WARNING,
265             "ejb.sfsb_storemgr_removedir_failed", params);
266         }
267         }
268         } catch (Throwable JavaDoc th) {
269             _logger.log(Level.WARNING, "ejb.sfsb_storemgr_removeall_exception", th);
270         }
271     }
272       
273     public void removeExpired() {
274     expiredSessionCount += removeExpiredSessions();
275     }
276
277     public int removeExpiredSessions() {
278     if (passivationTimeoutInSeconds <= 0) {
279         return 0;
280     }
281     long threshold = System.currentTimeMillis()
282         - (passivationTimeoutInSeconds * 1000)
283         - (gracePeriodInSeconds * 1000);
284     int expiredSessions = 0;
285         try {
286         String JavaDoc[] fileNames = baseDir.list();
287         int size = fileNames.length;
288         for (int i=0; (i<size) && (! shutdown); i++) {
289         File JavaDoc file = new File JavaDoc(baseDir, fileNames[i]);
290         if (file.exists()) {
291             long lastAccessed = file.lastModified();
292             if (lastAccessed < threshold) {
293             if (! file.delete()) {
294                 if (file.exists()) {
295                 _logger.log(Level.WARNING, storeName
296                     + "Couldn't remove file: " + fileNames[i]);
297                 }
298             } else {
299                 expiredSessions++;
300             }
301             }
302         }
303         }
304     } catch (Exception JavaDoc ex) {
305         _logger.log(Level.WARNING, storeName + "Exception while getting "
306             + "expired files", ex);
307     }
308
309     return expiredSessions;
310     }
311
312     public void shutdown() {
313         shutdown = true;
314     }
315       
316     public void updateLastAccessTime(Object JavaDoc sessionKey, long time)
317         throws SFSBStoreManagerException
318     {
319     String JavaDoc fileName = sessionKey.toString();
320     try {
321         File JavaDoc file = new File JavaDoc(baseDir, fileName);
322
323         if (file.setLastModified(time) == false) {
324         if (file.exists() == false) {
325             _logger.log(Level.WARNING, storeName
326             + ": Cannot update timsestamp for: " + sessionKey
327                 + "; File does not exist");
328         } else {
329             throw new SFSBStoreManagerException(
330             storeName + ": Cannot update timsestamp for: " + sessionKey);
331         }
332         }
333     } catch (SFSBStoreManagerException sfsbSMEx) {
334         throw sfsbSMEx;
335     } catch (Exception JavaDoc ex) {
336         _logger.log(Level.WARNING, storeName
337         + ": Exception while updating timestamp", ex);
338         throw new SFSBStoreManagerException(
339         "Cannot update timsestamp for: " + sessionKey
340             + "; Got exception: " + ex);
341     }
342     }
343
344     /***************************************************************/
345     /************** Methods on MonitorableSFSBCache **************/
346     /***************************************************************/
347
348     public int getCurrentSize() {
349         //return passivatedSessions.getEntryCount();
350
try {
351         return baseDir.list().length;
352     } catch (Exception JavaDoc ex) {
353     }
354     return 0;
355     }
356
357     public int getLoadCount() {
358         return loadCount;
359     }
360     
361     public int getLoadSuccessCount() {
362         return loadSuccessCount;
363     }
364     
365     public int getLoadErrorCount() {
366         return loadErrorCount;
367     }
368
369     public int getPassivationCount() {
370         return storeCount;
371     }
372     
373     public int getPassivationSuccessCount() {
374         return storeSuccessCount;
375     }
376     
377     public int getPassivationErrorCount() {
378         return storeErrorCount;
379     }
380
381     public int getCheckpointCount() {
382         return storeCount;
383     }
384     
385     public int getCheckpointSuccessCount() {
386         return storeSuccessCount;
387     }
388     
389     public int getCheckpointErrorCount() {
390         return storeErrorCount;
391     }
392
393     public int getExpiredSessionCount() {
394         return expiredSessionCount;
395     }
396
397
398     /***************************************************************/
399     /********************* Internal methods **********************/
400     /***************************************************************/
401
402     private void saveState(SFSBBeanState beanState, boolean isPassivated)
403     throws SFSBStoreManagerException
404     {
405
406         Object JavaDoc sessionKey = beanState.getId();
407         String JavaDoc fileName = sessionKey.toString();
408
409     if(_logger.isLoggable(TRACE_LEVEL)) {
410         _logger.log(TRACE_LEVEL, storeName + " Attempting to save "
411             + "session: " + sessionKey);
412     }
413         File JavaDoc file = null;
414
415         BufferedOutputStream JavaDoc bos = null;
416         FileOutputStream JavaDoc fos = null;
417
418         try {
419             storeCount++;
420             file = new File JavaDoc(baseDir, fileName);
421         if (file.exists()) {
422         if (beanState.isNew()) {
423             _logger.log(Level.WARNING, storeName + " [InternalError] "
424             + "isNew() must be false for: " + sessionKey);
425         }
426         } else {
427         if (beanState.isNew() == false) {
428             _logger.log(Level.WARNING, storeName + " [InternalError] "
429             + "isNew() must be true for: " + sessionKey);
430         }
431         }
432             fos = new FileOutputStream JavaDoc(file);
433             bos = new BufferedOutputStream JavaDoc(fos);
434             byte[] data = beanState.getState();
435             bos.write(data, 0, data.length);
436
437             storeSuccessCount++;
438         if(_logger.isLoggable(TRACE_LEVEL)) {
439         _logger.log(TRACE_LEVEL, storeName + " Successfully saved "
440             + "session: " + sessionKey);
441             }
442         } catch (Exception JavaDoc ex) {
443             storeErrorCount++;
444         _logger.log(Level.WARNING, "ejb.sfsb_storemgr_savestate_failed",
445                 new Object JavaDoc[] {fileName});
446         _logger.log(Level.WARNING, "ejb.sfsb_storemgr_savestate_exception", ex);
447             try { removeFile(file); } catch (Exception JavaDoc ex1) {}
448             String JavaDoc errMsg = "Could not save session: " + beanState.getId();
449             throw new SFSBStoreManagerException(errMsg, ex);
450         } finally {
451             try {
452         if (bos != null) bos.close();
453         } catch (Exception JavaDoc ex) {
454         _logger.log(Level.FINE, "Error while closing buffered output stream", ex);
455         }
456             try {
457         if (fos != null) fos.close();
458         } catch (Exception JavaDoc ex) {
459         _logger.log(Level.FINE, "Error while closing file output stream", ex);
460         }
461         }
462     }
463       
464     private boolean removeFile(final File JavaDoc file) {
465         Boolean JavaDoc status = (Boolean JavaDoc) java.security.AccessController.doPrivileged(
466             new java.security.PrivilegedAction JavaDoc() {
467                 public java.lang.Object JavaDoc run() {
468                     return (new Boolean JavaDoc(file.delete()));
469                 }
470             }
471         );
472
473         boolean success = status.booleanValue();
474         if (!success) {
475             _logger.log(Level.WARNING, "ejb.sfsb_storemgr_removestate_failed",
476                 new Object JavaDoc[] {file.getName()});
477         } else {
478         if(_logger.isLoggable(TRACE_LEVEL)) {
479         _logger.log(TRACE_LEVEL, storeName + " Removed session: "
480             + file.getName());
481             }
482     }
483
484     return success;
485     }
486
487     public MonitorableSFSBStoreManager getMonitorableSFSBStoreManager() {
488     return this;
489     }
490
491     public long getCurrentStoreSize() {
492     try {
493         return baseDir.list().length;
494     } catch (Exception JavaDoc ex) {
495     }
496     return 0;
497     }
498
499     public void appendStats(StringBuffer JavaDoc sbuf) {
500     }
501
502     public void monitoringLevelChanged(boolean monitoringOn) {
503     }
504
505 }
506
Popular Tags