jakarta-jcs-dev mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From asm...@apache.org
Subject svn commit: r783765 - in /jakarta/jcs/trunk/src: java/org/apache/jcs/access/exception/ java/org/apache/jcs/access/monitor/ java/org/apache/jcs/auxiliary/disk/ java/org/apache/jcs/auxiliary/disk/indexed/ java/org/apache/jcs/engine/ java/org/apache/jcs/e...
Date Thu, 11 Jun 2009 13:46:35 GMT
Author: asmuts
Date: Thu Jun 11 13:46:34 2009
New Revision: 783765

URL: http://svn.apache.org/viewvc?rev=783765&view=rev
Log:
Cleaning up:  Removing unused code.  Adding unit tests.

Added:
    jakarta/jcs/trunk/src/java/org/apache/jcs/engine/memory/lru/LHMLRUMemoryCache.java
    jakarta/jcs/trunk/src/test-conf/TestLHMLRUCache.ccf
    jakarta/jcs/trunk/src/test/org/apache/jcs/TestLogConfigurationUtil.java
    jakarta/jcs/trunk/src/test/org/apache/jcs/auxiliary/disk/AbstractDiskCacheUnitTest.java
    jakarta/jcs/trunk/src/test/org/apache/jcs/auxiliary/disk/LRUMapJCSUnitTest.java
    jakarta/jcs/trunk/src/test/org/apache/jcs/auxiliary/disk/PurgatoryElementUnitTest.java
    jakarta/jcs/trunk/src/test/org/apache/jcs/engine/memory/lru/LHMLRUMemoryCacheConcurrentUnitTest.java
    jakarta/jcs/trunk/src/test/org/apache/jcs/engine/memory/lru/LHMLRUMemoryCacheUnitTest.java
Removed:
    jakarta/jcs/trunk/src/java/org/apache/jcs/access/exception/NotARetrievableObjectException.java
    jakarta/jcs/trunk/src/java/org/apache/jcs/access/exception/NullObjectException.java
    jakarta/jcs/trunk/src/java/org/apache/jcs/access/monitor/MonitorAccess.java
    jakarta/jcs/trunk/src/java/org/apache/jcs/access/monitor/MonitorXMLRPCServer.java
Modified:
    jakarta/jcs/trunk/src/java/org/apache/jcs/auxiliary/disk/AbstractDiskCache.java
    jakarta/jcs/trunk/src/java/org/apache/jcs/auxiliary/disk/AbstractDiskCacheAttributes.java
    jakarta/jcs/trunk/src/java/org/apache/jcs/auxiliary/disk/PurgatoryElement.java
    jakarta/jcs/trunk/src/java/org/apache/jcs/auxiliary/disk/indexed/IndexedDiskElementDescriptor.java
    jakarta/jcs/trunk/src/java/org/apache/jcs/engine/CacheEventQueueFactory.java
    jakarta/jcs/trunk/src/java/org/apache/jcs/engine/control/CompositeCacheManager.java
    jakarta/jcs/trunk/src/java/org/apache/jcs/engine/memory/AbstractMemoryCache.java
    jakarta/jcs/trunk/src/java/org/apache/jcs/utils/struct/LRUMap.java
    jakarta/jcs/trunk/src/test/org/apache/jcs/engine/memory/lru/LRUMemoryCacheConcurrentUnitTest.java

Modified: jakarta/jcs/trunk/src/java/org/apache/jcs/auxiliary/disk/AbstractDiskCache.java
URL: http://svn.apache.org/viewvc/jakarta/jcs/trunk/src/java/org/apache/jcs/auxiliary/disk/AbstractDiskCache.java?rev=783765&r1=783764&r2=783765&view=diff
==============================================================================
--- jakarta/jcs/trunk/src/java/org/apache/jcs/auxiliary/disk/AbstractDiskCache.java (original)
+++ jakarta/jcs/trunk/src/java/org/apache/jcs/auxiliary/disk/AbstractDiskCache.java Thu Jun 11 13:46:34 2009
@@ -71,7 +71,7 @@
     private static final Log log = LogFactory.getLog( AbstractDiskCache.class );
 
     /** Generic disk cache attributes */
-    private IDiskCacheAttributes dcattr = null;
+    private IDiskCacheAttributes diskCacheAttributes = null;
 
     /**
      * Map where elements are stored between being added to this cache and actually spooled to disk.
@@ -89,7 +89,10 @@
      */
     protected ICacheEventQueue cacheEventQueue;
 
-    /** Indicates whether the cache is 'alive': initialized, but not yet disposed. */
+    /**
+     * Indicates whether the cache is 'alive': initialized, but not yet disposed. Child classes must
+     * set this to true.
+     */
     protected boolean alive = false;
 
     /** Every cache will have a name, subclasses must set this when they are initialized. */
@@ -107,20 +110,22 @@
     // ----------------------------------------------------------- constructors
 
     /**
-     * Construct the abstract disk cache, create event queues and purgatory.
+     * Construct the abstract disk cache, create event queues and purgatory. Child classes should
+     * set the alive flag to true after they are initialized.
      * <p>
      * @param attr
      */
     public AbstractDiskCache( IDiskCacheAttributes attr )
     {
-        this.dcattr = attr;
+        this.diskCacheAttributes = attr;
 
         this.cacheName = attr.getCacheName();
 
         // create queue
         CacheEventQueueFactory fact = new CacheEventQueueFactory();
         this.cacheEventQueue = fact.createCacheEventQueue( new MyCacheListener(), CacheInfo.listenerId, cacheName,
-                                                           dcattr.getEventQueuePoolName(), dcattr.getEventQueueType() );
+                                                           diskCacheAttributes.getEventQueuePoolName(),
+                                                           diskCacheAttributes.getEventQueueType() );
 
         // create purgatory
         initPurgatory();
@@ -146,9 +151,9 @@
             {
                 synchronized ( purgatory )
                 {
-                    if ( dcattr.getMaxPurgatorySize() >= 0 )
+                    if ( diskCacheAttributes.getMaxPurgatorySize() >= 0 )
                     {
-                        purgatory = new LRUMapJCS( dcattr.getMaxPurgatorySize() );
+                        purgatory = new LRUMapJCS( diskCacheAttributes.getMaxPurgatorySize() );
                     }
                     else
                     {
@@ -158,9 +163,9 @@
             }
             else
             {
-                if ( dcattr.getMaxPurgatorySize() >= 0 )
+                if ( diskCacheAttributes.getMaxPurgatorySize() >= 0 )
                 {
-                    purgatory = new LRUMapJCS( dcattr.getMaxPurgatorySize() );
+                    purgatory = new LRUMapJCS( diskCacheAttributes.getMaxPurgatorySize() );
                 }
                 else
                 {
@@ -240,6 +245,10 @@
 
         if ( !alive )
         {
+            if ( log.isDebugEnabled() )
+            {
+                log.debug( "get was called, but the disk cache is not alive." );
+            }
             return null;
         }
 
@@ -430,7 +439,7 @@
     public final void removeAll()
         throws IOException
     {
-        if ( this.dcattr.isAllowRemoveAll() )
+        if ( this.diskCacheAttributes.isAllowRemoveAll() )
         {
             // Replace purgatory with a new empty hashtable
             initPurgatory();
@@ -492,7 +501,7 @@
         // wait up to 60 seconds for dispose and then quit if not done.
         try
         {
-            t.join( this.dcattr.getShutdownSpoolTimeLimit() * 1000 );
+            t.join( this.diskCacheAttributes.getShutdownSpoolTimeLimit() * 1000 );
         }
         catch ( InterruptedException ex )
         {
@@ -763,10 +772,10 @@
 
     /**
      * Before the event logging layer, the subclasses implemented the do* methods. Now the do*
-     * methods call the *WithEventLogging method on the super. The *WithEventLogging methods call the
-     * abstract process* methods. The children implement the process methods.
+     * methods call the *WithEventLogging method on the super. The *WithEventLogging methods call
+     * the abstract process* methods. The children implement the process methods.
      * <p>
-     * ex.  doGet calls getWithEventLogging, which calls processGet
+     * ex. doGet calls getWithEventLogging, which calls processGet
      */
 
     /**

Modified: jakarta/jcs/trunk/src/java/org/apache/jcs/auxiliary/disk/AbstractDiskCacheAttributes.java
URL: http://svn.apache.org/viewvc/jakarta/jcs/trunk/src/java/org/apache/jcs/auxiliary/disk/AbstractDiskCacheAttributes.java?rev=783765&r1=783764&r2=783765&view=diff
==============================================================================
--- jakarta/jcs/trunk/src/java/org/apache/jcs/auxiliary/disk/AbstractDiskCacheAttributes.java (original)
+++ jakarta/jcs/trunk/src/java/org/apache/jcs/auxiliary/disk/AbstractDiskCacheAttributes.java Thu Jun 11 13:46:34 2009
@@ -160,9 +160,10 @@
     {
         StringBuffer str = new StringBuffer();
         str.append( "AbstractDiskCacheAttributes " );
-        str.append( "\n diskPath = " + diskPath );
-        str.append( "\n maxPurgatorySize   = " + maxPurgatorySize );
-        str.append( "\n allowRemoveAll   = " + allowRemoveAll );
+        str.append( "\n diskPath = " + getDiskPath() );
+        str.append( "\n maxPurgatorySize   = " + getMaxPurgatorySize() );
+        str.append( "\n allowRemoveAll   = " + isAllowRemoveAll() );
+        str.append( "\n ShutdownSpoolTimeLimit   = " + getShutdownSpoolTimeLimit() );
         return str.toString();
     }
 }

Modified: jakarta/jcs/trunk/src/java/org/apache/jcs/auxiliary/disk/PurgatoryElement.java
URL: http://svn.apache.org/viewvc/jakarta/jcs/trunk/src/java/org/apache/jcs/auxiliary/disk/PurgatoryElement.java?rev=783765&r1=783764&r2=783765&view=diff
==============================================================================
--- jakarta/jcs/trunk/src/java/org/apache/jcs/auxiliary/disk/PurgatoryElement.java (original)
+++ jakarta/jcs/trunk/src/java/org/apache/jcs/auxiliary/disk/PurgatoryElement.java Thu Jun 11 13:46:34 2009
@@ -128,4 +128,21 @@
     {
         cacheElement.setElementAttributes( attr );
     }
+    
+    /**
+     * @return debug string
+     */
+    public String toString()
+    {
+        StringBuffer buf = new StringBuffer();
+        buf.append( "[PurgatoryElement: " );
+        buf.append( " isSpoolable = " + isSpoolable() );
+        buf.append( " CacheElement = " + getCacheElement() );
+        buf.append( " CacheName = " + getCacheName() );
+        buf.append( " Key = " + getKey() );
+        buf.append( " Value = " + getVal() );
+        buf.append( " ElementAttributes = " + getElementAttributes() );
+        buf.append( "]" );
+        return buf.toString();
+    }    
 }

Modified: jakarta/jcs/trunk/src/java/org/apache/jcs/auxiliary/disk/indexed/IndexedDiskElementDescriptor.java
URL: http://svn.apache.org/viewvc/jakarta/jcs/trunk/src/java/org/apache/jcs/auxiliary/disk/indexed/IndexedDiskElementDescriptor.java?rev=783765&r1=783764&r2=783765&view=diff
==============================================================================
--- jakarta/jcs/trunk/src/java/org/apache/jcs/auxiliary/disk/indexed/IndexedDiskElementDescriptor.java (original)
+++ jakarta/jcs/trunk/src/java/org/apache/jcs/auxiliary/disk/indexed/IndexedDiskElementDescriptor.java Thu Jun 11 13:46:34 2009
@@ -38,24 +38,6 @@
     public int len;
 
     /**
-     * Set the offset (i.e. position, and the size of the element)
-     * <p>
-     * @param pos
-     * @param data
-     */
-    public void init( long pos, byte[] data )
-    {
-        this.pos = pos;
-        this.len = data.length;
-    }
-
-    /** Constructor for the DiskElementDescriptor object */
-    public IndexedDiskElementDescriptor()
-    {
-        super();
-    }
-
-    /**
      * Constructs a usable disk element descriptor.
      * <p>
      * @param pos

Modified: jakarta/jcs/trunk/src/java/org/apache/jcs/engine/CacheEventQueueFactory.java
URL: http://svn.apache.org/viewvc/jakarta/jcs/trunk/src/java/org/apache/jcs/engine/CacheEventQueueFactory.java?rev=783765&r1=783764&r2=783765&view=diff
==============================================================================
--- jakarta/jcs/trunk/src/java/org/apache/jcs/engine/CacheEventQueueFactory.java (original)
+++ jakarta/jcs/trunk/src/java/org/apache/jcs/engine/CacheEventQueueFactory.java Thu Jun 11 13:46:34 2009
@@ -74,7 +74,7 @@
         }
 
         ICacheEventQueue eventQueue = null;
-        if ( ICacheEventQueue.SINGLE_QUEUE_TYPE.equalsIgnoreCase( poolType ) )
+        if ( poolType == null || ICacheEventQueue.SINGLE_QUEUE_TYPE.equalsIgnoreCase( poolType ) )
         {
             eventQueue = new CacheEventQueue( listener, listenerId, cacheName, maxFailure, waitBeforeRetry );
         }

Modified: jakarta/jcs/trunk/src/java/org/apache/jcs/engine/control/CompositeCacheManager.java
URL: http://svn.apache.org/viewvc/jakarta/jcs/trunk/src/java/org/apache/jcs/engine/control/CompositeCacheManager.java?rev=783765&r1=783764&r2=783765&view=diff
==============================================================================
--- jakarta/jcs/trunk/src/java/org/apache/jcs/engine/control/CompositeCacheManager.java (original)
+++ jakarta/jcs/trunk/src/java/org/apache/jcs/engine/control/CompositeCacheManager.java Thu Jun 11 13:46:34 2009
@@ -114,6 +114,7 @@
      * Gets the CacheHub instance. For backward compatibility, if this creates the instance it will
      * attempt to configure it with the default configuration. If you want to configure from your
      * own source, use {@link #getUnconfiguredInstance}and then call {@link #configure}
+     * <p>
      * @return CompositeCacheManager
      */
     public static synchronized CompositeCacheManager getInstance()
@@ -134,6 +135,7 @@
 
     /**
      * Initializes the cache manager using the props file for the given name.
+     * <p>
      * @param propsFilename
      * @return CompositeCacheManager configured from the give propsFileName
      */
@@ -182,6 +184,7 @@
     /**
      * Simple factory method, must override in subclasses so getInstance creates / returns the
      * correct object.
+     * <p>
      * @return CompositeCacheManager
      */
     protected static CompositeCacheManager createInstance()

Modified: jakarta/jcs/trunk/src/java/org/apache/jcs/engine/memory/AbstractMemoryCache.java
URL: http://svn.apache.org/viewvc/jakarta/jcs/trunk/src/java/org/apache/jcs/engine/memory/AbstractMemoryCache.java?rev=783765&r1=783764&r2=783765&view=diff
==============================================================================
--- jakarta/jcs/trunk/src/java/org/apache/jcs/engine/memory/AbstractMemoryCache.java (original)
+++ jakarta/jcs/trunk/src/java/org/apache/jcs/engine/memory/AbstractMemoryCache.java Thu Jun 11 13:46:34 2009
@@ -107,7 +107,6 @@
             }
             shrinkerDaemon.executePeriodically( cattr.getShrinkerIntervalSeconds() * 1000, new ShrinkerThread( this ),
                                                 false );
-
         }
     }
 

Added: jakarta/jcs/trunk/src/java/org/apache/jcs/engine/memory/lru/LHMLRUMemoryCache.java
URL: http://svn.apache.org/viewvc/jakarta/jcs/trunk/src/java/org/apache/jcs/engine/memory/lru/LHMLRUMemoryCache.java?rev=783765&view=auto
==============================================================================
--- jakarta/jcs/trunk/src/java/org/apache/jcs/engine/memory/lru/LHMLRUMemoryCache.java (added)
+++ jakarta/jcs/trunk/src/java/org/apache/jcs/engine/memory/lru/LHMLRUMemoryCache.java Thu Jun 11 13:46:34 2009
@@ -0,0 +1,390 @@
+package org.apache.jcs.engine.memory.lru;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import java.io.IOException;
+import java.io.Serializable;
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.Iterator;
+import java.util.Map;
+
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+import org.apache.jcs.engine.CacheConstants;
+import org.apache.jcs.engine.CacheElement;
+import org.apache.jcs.engine.behavior.ICacheElement;
+import org.apache.jcs.engine.control.CompositeCache;
+import org.apache.jcs.engine.control.group.GroupAttrName;
+import org.apache.jcs.engine.control.group.GroupId;
+import org.apache.jcs.engine.memory.AbstractMemoryCache;
+import org.apache.jcs.engine.memory.util.MemoryElementDescriptor;
+import org.apache.jcs.engine.stats.StatElement;
+import org.apache.jcs.engine.stats.Stats;
+import org.apache.jcs.engine.stats.behavior.IStatElement;
+import org.apache.jcs.engine.stats.behavior.IStats;
+
+/**
+ * This is a test memory manager using the jdk1.4 LinkedHashMap. There may be some thread safety
+ * issues.
+ */
+public class LHMLRUMemoryCache
+    extends AbstractMemoryCache
+{
+    /** Don't change */
+    private static final long serialVersionUID = 6403738094136424101L;
+
+    /** The Logger. */
+    private final static Log log = LogFactory.getLog( LRUMemoryCache.class );
+
+    /** number of hits */
+    protected int hitCnt = 0;
+
+    /** number of misses */
+    protected int missCnt = 0;
+
+    /** number of puts */
+    protected int putCnt = 0;
+
+    /**
+     * For post reflection creation initialization
+     * <p>
+     * @param hub
+     */
+    public synchronized void initialize( CompositeCache hub )
+    {
+        super.initialize( hub );
+        log.info( "initialized LHMLRUMemoryCache for " + cacheName );
+    }
+
+    /**
+     * Returns a synchronized LHMSpooler
+     * <p>
+     * @return Collections.synchronizedMap( new LHMSpooler() )
+     */
+    public Map createMap()
+    {
+        return Collections.synchronizedMap( new LHMSpooler() );
+    }
+
+    /**
+     * Puts an item to the cache.
+     * <p>
+     * @param ce Description of the Parameter
+     * @exception IOException
+     */
+    public void update( ICacheElement ce )
+        throws IOException
+    {
+        putCnt++;
+        ce.getElementAttributes().setLastAccessTimeNow();
+        map.put( ce.getKey(), ce );
+    }
+
+    /**
+     * Get an item from the cache without affecting its last access time or position. There is no
+     * way to do this with the LinkedHashMap!
+     * <p>
+     * @param key Identifies item to find
+     * @return Element matching key if found, or null
+     * @exception IOException
+     */
+    public ICacheElement getQuiet( Serializable key )
+        throws IOException
+    {
+        return (ICacheElement) map.get( key );
+    }
+
+    /**
+     * Get an item from the cache
+     * <p>
+     * @param key Identifies item to find
+     * @return ICacheElement if found, else null
+     * @exception IOException
+     */
+    public synchronized ICacheElement get( Serializable key )
+        throws IOException
+    {
+        ICacheElement ce = null;
+
+        if ( log.isDebugEnabled() )
+        {
+            log.debug( "getting item from cache " + cacheName + " for key " + key );
+        }
+
+        ce = (ICacheElement) map.get( key );
+
+        if ( ce != null )
+        {
+            hitCnt++;
+            ce.getElementAttributes().setLastAccessTimeNow();
+            if ( log.isDebugEnabled() )
+            {
+                log.debug( cacheName + ": LRUMemoryCache hit for " + key );
+            }
+        }
+        else
+        {
+            missCnt++;
+            log.debug( cacheName + ": LRUMemoryCache miss for " + key );
+        }
+
+        return ce;
+    }
+
+    /**
+     * Removes an item from the cache. This method handles hierarchical removal. If the key is a
+     * String and ends with the CacheConstants.NAME_COMPONENT_DELIMITER, then all items with keys
+     * starting with the argument String will be removed.
+     * <p>
+     * @param key
+     * @return true if removed
+     * @exception IOException
+     */
+    public synchronized boolean remove( Serializable key )
+        throws IOException
+    {
+        if ( log.isDebugEnabled() )
+        {
+            log.debug( "removing item for key: " + key );
+        }
+
+        boolean removed = false;
+
+        // handle partial removal
+        if ( key instanceof String && ( (String) key ).endsWith( CacheConstants.NAME_COMPONENT_DELIMITER ) )
+        {
+            // remove all keys of the same name hierarchy.
+            synchronized ( map )
+            {
+                for ( Iterator itr = map.entrySet().iterator(); itr.hasNext(); )
+                {
+                    Map.Entry entry = (Map.Entry) itr.next();
+                    Object k = entry.getKey();
+
+                    if ( k instanceof String && ( (String) k ).startsWith( key.toString() ) )
+                    {
+                        itr.remove();
+                        removed = true;
+                    }
+                }
+            }
+        }
+        else if ( key instanceof GroupId )
+        {
+            // remove all keys of the same name hierarchy.
+            synchronized ( map )
+            {
+                for ( Iterator itr = map.entrySet().iterator(); itr.hasNext(); )
+                {
+                    Map.Entry entry = (Map.Entry) itr.next();
+                    Object k = entry.getKey();
+
+                    if ( k instanceof GroupAttrName && ( (GroupAttrName) k ).groupId.equals( key ) )
+                    {
+                        itr.remove();
+                        removed = true;
+                    }
+                }
+            }
+        }
+        else
+        {
+            // remove single item.
+            ICacheElement ce = (ICacheElement) map.remove( key );
+            if ( ce != null )
+            {
+                removed = true;
+            }
+        }
+
+        return removed;
+    }
+
+    /**
+     * Get an Array of the keys for all elements in the memory cache
+     * <p>
+     * @return An Object[]
+     */
+    public Object[] getKeyArray()
+    {
+        // need a better locking strategy here.
+        synchronized ( this )
+        {
+            // may need to lock to map here?
+            return map.keySet().toArray();
+        }
+    }
+
+    /**
+     * This returns semi-structured information on the memory cache, such as the size, put count,
+     * hit count, and miss count.
+     * <p>
+     * @return IStats
+     */
+    public synchronized IStats getStatistics()
+    {
+        IStats stats = new Stats();
+        stats.setTypeName( "LHMLRU Memory Cache" );
+
+        ArrayList elems = new ArrayList();
+
+        IStatElement se = null;
+
+        se = new StatElement();
+        se.setName( "Map Size" );
+        se.setData( "" + map.size() );
+        elems.add( se );
+
+        se = new StatElement();
+        se.setName( "Put Count" );
+        se.setData( "" + putCnt );
+        elems.add( se );
+
+        se = new StatElement();
+        se.setName( "Hit Count" );
+        se.setData( "" + hitCnt );
+        elems.add( se );
+
+        se = new StatElement();
+        se.setName( "Miss Count" );
+        se.setData( "" + missCnt );
+        elems.add( se );
+
+        // get an array and put them in the Stats object
+        IStatElement[] ses = (IStatElement[]) elems.toArray( new StatElement[0] );
+        stats.setStatElements( ses );
+
+        // int rate = ((hitCnt + missCnt) * 100) / (hitCnt * 100) * 100;
+        // buf.append("\n Hit Rate = " + rate + " %" );
+
+        return stats;
+    }
+
+    // ---------------------------------------------------------- debug methods
+
+    /**
+     * Dump the cache map for debugging.
+     */
+    public void dumpMap()
+    {
+        if ( log.isDebugEnabled() )
+        {
+            log.debug( "dumpingMap" );
+
+            for ( Iterator itr = map.entrySet().iterator(); itr.hasNext(); )
+            {
+                Map.Entry e = (Map.Entry) itr.next();
+                MemoryElementDescriptor me = (MemoryElementDescriptor) e.getValue();
+                log.debug( "dumpMap> key=" + e.getKey() + ", val=" + me.ce.getVal() );
+            }
+        }
+    }
+
+    /**
+     * Dump the cache entries from first to last for debugging.
+     */
+    public void dumpCacheEntries()
+    {
+        dumpMap();
+    }
+
+    /**
+     * This can't be implemented.
+     * <p>
+     * @param numberToFree 
+     * @return 0 
+     * @throws IOException 
+     */
+    public int freeElements( int numberToFree )
+        throws IOException
+    {
+        // can't be implemented using the LHM
+        return 0;
+    }
+
+    // ---------------------------------------------------------- extended map
+
+    /**
+     * Implementation of removeEldestEntry in LinkedHashMap
+     */
+    public class LHMSpooler
+        extends java.util.LinkedHashMap
+    {
+        /** Don't change. */
+        private static final long serialVersionUID = -1255907868906762484L;
+
+        /**
+         * Initialize to a small size--for now, 1/2 of max 3rd variable "true" indicates that it
+         * should be access and not time governed. This could be configurable.
+         */
+        public LHMSpooler()
+        {
+            super( (int) ( cache.getCacheAttributes().getMaxObjects() * .5 ), .75F, true );
+        }
+
+        /**
+         * Remove eldest. Automatically called by LinkedHashMap.
+         * <p>
+         * @param eldest
+         * @return true if removed
+         */
+        protected boolean removeEldestEntry( Map.Entry eldest )
+        {
+            CacheElement element = (CacheElement) eldest.getValue();
+
+            if ( size() <= cache.getCacheAttributes().getMaxObjects() )
+            {
+                return false;
+            }
+            else
+            {
+
+                if ( log.isDebugEnabled() )
+                {
+                    log.debug( "LHMLRU max size: " + cache.getCacheAttributes().getMaxObjects()
+                        + ".  Spooling element, key: " + element.getKey() );
+                }
+                spoolToDisk( element );
+
+                if ( log.isDebugEnabled() )
+                {
+                    log.debug( "LHMLRU size: " + map.size() );
+                }
+            }
+            return true;
+        }
+
+        /**
+         * Puts the element in the DiskStore
+         * <p>
+         * @param element The CacheElement
+         */
+        private void spoolToDisk( CacheElement element )
+        {
+            cache.spoolToDisk( element );
+
+            if ( log.isDebugEnabled() )
+            {
+                log.debug( cache.getCacheName() + "Spoolled element to disk: " + element.getKey() );
+            }
+        }
+    }
+}

Modified: jakarta/jcs/trunk/src/java/org/apache/jcs/utils/struct/LRUMap.java
URL: http://svn.apache.org/viewvc/jakarta/jcs/trunk/src/java/org/apache/jcs/utils/struct/LRUMap.java?rev=783765&r1=783764&r2=783765&view=diff
==============================================================================
--- jakarta/jcs/trunk/src/java/org/apache/jcs/utils/struct/LRUMap.java (original)
+++ jakarta/jcs/trunk/src/java/org/apache/jcs/utils/struct/LRUMap.java Thu Jun 11 13:46:34 2009
@@ -661,4 +661,12 @@
         // TODO fix this, it needs to return the keys inside the wrappers.
         return map.keySet();
     }
+
+    /**
+     * @return the max objects size.
+     */
+    public int getMaxObjects()
+    {
+        return maxObjects;
+    }
 }

Added: jakarta/jcs/trunk/src/test-conf/TestLHMLRUCache.ccf
URL: http://svn.apache.org/viewvc/jakarta/jcs/trunk/src/test-conf/TestLHMLRUCache.ccf?rev=783765&view=auto
==============================================================================
--- jakarta/jcs/trunk/src/test-conf/TestLHMLRUCache.ccf (added)
+++ jakarta/jcs/trunk/src/test-conf/TestLHMLRUCache.ccf Thu Jun 11 13:46:34 2009
@@ -0,0 +1,23 @@
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements.  See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership.  The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License.  You may obtain a copy of the License at
+#
+#   http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied.  See the License for the
+# specific language governing permissions and limitations
+# under the License.
+# Cache configuration for the 'TestDiskCache' test. The memory cache has a
+# a maximum of 100 objects, so objects should get pushed into the disk cache
+
+jcs.default=
+jcs.default.cacheattributes=org.apache.jcs.engine.CompositeCacheAttributes
+jcs.default.cacheattributes.MaxObjects=100
+jcs.default.cacheattributes.MemoryCacheName=org.apache.jcs.engine.memory.lru.LHMLRUMemoryCache
\ No newline at end of file

Added: jakarta/jcs/trunk/src/test/org/apache/jcs/TestLogConfigurationUtil.java
URL: http://svn.apache.org/viewvc/jakarta/jcs/trunk/src/test/org/apache/jcs/TestLogConfigurationUtil.java?rev=783765&view=auto
==============================================================================
--- jakarta/jcs/trunk/src/test/org/apache/jcs/TestLogConfigurationUtil.java (added)
+++ jakarta/jcs/trunk/src/test/org/apache/jcs/TestLogConfigurationUtil.java Thu Jun 11 13:46:34 2009
@@ -0,0 +1,27 @@
+package org.apache.jcs;
+
+import java.io.StringWriter;
+
+import org.apache.log4j.Level;
+import org.apache.log4j.Logger;
+import org.apache.log4j.PatternLayout;
+import org.apache.log4j.WriterAppender;
+
+/** Utility for testing log messages. */
+public class TestLogConfigurationUtil
+{
+    /**
+     * Configures a logger for the given name. This allows us to check the log output.
+     * <p>
+     * @param stringWriter string writer
+     * @param loggerName logger name
+     */
+    public static void configureLogger( StringWriter stringWriter, String loggerName )
+    {
+        Logger logger = Logger.getLogger( loggerName );
+        WriterAppender appender = new WriterAppender( new PatternLayout(), stringWriter );
+
+        logger.addAppender( appender );
+        logger.setLevel( Level.DEBUG );
+    }  
+}

Added: jakarta/jcs/trunk/src/test/org/apache/jcs/auxiliary/disk/AbstractDiskCacheUnitTest.java
URL: http://svn.apache.org/viewvc/jakarta/jcs/trunk/src/test/org/apache/jcs/auxiliary/disk/AbstractDiskCacheUnitTest.java?rev=783765&view=auto
==============================================================================
--- jakarta/jcs/trunk/src/test/org/apache/jcs/auxiliary/disk/AbstractDiskCacheUnitTest.java (added)
+++ jakarta/jcs/trunk/src/test/org/apache/jcs/auxiliary/disk/AbstractDiskCacheUnitTest.java Thu Jun 11 13:46:34 2009
@@ -0,0 +1,274 @@
+package org.apache.jcs.auxiliary.disk;
+
+import java.io.IOException;
+import java.io.Serializable;
+import java.io.StringWriter;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.Map;
+import java.util.Set;
+
+import junit.framework.TestCase;
+
+import org.apache.jcs.TestLogConfigurationUtil;
+import org.apache.jcs.auxiliary.AuxiliaryCacheAttributes;
+import org.apache.jcs.auxiliary.disk.behavior.IDiskCacheAttributes;
+import org.apache.jcs.auxiliary.disk.indexed.IndexedDiskCacheAttributes;
+import org.apache.jcs.engine.CacheConstants;
+import org.apache.jcs.engine.CacheElement;
+import org.apache.jcs.engine.ElementAttributes;
+import org.apache.jcs.engine.behavior.ICacheElement;
+import org.apache.jcs.engine.behavior.IElementAttributes;
+
+/** Tests for the abstract disk cache. It's largely tested by actual instances. */
+public class AbstractDiskCacheUnitTest
+    extends TestCase
+{
+    /**
+     * Verify that update and get work.
+     * <p>
+     * @throws IOException
+     */
+    public void testUpdateGet_allowed()
+        throws IOException
+    {
+        // SETUP
+        String cacheName = "testUpdateGet_allowed";
+        IDiskCacheAttributes diskCacheAttributes = new IndexedDiskCacheAttributes();
+        diskCacheAttributes.setCacheName( cacheName );
+
+        AbstractDiskCacheTestInstance diskCache = new AbstractDiskCacheTestInstance( diskCacheAttributes );
+
+        String key = "myKey";
+        String value = "myValue";
+        IElementAttributes elementAttributes = new ElementAttributes();
+        ICacheElement cacheElement = new CacheElement( cacheName, key, value, elementAttributes );
+
+        diskCache.update( cacheElement );
+
+        // DO WORK
+        ICacheElement result = diskCache.get( key );
+
+        // VERIFY        
+        //System.out.println( diskCache.getStats() );
+        assertNotNull( "Item should be in the map.", result );
+    }
+    
+    /**
+     * Verify that alive is set to false..
+     * <p>
+     * @throws IOException
+     */
+    public void testDispose()
+        throws IOException
+    {
+        // SETUP
+        String cacheName = "testDispose";
+        IDiskCacheAttributes diskCacheAttributes = new IndexedDiskCacheAttributes();
+        diskCacheAttributes.setCacheName( cacheName );
+
+        AbstractDiskCacheTestInstance diskCache = new AbstractDiskCacheTestInstance( diskCacheAttributes );
+
+        String key = "myKey";
+        String value = "myValue";
+        IElementAttributes elementAttributes = new ElementAttributes();
+        ICacheElement cacheElement = new CacheElement( cacheName, key, value, elementAttributes );
+
+        diskCache.update( cacheElement );
+
+        // DO WORK
+        diskCache.dispose();
+
+        // VERIFY        
+        assertFalse( "disk cache should not be alive.", diskCache.alive );
+        assertEquals( "Status should be disposed", CacheConstants.STATUS_DISPOSED, diskCache.getStatus() );
+    }
+
+    /**
+     * Verify that removeAll is prohibited.
+     * <p>
+     * @throws IOException
+     */
+    public void testRemoveAll_notAllowed()
+        throws IOException
+    {
+        // SETUP
+        StringWriter stringWriter = new StringWriter();
+        TestLogConfigurationUtil.configureLogger( stringWriter, AbstractDiskCache.class.getName() );
+
+        IDiskCacheAttributes diskCacheAttributes = new IndexedDiskCacheAttributes();
+        diskCacheAttributes.setAllowRemoveAll( false );
+
+        AbstractDiskCacheTestInstance diskCache = new AbstractDiskCacheTestInstance( diskCacheAttributes );
+
+        String cacheName = "testRemoveAll_notAllowed";
+        String key = "myKey";
+        String value = "myValue";
+        IElementAttributes elementAttributes = new ElementAttributes();
+        ICacheElement cacheElement = new CacheElement( cacheName, key, value, elementAttributes );
+
+        diskCache.update( cacheElement );
+
+        // DO WORK
+        diskCache.removeAll();
+        String result = stringWriter.toString();
+
+        // VERIFY        
+        assertTrue( "Should say not allowed.", result.indexOf( "set to false" ) != -1 );
+        assertNotNull( "Item should be in the map.", diskCache.get( key ) );
+    }
+
+    /**
+     * Verify that removeAll is allowed.
+     * <p>
+     * @throws IOException
+     */
+    public void testRemoveAll_allowed()
+        throws IOException
+    {
+        // SETUP
+        IDiskCacheAttributes diskCacheAttributes = new IndexedDiskCacheAttributes();
+        diskCacheAttributes.setAllowRemoveAll( true );
+
+        AbstractDiskCacheTestInstance diskCache = new AbstractDiskCacheTestInstance( diskCacheAttributes );
+
+        String cacheName = "testRemoveAll_allowed";
+        String key = "myKey";
+        String value = "myValue";
+        IElementAttributes elementAttributes = new ElementAttributes();
+        ICacheElement cacheElement = new CacheElement( cacheName, key, value, elementAttributes );
+
+        diskCache.update( cacheElement );
+
+        // DO WORK
+        diskCache.removeAll();
+
+        // VERIFY        
+        assertNull( "Item should not be in the map.", diskCache.get( key ) );
+    }
+
+    /** Concrete, testable instance. */
+    class AbstractDiskCacheTestInstance
+        extends AbstractDiskCache
+    {
+        /** Internal map */
+        protected Map map = new HashMap();
+
+        /** used by the abstract aux class */
+        protected IDiskCacheAttributes diskCacheAttributes;
+
+        /**
+         * Creates the disk cache.
+         * <p>
+         * @param attr
+         */
+        public AbstractDiskCacheTestInstance( IDiskCacheAttributes attr )
+        {
+            super( attr );
+            diskCacheAttributes = attr;
+            super.alive = true;
+        }
+
+        /** Nothing. */
+        private static final long serialVersionUID = 1L;
+
+        /**
+         * The location on disk
+         * <p>
+         * @return "memory"
+         */
+        protected String getDiskLocation()
+        {
+            return "memory";
+        }
+
+        /**
+         * @param groupName
+         * @return Collections.EMPTY_SET
+         */
+        public Set getGroupKeys( String groupName )
+        {
+            return Collections.EMPTY_SET;
+        }
+
+        /**
+         * @return map.size()
+         */
+        public int getSize()
+        {
+            return map.size();
+        }
+
+        /**
+         * @throws IOException
+         */
+        protected void processDispose()
+            throws IOException
+        {
+            //System.out.println( "processDispose" );      
+        }
+
+        /**
+         * @param key
+         * @return ICacheElement
+         * @throws IOException
+         */
+        protected ICacheElement processGet( Serializable key )
+            throws IOException
+        {
+            //System.out.println( "processGet: " + key );
+            return (ICacheElement) map.get( key );
+        }
+
+        /**
+         * @param pattern
+         * @return Collections.EMPTY_MAP
+         * @throws IOException
+         */
+        protected Map processGetMatching( String pattern )
+            throws IOException
+        {
+            return Collections.EMPTY_MAP;
+        }
+
+        /**
+         * @param key
+         * @return false
+         * @throws IOException
+         */
+        protected boolean processRemove( Serializable key )
+            throws IOException
+        {
+            return map.remove( key ) != null;
+        }
+
+        /**
+         * @throws IOException
+         */
+        protected void processRemoveAll()
+            throws IOException
+        {
+            //System.out.println( "processRemoveAll" );
+            map.clear();
+        }
+
+        /**
+         * @param cacheElement
+         * @throws IOException
+         */
+        protected void processUpdate( ICacheElement cacheElement )
+            throws IOException
+        {
+            //System.out.println( "processUpdate: " + cacheElement );
+            map.put( cacheElement.getKey(), cacheElement );
+        }
+
+        /**
+         * @return null
+         */
+        public AuxiliaryCacheAttributes getAuxiliaryCacheAttributes()
+        {
+            return diskCacheAttributes;
+        }
+    }
+}

Added: jakarta/jcs/trunk/src/test/org/apache/jcs/auxiliary/disk/LRUMapJCSUnitTest.java
URL: http://svn.apache.org/viewvc/jakarta/jcs/trunk/src/test/org/apache/jcs/auxiliary/disk/LRUMapJCSUnitTest.java?rev=783765&view=auto
==============================================================================
--- jakarta/jcs/trunk/src/test/org/apache/jcs/auxiliary/disk/LRUMapJCSUnitTest.java (added)
+++ jakarta/jcs/trunk/src/test/org/apache/jcs/auxiliary/disk/LRUMapJCSUnitTest.java Thu Jun 11 13:46:34 2009
@@ -0,0 +1,58 @@
+package org.apache.jcs.auxiliary.disk;
+
+import java.io.StringWriter;
+
+import junit.framework.TestCase;
+
+import org.apache.jcs.TestLogConfigurationUtil;
+
+/** Unit tests for the LRUMapJCS implementation. */
+public class LRUMapJCSUnitTest
+    extends TestCase
+{
+    /** Verify that we default to unlimited */
+    public void testDefault()
+    {
+        // SETUP
+
+        // DO WORK
+        LRUMapJCS map = new LRUMapJCS();
+
+        // VERIFY
+        assertEquals( "Should be unlimted", -1, map.getMaxObjects() );
+    }
+
+    /** Verify that we default to unlimited */
+    public void testLimited()
+    {
+        // SETUP
+        int expected = 100;
+
+        // DO WORK
+        LRUMapJCS map = new LRUMapJCS( expected );
+
+        // VERIFY
+        assertEquals( "Should be expected", expected, map.getMaxObjects() );
+    }
+
+    /** Verify that the log message. */
+    public void testProcessRemovedLRU()
+    {
+        // SETUP
+        StringWriter stringWriter = new StringWriter();
+        TestLogConfigurationUtil.configureLogger( stringWriter, LRUMapJCS.class.getName() );
+
+        LRUMapJCS map = new LRUMapJCS();
+
+        String key = "myKey";
+        String value = "myValue";
+
+        // DO WORK
+        map.processRemovedLRU( key, value );
+        String result = stringWriter.toString();
+
+        // VERIFY
+        assertTrue( "Debug log should contain the key,", result.indexOf( key ) != -1 );
+        assertTrue( "Debug log should contain the value,", result.indexOf( value ) != -1 );
+    }
+}

Added: jakarta/jcs/trunk/src/test/org/apache/jcs/auxiliary/disk/PurgatoryElementUnitTest.java
URL: http://svn.apache.org/viewvc/jakarta/jcs/trunk/src/test/org/apache/jcs/auxiliary/disk/PurgatoryElementUnitTest.java?rev=783765&view=auto
==============================================================================
--- jakarta/jcs/trunk/src/test/org/apache/jcs/auxiliary/disk/PurgatoryElementUnitTest.java (added)
+++ jakarta/jcs/trunk/src/test/org/apache/jcs/auxiliary/disk/PurgatoryElementUnitTest.java Thu Jun 11 13:46:34 2009
@@ -0,0 +1,72 @@
+package org.apache.jcs.auxiliary.disk;
+
+import junit.framework.TestCase;
+
+import org.apache.jcs.engine.CacheElement;
+import org.apache.jcs.engine.ElementAttributes;
+import org.apache.jcs.engine.behavior.ICacheElement;
+import org.apache.jcs.engine.behavior.IElementAttributes;
+
+/** Simple unit tests for the Purgatory Element. */
+public class PurgatoryElementUnitTest
+    extends TestCase
+{
+    /** Verify basic data */
+    public void testSpoolable_normal()
+    {
+        // SETUP
+        String cacheName = "myCacheName";
+        String key = "myKey";
+        String value = "myValue";
+        IElementAttributes elementAttributes = new ElementAttributes();
+        ICacheElement cacheElement = new CacheElement( cacheName, key, value, elementAttributes );
+        PurgatoryElement purgatoryElement = new PurgatoryElement( cacheElement );
+        purgatoryElement.setSpoolable( false );
+
+        // DO WORK
+        boolean result = purgatoryElement.isSpoolable();
+
+        // VERIFY
+        assertFalse( "Should not be spoolable.", result );
+    }
+
+    /** Verify basic data */
+    public void testElementAttributes_normal()
+    {
+        // SETUP
+        String cacheName = "myCacheName";
+        String key = "myKey";
+        String value = "myValue";
+        IElementAttributes elementAttributes = new ElementAttributes();
+
+        ICacheElement cacheElement = new CacheElement( cacheName, key, value );
+        PurgatoryElement purgatoryElement = new PurgatoryElement( cacheElement );
+        purgatoryElement.setElementAttributes( elementAttributes );
+
+        // DO WORK
+        IElementAttributes result = cacheElement.getElementAttributes();
+
+        // VERIFY
+        assertEquals( "Should have set the attributes on the element", elementAttributes, result );
+    }
+
+    /** Verify basic data */
+    public void testToString_normal()
+    {
+        // SETUP
+        String cacheName = "myCacheName";
+        String key = "myKey";
+        String value = "myValue";
+        IElementAttributes elementAttributes = new ElementAttributes();
+        ICacheElement cacheElement = new CacheElement( cacheName, key, value, elementAttributes );
+        PurgatoryElement purgatoryElement = new PurgatoryElement( cacheElement );
+
+        // DO WORK
+        String result = purgatoryElement.toString();
+
+        // VERIFY
+        assertTrue( "Should have the cacheName.", result.indexOf( cacheName ) != -1 );
+        assertTrue( "Should have the key.", result.indexOf( key ) != -1 );
+        assertTrue( "Should have the value.", result.indexOf( value ) != -1 );
+    }
+}

Added: jakarta/jcs/trunk/src/test/org/apache/jcs/engine/memory/lru/LHMLRUMemoryCacheConcurrentUnitTest.java
URL: http://svn.apache.org/viewvc/jakarta/jcs/trunk/src/test/org/apache/jcs/engine/memory/lru/LHMLRUMemoryCacheConcurrentUnitTest.java?rev=783765&view=auto
==============================================================================
--- jakarta/jcs/trunk/src/test/org/apache/jcs/engine/memory/lru/LHMLRUMemoryCacheConcurrentUnitTest.java (added)
+++ jakarta/jcs/trunk/src/test/org/apache/jcs/engine/memory/lru/LHMLRUMemoryCacheConcurrentUnitTest.java Thu Jun 11 13:46:34 2009
@@ -0,0 +1,174 @@
+package org.apache.jcs.engine.memory.lru;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import java.util.HashSet;
+import java.util.Map;
+import java.util.Set;
+
+import junit.extensions.ActiveTestSuite;
+import junit.framework.Test;
+import junit.framework.TestCase;
+
+import org.apache.jcs.engine.CacheElement;
+import org.apache.jcs.engine.behavior.ICacheElement;
+import org.apache.jcs.engine.control.CompositeCache;
+import org.apache.jcs.engine.control.CompositeCacheManager;
+
+/**
+ * Test which exercises the LRUMemory cache. This one uses three different
+ * regions for three threads.
+ */
+public class LHMLRUMemoryCacheConcurrentUnitTest
+    extends TestCase
+{
+    /**
+     * Number of items to cache, twice the configured maxObjects for the memory
+     * cache regions.
+     */
+    private static int items = 200;
+
+    /**
+     * Constructor for the TestDiskCache object.
+     *
+     * @param testName
+     */
+    public LHMLRUMemoryCacheConcurrentUnitTest( String testName )
+    {
+        super( testName );
+    }
+
+    /**
+     * Main method passes this test to the text test runner.
+     *
+     * @param args
+     */
+    public static void main( String args[] )
+    {
+        String[] testCaseName = { LHMLRUMemoryCacheConcurrentUnitTest.class.getName() };
+        junit.textui.TestRunner.main( testCaseName );
+    }
+
+    /**
+     * A unit test suite for JUnit
+     * <p>
+     * @return The test suite
+     */
+    public static Test suite()
+    {
+        ActiveTestSuite suite = new ActiveTestSuite();
+
+        suite.addTest( new LHMLRUMemoryCacheConcurrentUnitTest( "testLHMLRUMemoryCache" )
+        {
+            public void runTest()
+                throws Exception
+            {
+                this.runTestForRegion( "indexedRegion1" );
+            }
+        } );
+        
+        return suite;
+    }
+
+    /**
+     * Test setup
+     */
+    public void setUp()
+    {
+        //JCS.setConfigFilename( "/TestLHMLRUCache.ccf" );
+    }
+
+    /**
+     * Adds items to cache, gets them, and removes them. The item count is more
+     * than the size of the memory cache, so items should be dumped.
+     * <p>
+     * @param region
+     *            Name of the region to access
+     *
+     * @exception Exception
+     *                If an error occurs
+     */
+    public void runTestForRegion( String region )
+        throws Exception
+    {
+        CompositeCacheManager cacheMgr = CompositeCacheManager.getUnconfiguredInstance();
+        cacheMgr.configure( "/TestLHMLRUCache.ccf" );
+        CompositeCache cache = cacheMgr.getCache( region );
+
+        LRUMemoryCache lru = new LRUMemoryCache();
+        lru.initialize( cache );
+
+        // Add items to cache
+
+        for ( int i = 0; i < items; i++ )
+        {
+            ICacheElement ice = new CacheElement( cache.getCacheName(), i + ":key", region + " data " + i );
+            ice.setElementAttributes( cache.getElementAttributes() );
+            lru.update( ice );
+        }
+
+        // Test that initial items have been purged
+        for ( int i = 0; i < 100; i++ )
+        {
+            assertNull( "Should not have " + i + ":key", lru.get( i + ":key" ) );
+        }
+
+        // Test that last items are in cache
+        for ( int i = 100; i < items; i++ )
+        {
+            String value = (String) lru.get( i + ":key" ).getVal();
+            assertEquals( region + " data " + i, value );
+        }
+
+        // Test that getMultiple returns all the items remaining in cache and none of the missing ones
+        Set keys = new HashSet();
+        for ( int i = 0; i < items; i++ )
+        {
+            keys.add( i + ":key" );
+        }
+
+        Map elements = lru.getMultiple( keys );
+        for ( int i = 0; i < 100; i++ )
+        {
+            assertNull( "Should not have " + i + ":key", elements.get( i + ":key" ) );
+        }
+        for ( int i = 100; i < items; i++ )
+        {
+            ICacheElement element = (ICacheElement) elements.get( i + ":key" );
+            assertNotNull( "element " + i + ":key is missing", element );
+            assertEquals( "value " + i + ":key", region + " data " + i, element.getVal() );
+        }
+
+        // Remove all the items
+
+        for ( int i = 0; i < items; i++ )
+        {
+            lru.remove( i + ":key" );
+        }
+
+        // Verify removal
+
+        for ( int i = 0; i < items; i++ )
+        {
+            assertNull( "Removed key should be null: " + i + ":key", lru.get( i + ":key" ) );
+        }
+    }
+
+}

Added: jakarta/jcs/trunk/src/test/org/apache/jcs/engine/memory/lru/LHMLRUMemoryCacheUnitTest.java
URL: http://svn.apache.org/viewvc/jakarta/jcs/trunk/src/test/org/apache/jcs/engine/memory/lru/LHMLRUMemoryCacheUnitTest.java?rev=783765&view=auto
==============================================================================
--- jakarta/jcs/trunk/src/test/org/apache/jcs/engine/memory/lru/LHMLRUMemoryCacheUnitTest.java (added)
+++ jakarta/jcs/trunk/src/test/org/apache/jcs/engine/memory/lru/LHMLRUMemoryCacheUnitTest.java Thu Jun 11 13:46:34 2009
@@ -0,0 +1,311 @@
+package org.apache.jcs.engine.memory.lru;
+
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+import java.util.HashSet;
+import java.util.Map;
+import java.util.Set;
+
+import junit.framework.TestCase;
+
+import org.apache.jcs.JCS;
+import org.apache.jcs.access.exception.CacheException;
+import org.apache.jcs.engine.CacheElement;
+import org.apache.jcs.engine.behavior.ICacheElement;
+import org.apache.jcs.engine.control.CompositeCache;
+import org.apache.jcs.engine.control.CompositeCacheManager;
+
+/**
+ * Tests for the test LHMLRU implementation.
+ * <p>
+ * @author Aaron Smuts
+ */
+public class LHMLRUMemoryCacheUnitTest
+    extends TestCase
+{
+    /** Test setup */
+    public void setUp()
+    {
+        JCS.setConfigFilename( "/TestLHMLRUCache.ccf" );
+    }
+
+    /**
+     * Verify that the mru gets used by a non-defined region when it is set as the default in the
+     * default region.
+     * <p>
+     * @throws CacheException
+     */
+    public void testLoadFromCCF()
+        throws CacheException
+    {
+        JCS cache = JCS.getInstance( "testPutGet" );
+        String memoryCacheName = cache.getCacheAttributes().getMemoryCacheName();
+        assertTrue( "Cache name should have LHMLRU in it.", memoryCacheName.indexOf( "LHMLRUMemoryCache" ) != -1 );
+    }
+
+    /**
+     * put twice as many as the max.  verify that the second half is in the cache.
+     * <p>
+     * @throws CacheException
+     */
+    public void testPutGetThroughHub()
+        throws CacheException
+    {
+        JCS cache = JCS.getInstance( "testPutGetThroughHub" );
+
+        int max = cache.getCacheAttributes().getMaxObjects();
+        int items = max * 2;
+
+        for ( int i = 0; i < items; i++ )
+        {
+            cache.put( i + ":key", "myregion" + " data " + i );
+        }
+
+        // Test that first items are not in the cache
+        for ( int i = max -1; i >= 0; i-- )
+        {
+            String value = (String) cache.get( i + ":key" );
+            assertNull( "Should not have value for key [" + i + ":key" + "] in the cache." + cache.getStats(), value );
+        }
+
+        // Test that last items are in cache
+        // skip 2 for the buffer.
+        for ( int i = max + 2; i < items; i++ )
+        {
+            String value = (String) cache.get( i + ":key" );
+            assertEquals( "myregion" + " data " + i, value );
+        }
+
+        // Test that getMultiple returns all the items remaining in cache and none of the missing ones
+        Set keys = new HashSet();
+        for ( int i = 0; i < items; i++ )
+        {
+            keys.add( i + ":key" );
+        }
+
+        Map elements = cache.getCacheElements( keys );
+        for ( int i = max-1; i >= 0; i-- )
+        {
+            assertNull( "Should not have value for key [" + i + ":key" + "] in the cache." + cache.getStats(), elements.get( i + ":key" ) );
+        }
+        for ( int i = max + 2; i < items; i++ )
+        {
+            ICacheElement element = (ICacheElement) elements.get( i + ":key" );
+            assertNotNull( "element " + i + ":key is missing", element );
+            assertEquals( "value " + i + ":key", "myregion" + " data " + i, element.getVal() );
+        }
+    }
+
+    /**
+     * Put twice as many as the max, twice. verify that the second half is in the cache.
+     * <p>
+     * @throws CacheException
+     */
+    public void testPutGetThroughHubTwice()
+        throws CacheException
+    {
+        JCS cache = JCS.getInstance( "testPutGetThroughHub" );
+
+        int max = cache.getCacheAttributes().getMaxObjects();
+        int items = max * 2;
+
+        for ( int i = 0; i < items; i++ )
+        {
+            cache.put( i + ":key", "myregion" + " data " + i );
+        }
+
+        for ( int i = 0; i < items; i++ )
+        {
+            cache.put( i + ":key", "myregion" + " data " + i );
+        }
+
+        // Test that first items are not in the cache
+        for ( int i = max -1; i >= 0; i-- )
+        {
+            String value = (String) cache.get( i + ":key" );
+            assertNull( "Should not have value for key [" + i + ":key" + "] in the cache.", value );
+        }
+
+        // Test that last items are in cache
+        // skip 2 for the buffer.
+        for ( int i = max + 2; i < items; i++ )
+        {
+            String value = (String) cache.get( i + ":key" );
+            assertEquals( "myregion" + " data " + i, value );
+        }
+
+    }
+
+    /**
+     * put the max and remove each. verify that they are all null.
+     * <p>
+     * @throws CacheException
+     */
+    public void testPutRemoveThroughHub()
+        throws CacheException
+    {
+        JCS cache = JCS.getInstance( "testPutGetThroughHub" );
+
+        int max = cache.getCacheAttributes().getMaxObjects();
+        int items = max * 2;
+
+        for ( int i = 0; i < items; i++ )
+        {
+            cache.put( i + ":key", "myregion" + " data " + i );
+        }
+
+        for ( int i = 0; i < items; i++ )
+        {
+            cache.remove( i + ":key" );
+        }
+
+        // Test that first items are not in the cache
+        for ( int i = max; i >= 0; i-- )
+        {
+            String value = (String) cache.get( i + ":key" );
+            assertNull( "Should not have value for key [" + i + ":key" + "] in the cache.", value );
+        }
+    }
+
+    /**
+     * put the max and clear. verify that no elements remain.
+     * <p>
+     * @throws CacheException
+     */
+    public void testClearThroughHub()
+        throws CacheException
+    {
+        JCS cache = JCS.getInstance( "testPutGetThroughHub" );
+
+        int max = cache.getCacheAttributes().getMaxObjects();
+        int items = max * 2;
+
+        for ( int i = 0; i < items; i++ )
+        {
+            cache.put( i + ":key", "myregion" + " data " + i );
+        }
+
+        cache.clear();
+
+        // Test that first items are not in the cache
+        for ( int i = max; i >= 0; i-- )
+        {
+            String value = (String) cache.get( i + ":key" );
+            assertNull( "Should not have value for key [" + i + ":key" + "] in the cache.", value );
+        }
+    }
+
+    /**
+     * Get stats.
+     * <p>
+     * @throws CacheException
+     */
+    public void testGetStatsThroughHub()
+        throws CacheException
+    {
+        JCS cache = JCS.getInstance( "testGetStatsThroughHub" );
+
+        int max = cache.getCacheAttributes().getMaxObjects();
+        int items = max * 2;
+
+        for ( int i = 0; i < items; i++ )
+        {
+            cache.put( i + ":key", "myregion" + " data " + i );
+        }
+
+        String stats = cache.getStats();
+
+        //System.out.println( stats );
+
+        // TODO improve stats check
+        assertTrue( "Should have 200 puts" + stats, stats.indexOf( "200" ) != -1 );
+    }
+
+    /**
+     * Put half the max and clear. get the key array and verify that it has the correct number of
+     * items.
+     * <p>
+     * @throws Exception
+     */
+    public void testGetKeyArray()
+        throws Exception
+    {
+        CompositeCacheManager cacheMgr = CompositeCacheManager.getUnconfiguredInstance();
+        cacheMgr.configure( "/TestLHMLRUCache.ccf" );
+        CompositeCache cache = cacheMgr.getCache( "testGetKeyArray" );
+
+        LHMLRUMemoryCache mru = new LHMLRUMemoryCache();
+        mru.initialize( cache );
+
+        int max = cache.getCacheAttributes().getMaxObjects();
+        int items = max / 2;
+
+        for ( int i = 0; i < items; i++ )
+        {
+            ICacheElement ice = new CacheElement( cache.getCacheName(), i + ":key", cache.getCacheName() + " data " + i );
+            ice.setElementAttributes( cache.getElementAttributes() );
+            mru.update( ice );
+        }
+
+        Object[] keys = mru.getKeyArray();
+
+        assertEquals( "Wrong number of keys.", items, keys.length );
+    }
+
+    /**
+     * Add a few keys with the delimeter. Remove them.
+     * <p>
+     * @throws CacheException
+     */
+    public void testRemovePartialThroughHub()
+        throws CacheException
+    {
+        JCS cache = JCS.getInstance( "testGetStatsThroughHub" );
+
+        int max = cache.getCacheAttributes().getMaxObjects();
+        int items = max / 2;
+
+        cache.put( "test", "data" );
+
+        String root = "myroot";
+
+        for ( int i = 0; i < items; i++ )
+        {
+            cache.put( root + ":" + i + ":key", "myregion" + " data " + i );
+        }
+
+        // Test that last items are in cache
+        for ( int i = 0; i < items; i++ )
+        {
+            String value = (String) cache.get( root + ":" + i + ":key" );
+            assertEquals( "myregion" + " data " + i, value );
+        }
+
+        // remove partial
+        cache.remove( root + ":" );
+
+        for ( int i = 0; i < items; i++ )
+        {
+            assertNull( "Should have been removed by partial loop.", cache.get( root + ":" + i + ":key" ) );
+        }
+
+        assertNotNull( "Other item should be in the cache.", cache.get( "test" ) );
+    }
+}

Modified: jakarta/jcs/trunk/src/test/org/apache/jcs/engine/memory/lru/LRUMemoryCacheConcurrentUnitTest.java
URL: http://svn.apache.org/viewvc/jakarta/jcs/trunk/src/test/org/apache/jcs/engine/memory/lru/LRUMemoryCacheConcurrentUnitTest.java?rev=783765&r1=783764&r2=783765&view=diff
==============================================================================
--- jakarta/jcs/trunk/src/test/org/apache/jcs/engine/memory/lru/LRUMemoryCacheConcurrentUnitTest.java (original)
+++ jakarta/jcs/trunk/src/test/org/apache/jcs/engine/memory/lru/LRUMemoryCacheConcurrentUnitTest.java Thu Jun 11 13:46:34 2009
@@ -47,7 +47,7 @@
 
     /**
      * Constructor for the TestDiskCache object.
-     *
+     * <p>
      * @param testName
      */
     public LRUMemoryCacheConcurrentUnitTest( String testName )
@@ -57,7 +57,7 @@
 
     /**
      * Main method passes this test to the text test runner.
-     *
+     * <p>
      * @param args
      */
     public static void main( String args[] )
@@ -80,7 +80,7 @@
             public void runTest()
                 throws Exception
             {
-                this.runTestForRegion( "indexedRegion1" );
+                this.runTestForRegion( "testRegion1" );
             }
         } );
         
@@ -101,7 +101,6 @@
      * <p>
      * @param region
      *            Name of the region to access
-     *
      * @exception Exception
      *                If an error occurs
      */
@@ -157,18 +156,15 @@
         }
 
         // Remove all the items
-
         for ( int i = 0; i < items; i++ )
         {
             lru.remove( i + ":key" );
         }
 
         // Verify removal
-
         for ( int i = 0; i < items; i++ )
         {
             assertNull( "Removed key should be null: " + i + ":key", lru.get( i + ":key" ) );
         }
     }
-
 }



---------------------------------------------------------------------
To unsubscribe, e-mail: jcs-dev-unsubscribe@jakarta.apache.org
For additional commands, e-mail: jcs-dev-help@jakarta.apache.org


Mime
View raw message