Add native hints for Caffeine cache. (#1194)
This commit is contained in:
committed by
GitHub
parent
9a06eb4a05
commit
e4bd5b300b
@@ -635,7 +635,7 @@ public class MyClass {
|
||||
The Spring WebFlux can work with both reactive and non-reactive `WebClient` configurations, as the topics describe:
|
||||
|
||||
* <<webflux-with-reactive-loadbalancer>>
|
||||
* <<load-balancer-exchange-filter-functionload-balancer-exchange-filter-function>>
|
||||
* <<load-balancer-exchange-filter-function>>
|
||||
|
||||
[[webflux-with-reactive-loadbalancer]]
|
||||
==== Spring WebFlux `WebClient` with `ReactorLoadBalancerExchangeFilterFunction`
|
||||
|
||||
@@ -16,12 +16,21 @@
|
||||
|
||||
package org.springframework.cloud.loadbalancer.config;
|
||||
|
||||
import java.util.Objects;
|
||||
import java.util.Set;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
import com.github.benmanes.caffeine.cache.Caffeine;
|
||||
import com.stoyanr.evictor.ConcurrentMapWithTimedEviction;
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
|
||||
import org.springframework.aot.hint.MemberCategory;
|
||||
import org.springframework.aot.hint.RuntimeHints;
|
||||
import org.springframework.aot.hint.RuntimeHintsRegistrar;
|
||||
import org.springframework.aot.hint.TypeReference;
|
||||
import org.springframework.beans.factory.InitializingBean;
|
||||
import org.springframework.beans.factory.config.BeanDefinition;
|
||||
import org.springframework.boot.autoconfigure.AutoConfigureAfter;
|
||||
import org.springframework.boot.autoconfigure.cache.CacheAutoConfiguration;
|
||||
import org.springframework.boot.autoconfigure.condition.AllNestedConditions;
|
||||
@@ -39,8 +48,11 @@ import org.springframework.cloud.loadbalancer.cache.DefaultLoadBalancerCacheMana
|
||||
import org.springframework.cloud.loadbalancer.cache.LoadBalancerCacheManager;
|
||||
import org.springframework.cloud.loadbalancer.cache.LoadBalancerCacheProperties;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.ClassPathScanningCandidateComponentProvider;
|
||||
import org.springframework.context.annotation.Conditional;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.core.type.filter.AssignableTypeFilter;
|
||||
import org.springframework.util.ClassUtils;
|
||||
|
||||
/**
|
||||
* An AutoConfiguration that automatically enables caching when Spring Boot, and Spring
|
||||
@@ -149,3 +161,52 @@ public class LoadBalancerCacheAutoConfiguration {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// Remove after adding hints to GraalVM reachability metadata repo
|
||||
class CaffeineHints implements RuntimeHintsRegistrar {
|
||||
|
||||
private static final Log LOG = LogFactory.getLog(CaffeineHints.class);
|
||||
|
||||
private static final String CAFFEINE_BOUNDED_LOCAL_CACHE_CLASS_NAME = "com.github.benmanes.caffeine.cache.BoundedLocalCache";
|
||||
|
||||
private static final String CAFFEINE_CACHE_BASE_PACKAGE = "com/github/benmanes/caffeine/cache";
|
||||
|
||||
private static final String CAFFEINE_NODE_CLASS_NAME = "com.github.benmanes.caffeine.cache.Node";
|
||||
|
||||
@Override
|
||||
public void registerHints(RuntimeHints hints, ClassLoader classLoader) {
|
||||
if (!ClassUtils.isPresent("com.github.benmanes.caffeine.cache.Caffeine", classLoader)) {
|
||||
return;
|
||||
}
|
||||
hints.reflection()
|
||||
.registerType(TypeReference.of(Caffeine.class),
|
||||
hint -> hint.withMembers(MemberCategory.INVOKE_DECLARED_METHODS,
|
||||
MemberCategory.INVOKE_DECLARED_CONSTRUCTORS, MemberCategory.DECLARED_FIELDS))
|
||||
.registerType(TypeReference.of("com.github.benmanes.caffeine.cache.BoundedLocalCache"),
|
||||
hint -> hint.withMembers(MemberCategory.INVOKE_DECLARED_METHODS,
|
||||
MemberCategory.INVOKE_DECLARED_CONSTRUCTORS, MemberCategory.DECLARED_FIELDS))
|
||||
.registerType(TypeReference.of("com.github.benmanes.caffeine.cache.LocalCacheFactory"),
|
||||
hint -> hint.withMembers(MemberCategory.INVOKE_DECLARED_METHODS,
|
||||
MemberCategory.INVOKE_DECLARED_CONSTRUCTORS, MemberCategory.DECLARED_FIELDS))
|
||||
.registerType(TypeReference.of("com.github.benmanes.caffeine.cache.Node"),
|
||||
hint -> hint.withMembers(MemberCategory.INVOKE_DECLARED_METHODS,
|
||||
MemberCategory.INVOKE_DECLARED_CONSTRUCTORS, MemberCategory.DECLARED_FIELDS));
|
||||
getCaffeineSubtypes().forEach(cacheType -> hints.reflection().registerType(TypeReference.of(cacheType),
|
||||
hint -> hint.withMembers(MemberCategory.INVOKE_DECLARED_METHODS,
|
||||
MemberCategory.INVOKE_DECLARED_CONSTRUCTORS, MemberCategory.DECLARED_FIELDS)));
|
||||
}
|
||||
|
||||
private Set<String> getCaffeineSubtypes() {
|
||||
ClassPathScanningCandidateComponentProvider provider = new ClassPathScanningCandidateComponentProvider(false);
|
||||
try {
|
||||
provider.addIncludeFilter(new AssignableTypeFilter(Class.forName(CAFFEINE_BOUNDED_LOCAL_CACHE_CLASS_NAME)));
|
||||
provider.addIncludeFilter(new AssignableTypeFilter(Class.forName(CAFFEINE_NODE_CLASS_NAME)));
|
||||
}
|
||||
catch (ClassNotFoundException e) {
|
||||
LOG.warn("Could not get class for name: " + CAFFEINE_BOUNDED_LOCAL_CACHE_CLASS_NAME);
|
||||
}
|
||||
return provider.findCandidateComponents(CAFFEINE_CACHE_BASE_PACKAGE).stream().filter(Objects::nonNull)
|
||||
.map(BeanDefinition::getBeanClassName).filter(Objects::nonNull).collect(Collectors.toSet());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -0,0 +1,2 @@
|
||||
org.springframework.aot.hint.RuntimeHintsRegistrar=\
|
||||
org.springframework.cloud.loadbalancer.config.CaffeineHints
|
||||
@@ -38,7 +38,6 @@ import static org.assertj.core.api.Assertions.assertThat;
|
||||
*
|
||||
* @author Olga Maciaszek-Sharma
|
||||
*/
|
||||
|
||||
class LoadBalancerCacheAutoConfigurationTests {
|
||||
|
||||
@Test
|
||||
|
||||
Reference in New Issue
Block a user