1 package org.apache.jcs.engine;
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22 import java.io.IOException;
23
24 import java.util.HashMap;
25 import java.util.HashSet;
26 import java.util.Iterator;
27 import java.util.Map;
28 import java.util.Set;
29
30 import org.apache.jcs.engine.behavior.ICacheObserver;
31 import org.apache.jcs.engine.behavior.ICacheListener;
32
33 import org.apache.commons.logging.Log;
34 import org.apache.commons.logging.LogFactory;
35
36 /***
37 * Intercepts the requests to the underlying ICacheObserver object so that the
38 * listeners can be recorded locally for remote connection recovery purposes.
39 * (Durable subscription like those in JMS is not implemented at this stage for
40 * it can be too expensive on the runtime.)
41 *
42 */
43 public class CacheWatchRepairable
44 implements ICacheObserver
45 {
46 private final static Log log = LogFactory.getLog( CacheWatchRepairable.class );
47
48
49 private ICacheObserver cacheWatch;
50
51 private Map cacheMap = new HashMap();
52
53 /***
54 * Replaces the underlying cache watch service and reattached all existing
55 * listeners to the new cache watch.
56 * <p>
57 * @param cacheWatch
58 * The new cacheWatch value
59 */
60 public void setCacheWatch( ICacheObserver cacheWatch )
61 {
62 this.cacheWatch = cacheWatch;
63 synchronized ( cacheMap )
64 {
65 for ( Iterator itr = cacheMap.entrySet().iterator(); itr.hasNext(); )
66 {
67 Map.Entry entry = (Map.Entry) itr.next();
68 String cacheName = (String) entry.getKey();
69 Set listenerSet = (Set) entry.getValue();
70 for ( Iterator itr2 = listenerSet.iterator(); itr2.hasNext(); )
71 {
72 try
73 {
74 cacheWatch.addCacheListener( cacheName, (ICacheListener) itr2.next() );
75 }
76 catch ( IOException ex )
77 {
78 log.error( "Problem adding listener.", ex );
79 }
80 }
81 }
82 }
83 }
84
85 /***
86 * Adds a feature to the CacheListener attribute of the CacheWatchRepairable
87 * object
88 * <p>
89 * @param cacheName
90 * The feature to be added to the CacheListener attribute
91 * @param obj
92 * The feature to be added to the CacheListener attribute
93 * @throws IOException
94 */
95 public void addCacheListener( String cacheName, ICacheListener obj )
96 throws IOException
97 {
98
99
100
101 synchronized ( cacheMap )
102 {
103 Set listenerSet = (Set) cacheMap.get( cacheName );
104 if ( listenerSet == null )
105 {
106 listenerSet = new HashSet();
107 cacheMap.put( cacheName, listenerSet );
108 }
109 listenerSet.add( obj );
110 }
111 cacheWatch.addCacheListener( cacheName, obj );
112 }
113
114 /***
115 * Adds a feature to the CacheListener attribute of the CacheWatchRepairable
116 * object
117 * <p>
118 * @param obj
119 * The feature to be added to the CacheListener attribute
120 * @throws IOException
121 */
122 public void addCacheListener( ICacheListener obj )
123 throws IOException
124 {
125
126
127
128 synchronized ( cacheMap )
129 {
130 for ( Iterator itr = cacheMap.values().iterator(); itr.hasNext(); )
131 {
132 Set listenerSet = (Set) itr.next();
133 listenerSet.add( obj );
134 }
135 }
136 cacheWatch.addCacheListener( obj );
137 }
138
139 /***
140 * Tell the server to release us.
141 * <p>
142 * @param cacheName
143 * @param obj
144 * @throws IOException
145 */
146 public void removeCacheListener( String cacheName, ICacheListener obj )
147 throws IOException
148 {
149 if ( log.isInfoEnabled() )
150 {
151 log.info( "removeCacheListener, cacheName [" + cacheName + "]" );
152 }
153
154
155
156 synchronized ( cacheMap )
157 {
158 Set listenerSet = (Set) cacheMap.get( cacheName );
159 if ( listenerSet != null )
160 {
161 listenerSet.remove( obj );
162 }
163 }
164 cacheWatch.removeCacheListener( cacheName, obj );
165 }
166
167 /***
168 * @param obj
169 * @throws IOException
170 */
171 public void removeCacheListener( ICacheListener obj )
172 throws IOException
173 {
174 if ( log.isInfoEnabled() )
175 {
176 log.info( "removeCacheListener, ICacheListener [" + obj + "]" );
177 }
178
179
180
181 synchronized ( cacheMap )
182 {
183 for ( Iterator itr = cacheMap.values().iterator(); itr.hasNext(); )
184 {
185 Set listenerSet = (Set) itr.next();
186 if ( log.isDebugEnabled() )
187 {
188 log.debug( "Before removing [" + obj + "] the listenerSet = " + listenerSet );
189 }
190 listenerSet.remove( obj );
191 }
192 }
193 cacheWatch.removeCacheListener( obj );
194 }
195 }