extensions/net.sf.basedb.varsearch/trunk/src/net/sf/basedb/varsearch/query/QueryCache.java

Code
Comments
Other
Rev Date Author Line
6137 18 Feb 21 nicklas 1 package net.sf.basedb.varsearch.query;
6137 18 Feb 21 nicklas 2
6137 18 Feb 21 nicklas 3 import java.util.Collections;
6137 18 Feb 21 nicklas 4 import java.util.HashMap;
6137 18 Feb 21 nicklas 5 import java.util.Iterator;
6137 18 Feb 21 nicklas 6 import java.util.Map;
6137 18 Feb 21 nicklas 7 import java.util.Map.Entry;
6137 18 Feb 21 nicklas 8
6137 18 Feb 21 nicklas 9
6137 18 Feb 21 nicklas 10 /**
6137 18 Feb 21 nicklas 11   Cache for keeping results from queries.
6137 18 Feb 21 nicklas 12
6137 18 Feb 21 nicklas 13   @author nicklas
6137 18 Feb 21 nicklas 14 */
6137 18 Feb 21 nicklas 15 public class QueryCache 
6137 18 Feb 21 nicklas 16 {
6137 18 Feb 21 nicklas 17
6137 18 Feb 21 nicklas 18   private final Map<String, CacheEntry> cache;
6137 18 Feb 21 nicklas 19   private final long timeoutInMillis;
6137 18 Feb 21 nicklas 20   private long nextCleanup;
6137 18 Feb 21 nicklas 21   
6137 18 Feb 21 nicklas 22   /**
6137 18 Feb 21 nicklas 23     Creates a new cache with the specified timeout.
6137 18 Feb 21 nicklas 24   */
6137 18 Feb 21 nicklas 25   public QueryCache(int timeoutInMinutes)
6137 18 Feb 21 nicklas 26   {
6137 18 Feb 21 nicklas 27     this.cache = Collections.synchronizedMap(new HashMap<>());
6137 18 Feb 21 nicklas 28     this.timeoutInMillis = timeoutInMinutes * 60000;
6137 18 Feb 21 nicklas 29     this.nextCleanup = System.currentTimeMillis() + timeoutInMillis;
6137 18 Feb 21 nicklas 30   }
6137 18 Feb 21 nicklas 31
6137 18 Feb 21 nicklas 32   /**
6137 18 Feb 21 nicklas 33     Get a cached entry if. Null is returned if there is no
6245 24 May 21 nicklas 34     entry or if the existing entry is too old or if the
6245 24 May 21 nicklas 35     existing entry contains a result that timed out and the 
6245 24 May 21 nicklas 36     new timeout is longer.
6137 18 Feb 21 nicklas 37   */
6245 24 May 21 nicklas 38   public QueryResult get(String key, int newTimeout)
6137 18 Feb 21 nicklas 39   {
6245 24 May 21 nicklas 40     QueryResult result = null;
6137 18 Feb 21 nicklas 41     CacheEntry entry = cache.get(key);
6245 24 May 21 nicklas 42     if (entry != null) 
6245 24 May 21 nicklas 43     {
6245 24 May 21 nicklas 44       entry.setTimeout(System.currentTimeMillis()+timeoutInMillis);
6245 24 May 21 nicklas 45       result = entry.getResult();
6245 24 May 21 nicklas 46       if (result.hasTimedOut() && result.getTimeoutInSeconds() < newTimeout)
6245 24 May 21 nicklas 47       {
6245 24 May 21 nicklas 48         result = null;
6245 24 May 21 nicklas 49       }
6245 24 May 21 nicklas 50     }
6245 24 May 21 nicklas 51     return result;
6137 18 Feb 21 nicklas 52   }
6137 18 Feb 21 nicklas 53
6137 18 Feb 21 nicklas 54   /**
6137 18 Feb 21 nicklas 55     Store a new entry into the cache.
6137 18 Feb 21 nicklas 56   */
6241 21 May 21 nicklas 57   public void store(String key, QueryResult result)
6137 18 Feb 21 nicklas 58   {
6137 18 Feb 21 nicklas 59     long time = System.currentTimeMillis();
6241 21 May 21 nicklas 60     CacheEntry entry = new CacheEntry(time+timeoutInMillis, result);
6137 18 Feb 21 nicklas 61     cache.put(key, entry);
6165 08 Mar 21 nicklas 62     if (time > nextCleanup) clean(false);
6137 18 Feb 21 nicklas 63   }
6137 18 Feb 21 nicklas 64   
6163 05 Mar 21 nicklas 65   /**
6163 05 Mar 21 nicklas 66     Get the number of stored query results in the cache.
6163 05 Mar 21 nicklas 67   */
6163 05 Mar 21 nicklas 68   public int getSize()
6163 05 Mar 21 nicklas 69   {
6163 05 Mar 21 nicklas 70     return cache.size();
6163 05 Mar 21 nicklas 71   }
6163 05 Mar 21 nicklas 72   
6165 08 Mar 21 nicklas 73   /**
6165 08 Mar 21 nicklas 74     Clean the cache from results.
6165 08 Mar 21 nicklas 75     @param all TRUE to clean all results, FALSE to only clean results that have timed out
6165 08 Mar 21 nicklas 76   */
6165 08 Mar 21 nicklas 77   public void clean(boolean all)
6137 18 Feb 21 nicklas 78   {
6137 18 Feb 21 nicklas 79     synchronized (cache)
6137 18 Feb 21 nicklas 80     {
6137 18 Feb 21 nicklas 81       long time = System.currentTimeMillis();
6165 08 Mar 21 nicklas 82       if (all)
6137 18 Feb 21 nicklas 83       {
6165 08 Mar 21 nicklas 84         cache.clear();
6137 18 Feb 21 nicklas 85       }
6165 08 Mar 21 nicklas 86       else
6165 08 Mar 21 nicklas 87       {
6165 08 Mar 21 nicklas 88         Iterator<Entry<String, CacheEntry>> it = cache.entrySet().iterator();
6165 08 Mar 21 nicklas 89         while (it.hasNext())
6165 08 Mar 21 nicklas 90         {
6165 08 Mar 21 nicklas 91           if (it.next().getValue().getTimeout() < time) it.remove();
6165 08 Mar 21 nicklas 92         }
6165 08 Mar 21 nicklas 93       }
6137 18 Feb 21 nicklas 94       nextCleanup = time + timeoutInMillis;
6137 18 Feb 21 nicklas 95     }
6137 18 Feb 21 nicklas 96   }
6137 18 Feb 21 nicklas 97   
6137 18 Feb 21 nicklas 98   static class CacheEntry
6137 18 Feb 21 nicklas 99   {
6241 21 May 21 nicklas 100     private final QueryResult result;
6137 18 Feb 21 nicklas 101     private long timeout;
6137 18 Feb 21 nicklas 102     
6241 21 May 21 nicklas 103     CacheEntry(long timeout, QueryResult result)
6137 18 Feb 21 nicklas 104     {
6241 21 May 21 nicklas 105       this.result = result;
6137 18 Feb 21 nicklas 106       this.timeout = timeout;
6137 18 Feb 21 nicklas 107     }
6137 18 Feb 21 nicklas 108     
6137 18 Feb 21 nicklas 109     void setTimeout(long timeout)
6137 18 Feb 21 nicklas 110     {
6137 18 Feb 21 nicklas 111       this.timeout = timeout;
6137 18 Feb 21 nicklas 112     }
6137 18 Feb 21 nicklas 113     
6137 18 Feb 21 nicklas 114     long getTimeout()
6137 18 Feb 21 nicklas 115     {
6137 18 Feb 21 nicklas 116       return timeout;
6137 18 Feb 21 nicklas 117     }
6137 18 Feb 21 nicklas 118     
6241 21 May 21 nicklas 119     QueryResult getResult()
6137 18 Feb 21 nicklas 120     {
6241 21 May 21 nicklas 121       return result;
6137 18 Feb 21 nicklas 122     }
6137 18 Feb 21 nicklas 123   }
6137 18 Feb 21 nicklas 124
6137 18 Feb 21 nicklas 125 }