jmcnally    02/03/27 15:54:54

  Modified:    src/java/org/apache/torque/manager AbstractBaseManager.java
                        MethodCacheKey.java MethodResultCache.java
  Log:
  Switched MethodResultCache to use groups, so that method results for the same
  method with different arguments can be invalidated as a group.
  
  Removed hack in MethodCacheKey that was not working very well, and is
  not needed due to the change in MethodResultCache.
  
  Managers take on the task of invalidating caches.  The keeps the number
  of listeners small and better behaved.  Since the manager handles the
  cache it is not unreasonable for it to handle invalidation as well.
  
  Revision  Changes    Path
  1.3       +43 -44    
jakarta-turbine-torque/src/java/org/apache/torque/manager/AbstractBaseManager.java
  
  Index: AbstractBaseManager.java
  ===================================================================
  RCS file: 
/home/cvs/jakarta-turbine-torque/src/java/org/apache/torque/manager/AbstractBaseManager.java,v
  retrieving revision 1.2
  retrieving revision 1.3
  diff -u -r1.2 -r1.3
  --- AbstractBaseManager.java  15 Mar 2002 22:45:03 -0000      1.2
  +++ AbstractBaseManager.java  27 Mar 2002 23:54:54 -0000      1.3
  @@ -65,8 +65,9 @@
   import java.io.Serializable;
   import java.io.IOException;
   
  +import org.apache.commons.collections.FastArrayList;
   import org.apache.stratum.jcs.JCS;
  -import org.apache.stratum.jcs.access.behavior.ICacheAccess;
  +import org.apache.stratum.jcs.access.GroupCacheAccess;
   import org.apache.stratum.jcs.access.exception.CacheException;
   
   import org.apache.torque.TorqueException;
  @@ -79,7 +80,7 @@
    * instantiating OM's.
    *
    * @author <a href="mailto:[EMAIL PROTECTED]";>John McNally</a>
  - * @version $Id: AbstractBaseManager.java,v 1.2 2002/03/15 22:45:03 jmcnally Exp $
  + * @version $Id: AbstractBaseManager.java,v 1.3 2002/03/27 23:54:54 jmcnally Exp $
    */
   public abstract class AbstractBaseManager
       implements Serializable
  @@ -88,7 +89,7 @@
           Category.getInstance(AbstractBaseManager.class.getName());
   
       /** used to cache the om objects. cache is set by the region property */
  -    transient protected ICacheAccess cache;
  +    transient protected GroupCacheAccess cache;
   
       /** method results cache */
       protected MethodResultCache mrCache;
  @@ -193,7 +194,7 @@
           return om;
       }
   
  -    private Persistent cacheGet(ObjectKey key)
  +    protected Persistent cacheGet(ObjectKey key)
       {
           Persistent om = null;
           if (cache != null)
  @@ -202,13 +203,13 @@
               {
                   synchronized (this)
                   {
  -                    om = (Persistent)cache.get(key);
  +                    om = (Persistent)cache.get(key);  
                   }
               }
               else
               {
                   inGet++;
  -                om = (Persistent)cache.get(key);
  +                om = (Persistent)cache.get(key);  
                   inGet--;
               }
           }
  @@ -248,7 +249,7 @@
                       while (inGet > 0) 
                       {
                           Thread.yield();
  -                    }                    
  +                    }
                       cache.remove(key);
                   }
                   catch (CacheException ce)
  @@ -444,65 +445,63 @@
   
       public void addCacheListenerImpl(CacheListener listener)
       {
  -        List subsetKeys = listener.getInterestedFields();
  -        Iterator i = subsetKeys.iterator();
  +        List keys = listener.getInterestedFields();
  +        Iterator i = keys.iterator();
           while (i.hasNext()) 
           {
  -            Object[] ie = (Object[])i.next();
  -            String key1 = (String)ie[0];
  -         
  +            String key = (String)i.next();         
               // Peer.column names are the fields
  -            if (validFields != null && validFields.containsKey(key1)) 
  +            if (validFields != null && validFields.containsKey(key)) 
               {
  -                ObjectKey key2 = (ObjectKey)ie[1];
  -                Map subsetMap = (Map)listenersMap.get(key1);
  -                if (subsetMap == null) 
  +                List listeners = (List)listenersMap.get(key);
  +                if (listeners == null) 
                   {
  -                    subsetMap = createSubsetMap(key1);
  +                    listeners = createSubsetList(key);
                   }
                   
  -                List listeners = (List)subsetMap.get(key2);
  -                if (listeners == null) 
  -                {
  -                    listeners = createIdList(subsetMap, key2);
  +                boolean isNew = true;
  +                Iterator j = listeners.iterator();
  +                while (j.hasNext()) 
  +                {
  +                    Object listener2 = 
  +                        ((WeakReference)j.next()).get();
  +                    if (listener2 == null) 
  +                    {
  +                        // do a little cleanup while checking for dupes
  +                        // not thread-safe, not likely to be many nulls
  +                        // but should revisit
  +                        //j.remove();
  +                    }
  +                    else if (listener2 == listener)
  +                    {
  +                        isNew = false;
  +                        break;
  +                    }
                   }
  -                synchronized (listeners)
  +                if (isNew) 
                   {
                       listeners.add(new WeakReference(listener));
  -                }
  -            }            
  +                }                    
  +            }
           }
       }
   
  -    synchronized private Map createSubsetMap(String key)
  +    synchronized private List createSubsetList(String key)
       {
  -        Map map = null;
  +        FastArrayList list = null;
           if (listenersMap.containsKey(key)) 
           {
  -            map = (Map)listenersMap.get(key);
  +            list = (FastArrayList)listenersMap.get(key);
           }
           else 
           {
  -            map = new HashMap();
  -            listenersMap.put(key, map);
  +            list = new FastArrayList();
  +            list.setFast(true);
  +            listenersMap.put(key, list);
           }
  -        return map;
  +        return list;
       }
   
  -    synchronized private List createIdList(Map map, ObjectKey key)
  -    {
  -        List l = null;
  -        if (map.containsKey(key)) 
  -        {
  -            l = (List)map.get(key);
  -        }
  -        else 
  -        {
  -            l = new LinkedList();
  -            map.put(key, l);
  -        }
  -        return l;
  -    }
   
       protected void notifyListeners(List listeners, 
                                      Persistent oldOm, Persistent om)
  
  
  
  1.2       +11 -17    
jakarta-turbine-torque/src/java/org/apache/torque/manager/MethodCacheKey.java
  
  Index: MethodCacheKey.java
  ===================================================================
  RCS file: 
/home/cvs/jakarta-turbine-torque/src/java/org/apache/torque/manager/MethodCacheKey.java,v
  retrieving revision 1.1
  retrieving revision 1.2
  diff -u -r1.1 -r1.2
  --- MethodCacheKey.java       13 Mar 2002 21:31:23 -0000      1.1
  +++ MethodCacheKey.java       27 Mar 2002 23:54:54 -0000      1.2
  @@ -65,7 +65,7 @@
       private Serializable arg2;
       private Serializable arg3;
       private Serializable[] moreThanThree;
  -    private boolean lenient; 
  +    private String groupKey;
   
       public MethodCacheKey()
       {
  @@ -112,6 +112,7 @@
           n = 0;
           this.instanceOrClass = instanceOrClass;
           this.method = method;
  +        groupKey = instanceOrClass.toString() + method;
       }
   
       /**
  @@ -125,9 +126,8 @@
       public void init(Serializable instanceOrClass, String method, 
                        Serializable arg1)
       {
  +        init(instanceOrClass, method);
           n = 1;
  -        this.instanceOrClass = instanceOrClass;
  -        this.method = method;
           this.arg1 = arg1;
       }
   
  @@ -143,9 +143,8 @@
       public void init(Serializable instanceOrClass, String method, 
                        Serializable arg1, Serializable arg2)
       {
  +        init(instanceOrClass, method);
           n = 2;
  -        this.instanceOrClass = instanceOrClass;
  -        this.method = method;
           this.arg1 = arg1;
           this.arg2 = arg2;
       }
  @@ -164,9 +163,8 @@
                        Serializable arg1, Serializable arg2,
                        Serializable arg3)
       {
  +        init(instanceOrClass, method);
           n = 3;
  -        this.instanceOrClass = instanceOrClass;
  -        this.method = method;
           this.arg1 = arg1;
           this.arg2 = arg2;
           this.arg3 = arg3;
  @@ -183,9 +181,8 @@
        */
       public void init(Serializable[] keys)
       {
  +        init(keys[0], (String)keys[1]);
           n = keys.length-2;
  -        this.instanceOrClass = keys[0];
  -        this.method = (String)keys[1];
           if (n>0) 
           {
               this.arg1 = keys[2];
  @@ -204,9 +201,9 @@
           }
       }
   
  -    public void setLenient(boolean v)
  +    public String getGroupKey()
       {
  -        lenient = v;
  +        return groupKey;
       }
   
       public boolean equals(Object obj)
  @@ -215,10 +212,10 @@
           if ( obj instanceof MethodCacheKey ) 
           {
               MethodCacheKey sck = (MethodCacheKey)obj;
  -            equal = lenient || sck.n == n;
  +            equal = sck.n == n;
               equal &= Objects.equals(sck.method, method);
               equal &= Objects.equals(sck.instanceOrClass, instanceOrClass);
  -            if (equal && n > 0 && !lenient && !sck.lenient) 
  +            if (equal && n > 0) 
               {
                   equal &= Objects.equals(sck.arg1, arg1);
                   if (equal && n > 1) 
  @@ -247,8 +244,6 @@
       {
           int h = instanceOrClass.hashCode();
           h += method.hashCode();
  -        /* lenient equals requires hashCode only reflect the
  -           object and method name
           if (n > 0) 
           {
               h += (arg1 == null ? 0 : arg1.hashCode());
  @@ -269,7 +264,6 @@
                   }    
               }
           }
  -        */
           return h;
       }
   
  @@ -318,6 +312,6 @@
           arg2 = null;
           arg3 = null;
           moreThanThree = null;
  -        lenient = false;
  +        groupKey = null;
       }
   }
  
  
  
  1.2       +38 -24    
jakarta-turbine-torque/src/java/org/apache/torque/manager/MethodResultCache.java
  
  Index: MethodResultCache.java
  ===================================================================
  RCS file: 
/home/cvs/jakarta-turbine-torque/src/java/org/apache/torque/manager/MethodResultCache.java,v
  retrieving revision 1.1
  retrieving revision 1.2
  diff -u -r1.1 -r1.2
  --- MethodResultCache.java    13 Mar 2002 21:31:23 -0000      1.1
  +++ MethodResultCache.java    27 Mar 2002 23:54:54 -0000      1.2
  @@ -54,7 +54,7 @@
   import org.apache.log4j.Category;
   //import org.apache.stratum.configuration.Configuration;
   import org.apache.stratum.pool.DefaultPoolManager;
  -import org.apache.stratum.jcs.access.behavior.ICacheAccess;
  +import org.apache.stratum.jcs.access.GroupCacheAccess;
   import org.apache.stratum.jcs.access.exception.CacheException;
   
   import org.apache.torque.TorqueException;
  @@ -63,7 +63,7 @@
    * This class provides a cache for convenient storage of method results
    *
    * @author <a href="mailto:[EMAIL PROTECTED]";>John McNally</a>
  - * @version $Id: MethodResultCache.java,v 1.1 2002/03/13 21:31:23 jmcnally Exp $
  + * @version $Id: MethodResultCache.java,v 1.2 2002/03/27 23:54:54 jmcnally Exp $
    */
   public class MethodResultCache 
   {
  @@ -74,10 +74,11 @@
           "org.apache.torque.manager.MethodCacheKey";
       private DefaultPoolManager pool;
       private Map keys;
  -    private ICacheAccess jcsCache;
  +    private GroupCacheAccess jcsCache;
       private Class keyClass;
       private boolean lockCache;
       private int inGet;
  +    private Map groups;
   
       /*
       public MethodResultCache()
  @@ -87,7 +88,7 @@
       }
       */
   
  -    public MethodResultCache(ICacheAccess cache)
  +    public MethodResultCache(GroupCacheAccess cache)
           throws ClassNotFoundException
       {
           keys = new WeakHashMap();            
  @@ -95,6 +96,7 @@
           this.jcsCache = cache;            
           pool =  new DefaultPoolManager();
           pool.setCapacity(keyClassName, 10000);
  +        groups = new HashMap();
       }
   
       public void clear()
  @@ -130,13 +132,13 @@
               {
                   synchronized (this)
                   {
  -                    result = jcsCache.get(key);
  +                    result = jcsCache.getFromGroup(key, key.getGroupKey());
                   }
               }
               else
               {
                   inGet++;
  -                result = jcsCache.get(key);
  +                result = jcsCache.getFromGroup(key, key.getGroupKey());
                   inGet--;
               }
           }
  @@ -153,6 +155,27 @@
       protected Object putImpl(MethodCacheKey key, Object value)
           throws TorqueException
       {
  +        //register the group, if this is the first occurrence
  +        String group = key.getGroupKey();
  +        if (!groups.containsKey(group)) 
  +        {
  +            synchronized (jcsCache)
  +            {
  +                if (!groups.containsKey(group)) 
  +                {
  +                    try
  +                    {
  +                        jcsCache.defineGroup(group);
  +                    }
  +                    catch (CacheException ce)
  +                    {
  +                        throw new TorqueException(ce);
  +                    }
  +                    groups.put(group, null);
  +                }                
  +            }
  +        }
  +
           Object old = null;
           if (jcsCache != null)
           {
  @@ -161,13 +184,12 @@
                   lockCache = true;
                   try
                   {
  -                    old = jcsCache.get(key);
  +                    old = jcsCache.getFromGroup(key, group);
                       while (inGet > 0) 
                       {
                           Thread.yield();
                       }                    
  -                    jcsCache.put(key, value);
  -                    keys.put(key, key);
  +                    jcsCache.putInGroup(key, group, value);
                   }
                   catch (CacheException ce)
                   {
  @@ -195,15 +217,16 @@
                   lockCache = true;
                   try
                   {
  -                    old = jcsCache.get(key);
  +                    old = jcsCache.getFromGroup(key, key.getGroupKey());
                       while (inGet > 0) 
                       {
                           Thread.yield();
                       }
  -                    jcsCache.remove(key);
  -                    pool.putInstance(keys.remove(key));
  +                    jcsCache.remove(key, key.getGroupKey());
  +                    pool.putInstance(key);
                   }
  -                catch (CacheException ce)
  +                // jcs does not throw an exception here, might remove this
  +                catch (Exception ce) 
                   {
                       lockCache = false;
                       throw new TorqueException(
  @@ -407,9 +430,8 @@
       }
   
   
  -    public int removeAll(Serializable instanceOrClass, String method)
  +    public void removeAll(Serializable instanceOrClass, String method)
       {
  -        int result = -1;
           if (jcsCache != null) 
           {
               try
  @@ -417,14 +439,7 @@
                   MethodCacheKey key = 
                       (MethodCacheKey)pool.getInstance(keyClass);
                   key.init(instanceOrClass, method);
  -                key.setLenient(true);
  -                Object obj = null;
  -                do 
  -                {
  -                    obj = removeImpl(key);
  -                    result++;
  -                }
  -                while (obj != null);
  +                jcsCache.invalidateGroup(key.getGroupKey());
                   pool.putInstance(key);
               }
               catch (Exception e)
  @@ -432,7 +447,6 @@
                   log.error(e);
               }            
           }
  -        return result;
       }
   
   
  
  
  

--
To unsubscribe, e-mail:   <mailto:[EMAIL PROTECTED]>
For additional commands, e-mail: <mailto:[EMAIL PROTECTED]>

Reply via email to