View Javadoc

1   /**
2    *  Copyright 2003-2007 Greg Luck
3    *
4    *  Licensed under the Apache License, Version 2.0 (the "License");
5    *  you may not use this file except in compliance with the License.
6    *  You may obtain a copy of the License at
7    *
8    *      http://www.apache.org/licenses/LICENSE-2.0
9    *
10   *  Unless required by applicable law or agreed to in writing, software
11   *  distributed under the License is distributed on an "AS IS" BASIS,
12   *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13   *  See the License for the specific language governing permissions and
14   *  limitations under the License.
15   */
16  
17  
18  package net.sf.ehcache.distribution;
19  
20  import net.sf.ehcache.CacheException;
21  import net.sf.ehcache.Ehcache;
22  import org.apache.commons.logging.Log;
23  import org.apache.commons.logging.LogFactory;
24  
25  import java.rmi.NotBoundException;
26  import java.util.ArrayList;
27  import java.util.Date;
28  import java.util.Iterator;
29  import java.util.List;
30  
31  /**
32   * A provider of Peer RMI addresses based off manual configuration.
33   * <p/>
34   * Because there is no monitoring of whether a peer is actually there, the list of peers is dynamically
35   * looked up and verified each time a lookup request is made.
36   * <p/>
37   * @author Greg Luck
38   * @version $Id: ManualRMICacheManagerPeerProvider.java 512 2007-07-10 09:18:45Z gregluck $
39   */
40  public final class ManualRMICacheManagerPeerProvider extends RMICacheManagerPeerProvider {
41  
42      private static final Log LOG = LogFactory.getLog(ManualRMICacheManagerPeerProvider.class.getName());
43  
44      /**
45       * Empty constructor.
46       */
47      public ManualRMICacheManagerPeerProvider() {
48          super();
49      }
50  
51      /**
52       * {@inheritDoc}
53       */
54      public final void init() {
55          //nothing to do here
56      }
57  
58      /**
59       * Time for a cluster to form. This varies considerably, depending on the implementation.
60       *
61       * @return the time in ms, for a cluster to form
62       */
63      public long getTimeForClusterToForm() {
64          return 0;
65      }
66  
67      /**
68       * Register a new peer.
69       *
70       * @param rmiUrl
71       */
72      public final synchronized void registerPeer(String rmiUrl) {
73          peerUrls.put(rmiUrl, new Date());
74      }
75  
76  
77      /**
78       * @return a list of {@link CachePeer} peers, excluding the local peer.
79       */
80      public final synchronized List listRemoteCachePeers(Ehcache cache) throws CacheException {
81          List remoteCachePeers = new ArrayList();
82          List staleList = new ArrayList();
83          for (Iterator iterator = peerUrls.keySet().iterator(); iterator.hasNext();) {
84              String rmiUrl = (String) iterator.next();
85              String rmiUrlCacheName = extractCacheName(rmiUrl);
86              try {
87                  if (!rmiUrlCacheName.equals(cache.getName())) {
88                      continue;
89                  }
90                  Date date = (Date) peerUrls.get(rmiUrl);
91                  if (!stale(date)) {
92                      CachePeer cachePeer = lookupRemoteCachePeer(rmiUrl);
93                      remoteCachePeers.add(cachePeer);
94                  } else {
95                      if (LOG.isDebugEnabled()) {
96                          LOG.debug("rmiUrl " + rmiUrl + " is stale. Either the remote peer is shutdown or the " +
97                                  "network connectivity has been interrupted. Will be removed from list of remote cache peers");
98                      }
99                      staleList.add(rmiUrl);
100                 }
101             } catch (NotBoundException e) {
102                 if (LOG.isDebugEnabled()) {
103                     LOG.debug("No cache peer bound to URL at " + rmiUrl
104                             + ". It must have disappeared since the last heartbeat");
105                 }
106             } catch (Exception exception) {
107                 LOG.error(exception.getMessage(), exception);
108                 throw new CacheException("Unable to list remote cache peers. Error was " + exception.getMessage());
109             }
110         }
111 
112         //Remove any stale remote peers. Must be done here to avoid concurrent modification exception.
113         for (int i = 0; i < staleList.size(); i++) {
114             String rmiUrl = (String) staleList.get(i);
115             peerUrls.remove(rmiUrl);
116         }
117         return remoteCachePeers;
118     }
119 
120 
121     /**
122      * Whether the entry should be considered stale.
123      * <p/>
124      * Manual RMICacheManagerProviders use a static list of urls and are therefore never stale.
125      *
126      * @param date the date the entry was created
127      * @return true if stale
128      */
129     protected final boolean stale(Date date) {
130         return false;
131     }
132 
133 }