Commit 70078b67 authored by Tom Evans's avatar Tom Evans Committed by tevans

OF-588: Defer switch to clustered factory strategy until the server has joined the cluster

git-svn-id: http://svn.igniterealtime.org/svn/repos/openfire/trunk@13383 b35dd754-fafc-0310-a699-88a17e54d16e
parent 0006eeb5
...@@ -72,6 +72,7 @@ public class CacheFactory { ...@@ -72,6 +72,7 @@ public class CacheFactory {
private static String clusteredCacheFactoryClass; private static String clusteredCacheFactoryClass;
private static CacheFactoryStrategy cacheFactoryStrategy; private static CacheFactoryStrategy cacheFactoryStrategy;
private static CacheFactoryStrategy localCacheFactoryStrategy; private static CacheFactoryStrategy localCacheFactoryStrategy;
private static CacheFactoryStrategy clusteredCacheFactoryStrategy;
private static Thread statsThread; private static Thread statsThread;
public static final int DEFAULT_MAX_CACHE_SIZE = 1024 * 256; public static final int DEFAULT_MAX_CACHE_SIZE = 1024 * 256;
...@@ -407,15 +408,11 @@ public class CacheFactory { ...@@ -407,15 +408,11 @@ public class CacheFactory {
* @param cache the cache used for holding the lock. * @param cache the cache used for holding the lock.
* @return an existing lock on the specified key or creates a new one if none was found. * @return an existing lock on the specified key or creates a new one if none was found.
*/ */
public static Lock getLock(Object key, Cache cache) { public static synchronized Lock getLock(Object key, Cache cache) {
if (localOnly.contains(cache.getName())) { if (localOnly.contains(cache.getName())) {
return localCacheFactoryStrategy.getLock(key, cache); return localCacheFactoryStrategy.getLock(key, cache);
} else { } else {
// synchronized here because the backing cache return cacheFactoryStrategy.getLock(key, cache);
// will be swapped cluster startup/shutdown (OF-588)
synchronized(cache) {
return cacheFactoryStrategy.getLock(key, cache);
}
} }
} }
...@@ -604,19 +601,13 @@ public class CacheFactory { ...@@ -604,19 +601,13 @@ public class CacheFactory {
public static void startClustering() { public static void startClustering() {
try { try {
cacheFactoryStrategy = (CacheFactoryStrategy) Class.forName(clusteredCacheFactoryClass, true, clusteredCacheFactoryStrategy = (CacheFactoryStrategy) Class.forName(clusteredCacheFactoryClass, true,
getClusteredCacheStrategyClassLoader()) getClusteredCacheStrategyClassLoader()).newInstance();
.newInstance(); clusteringStarting = clusteredCacheFactoryStrategy.startCluster();
clusteringStarting = cacheFactoryStrategy.startCluster(); } catch (Exception e) {
} log.error("Clustered cache factory strategy " + clusteredCacheFactoryClass + " not found", e);
catch (Exception e) {
log.error("Unable to start clustering - continuing in local mode", e);
}
if (!clusteringStarting) {
// Revert to local cache factory if cluster fails to start
cacheFactoryStrategy = localCacheFactoryStrategy;
} }
else { if (clusteringStarting) {
if (statsThread == null) { if (statsThread == null) {
// Start a timing thread with 1 second of accuracy. // Start a timing thread with 1 second of accuracy.
statsThread = new Thread("Cache Stats") { statsThread = new Thread("Cache Stats") {
...@@ -676,7 +667,7 @@ public class CacheFactory { ...@@ -676,7 +667,7 @@ public class CacheFactory {
public static void stopClustering() { public static void stopClustering() {
// Stop the cluster // Stop the cluster
cacheFactoryStrategy.stopCluster(); clusteredCacheFactoryStrategy.stopCluster();
// Set the strategy to local // Set the strategy to local
cacheFactoryStrategy = localCacheFactoryStrategy; cacheFactoryStrategy = localCacheFactoryStrategy;
} }
...@@ -685,44 +676,39 @@ public class CacheFactory { ...@@ -685,44 +676,39 @@ public class CacheFactory {
* Notification message indicating that this JVM has joined a cluster. * Notification message indicating that this JVM has joined a cluster.
*/ */
@SuppressWarnings("unchecked") @SuppressWarnings("unchecked")
public static void joinedCluster() { public static synchronized void joinedCluster() {
cacheFactoryStrategy = clusteredCacheFactoryStrategy;
// Loop through local caches and switch them to clustered cache (purge content) // Loop through local caches and switch them to clustered cache (purge content)
for (Cache cache : getAllCaches()) { for (Cache cache : getAllCaches()) {
// skip local-only caches // skip local-only caches
if (localOnly.contains(cache.getName())) continue; if (localOnly.contains(cache.getName())) continue;
synchronized (cache) { cache.clear();
cache.clear(); CacheWrapper cacheWrapper = ((CacheWrapper) cache);
CacheWrapper cacheWrapper = ((CacheWrapper) cache); Cache clusteredCache = cacheFactoryStrategy.createCache(cacheWrapper.getName());
Cache clusteredCache = cacheFactoryStrategy.createCache(cacheWrapper.getName()); cacheWrapper.setWrappedCache(clusteredCache);
cacheWrapper.setWrappedCache(clusteredCache);
}
} }
clusteringStarting = false; clusteringStarting = false;
clusteringStarted = true; clusteringStarted = true;
log.info("Clustering started; cache migration complete");
} }
/** /**
* Notification message indicating that this JVM has left the cluster. * Notification message indicating that this JVM has left the cluster.
*/ */
@SuppressWarnings("unchecked") @SuppressWarnings("unchecked")
public static void leftCluster() { public static synchronized void leftCluster() {
clusteringStarted = false; clusteringStarted = false;
// Loop through clustered caches and change them to local caches (purge content) cacheFactoryStrategy = localCacheFactoryStrategy;
try {
cacheFactoryStrategy = localCacheFactoryStrategy;
for (Cache cache : getAllCaches()) { // Loop through clustered caches and change them to local caches (purge content)
// skip local-only caches for (Cache cache : getAllCaches()) {
if (localOnly.contains(cache.getName())) continue; // skip local-only caches
synchronized (cache) { if (localOnly.contains(cache.getName())) continue;
cache.clear(); cache.clear();
CacheWrapper cacheWrapper = ((CacheWrapper) cache); CacheWrapper cacheWrapper = ((CacheWrapper) cache);
Cache standaloneCache = cacheFactoryStrategy.createCache(cacheWrapper.getName()); Cache standaloneCache = cacheFactoryStrategy.createCache(cacheWrapper.getName());
cacheWrapper.setWrappedCache(standaloneCache); cacheWrapper.setWrappedCache(standaloneCache);
} }
} log.info("Clustering stopped; cache migration complete");
} catch (Exception e) {
log.error("Error reverting caches to local caches", e);
}
} }
} }
\ No newline at end of file
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment