-
Notifications
You must be signed in to change notification settings - Fork 1.6k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
fix #447: Allow the CaffeineCachingProvider to be used with OSGi DS
* annotated CaffeineCachingProvider to make it an OSGi service * when running in an OSGi container, set the CaffeineCachingProvider's classloader as the Thread context classloader for every API call on the provided CacheManagerImpl - this makes sure that the default config is read from the bundle; the default classloader will do a fallback to the app classloader, allowing to override / define configurations * added an OSGi DS test * made the bnd build reproducible (no extra bundle headers)
- Loading branch information
1 parent
ecd5e13
commit ac014b5
Showing
6 changed files
with
165 additions
and
68 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -37,9 +37,13 @@ | |
import javax.cache.spi.CachingProvider; | ||
|
||
import org.checkerframework.checker.nullness.qual.Nullable; | ||
import org.osgi.service.component.annotations.Activate; | ||
import org.osgi.service.component.annotations.Component; | ||
|
||
import com.github.benmanes.caffeine.jcache.CacheManagerImpl; | ||
import com.github.benmanes.caffeine.jcache.configuration.TypesafeConfigurator; | ||
import com.google.errorprone.annotations.concurrent.GuardedBy; | ||
import com.typesafe.config.ConfigFactory; | ||
|
||
/** | ||
* A provider that produces a JCache implementation backed by Caffeine. Typically this provider is | ||
|
@@ -53,13 +57,16 @@ | |
* | ||
* @author [email protected] (Ben Manes) | ||
*/ | ||
@Component | ||
public final class CaffeineCachingProvider implements CachingProvider { | ||
private static final ClassLoader DEFAULT_CLASS_LOADER = AccessController.doPrivileged( | ||
(PrivilegedAction<ClassLoader>) JCacheClassLoader::new); | ||
|
||
@GuardedBy("itself") | ||
private final Map<ClassLoader, Map<URI, CacheManager>> cacheManagers; | ||
|
||
private boolean isOsgiComponent; | ||
|
||
public CaffeineCachingProvider() { | ||
this.cacheManagers = new WeakHashMap<>(1); | ||
} | ||
|
@@ -165,11 +172,15 @@ private ClassLoader getManagerClassLoader(ClassLoader classLoader) { | |
*/ | ||
private static final class JCacheClassLoader extends ClassLoader { | ||
|
||
public JCacheClassLoader() { | ||
super(Thread.currentThread().getContextClassLoader()); | ||
} | ||
|
||
@Override | ||
public Class<?> loadClass(String name) throws ClassNotFoundException { | ||
ClassLoader contextClassLoader = Thread.currentThread().getContextClassLoader(); | ||
ClassNotFoundException error = null; | ||
if (contextClassLoader != null) { | ||
if (contextClassLoader != null && contextClassLoader != DEFAULT_CLASS_LOADER) { | ||
try { | ||
return contextClassLoader.loadClass(name); | ||
} catch (ClassNotFoundException e) { | ||
|
@@ -179,29 +190,43 @@ public Class<?> loadClass(String name) throws ClassNotFoundException { | |
|
||
ClassLoader classClassLoader = getClass().getClassLoader(); | ||
if ((classClassLoader != null) && (classClassLoader != contextClassLoader)) { | ||
return classClassLoader.loadClass(name); | ||
try { | ||
return classClassLoader.loadClass(name); | ||
} catch (ClassNotFoundException e) { | ||
error = e; | ||
} | ||
} | ||
|
||
ClassLoader parentClassLoader = getParent(); | ||
if (parentClassLoader != null && parentClassLoader != contextClassLoader && parentClassLoader != classClassLoader) { | ||
return parentClassLoader.loadClass(name); | ||
} | ||
throw (error == null) ? new ClassNotFoundException(name) : error; | ||
} | ||
|
||
@Override | ||
public @Nullable URL getResource(String name) { | ||
ClassLoader contextClassLoader = Thread.currentThread().getContextClassLoader(); | ||
if (contextClassLoader != null) { | ||
if (contextClassLoader != null && contextClassLoader != DEFAULT_CLASS_LOADER) { | ||
URL resource = contextClassLoader.getResource(name); | ||
if (resource != null) { | ||
return resource; | ||
} | ||
} | ||
|
||
ClassLoader classClassLoader = Thread.currentThread().getContextClassLoader(); | ||
ClassLoader classClassLoader = getClass().getClassLoader(); | ||
if ((classClassLoader != null) && (classClassLoader != contextClassLoader)) { | ||
URL resource = classClassLoader.getResource(name); | ||
if (resource != null) { | ||
return resource; | ||
} | ||
} | ||
|
||
ClassLoader parentClassLoader = getParent(); | ||
if (parentClassLoader != null && parentClassLoader != contextClassLoader && parentClassLoader != classClassLoader) { | ||
return parentClassLoader.getResource(name); | ||
} | ||
|
||
return null; | ||
} | ||
|
||
|
@@ -210,16 +235,33 @@ public Enumeration<URL> getResources(String name) throws IOException { | |
List<URL> resources = new ArrayList<>(); | ||
|
||
ClassLoader contextClassLoader = Thread.currentThread().getContextClassLoader(); | ||
if (contextClassLoader != null) { | ||
if (contextClassLoader != null && contextClassLoader != DEFAULT_CLASS_LOADER) { | ||
resources.addAll(Collections.list(contextClassLoader.getResources(name))); | ||
} | ||
|
||
ClassLoader classClassLoader = Thread.currentThread().getContextClassLoader(); | ||
ClassLoader classClassLoader = getClass().getClassLoader(); | ||
if ((classClassLoader != null) && (classClassLoader != contextClassLoader)) { | ||
resources.addAll(Collections.list(classClassLoader.getResources(name))); | ||
} | ||
|
||
ClassLoader parentClassLoader = getParent(); | ||
if (parentClassLoader != null && parentClassLoader != contextClassLoader && parentClassLoader != classClassLoader) { | ||
resources.addAll(Collections.list(parentClassLoader.getResources(name))); | ||
} | ||
|
||
return Collections.enumeration(resources); | ||
} | ||
} | ||
|
||
@Activate | ||
@SuppressWarnings("unused") | ||
private void activate() { | ||
isOsgiComponent = true; | ||
TypesafeConfigurator.setConfigSource(() -> ConfigFactory.load(DEFAULT_CLASS_LOADER)); | ||
} | ||
|
||
public boolean isOsgiComponent() { | ||
return isOsgiComponent; | ||
} | ||
|
||
} |
Oops, something went wrong.