CAMEL-11321: Start Camel faster by letting LRUCache warmup concurrently as that takes up 150 millis or more.
Project: http://git-wip-us.apache.org/repos/asf/camel/repo Commit: http://git-wip-us.apache.org/repos/asf/camel/commit/847241f0 Tree: http://git-wip-us.apache.org/repos/asf/camel/tree/847241f0 Diff: http://git-wip-us.apache.org/repos/asf/camel/diff/847241f0 Branch: refs/heads/master Commit: 847241f0222e3d9c736e69b699cb692e54497a0b Parents: f8e68ba Author: Claus Ibsen <davscl...@apache.org> Authored: Tue Jul 4 18:07:34 2017 +0200 Committer: Claus Ibsen <davscl...@apache.org> Committed: Wed Jul 5 09:28:22 2017 +0200 ---------------------------------------------------------------------- .../camel/component/bean/BeanComponent.java | 4 +- .../camel/component/bean/MethodInfoCache.java | 4 +- .../component/file/GenericFileProducer.java | 10 ++- .../properties/PropertiesComponent.java | 4 +- .../org/apache/camel/impl/ConsumerCache.java | 4 +- .../DefaultEndpointUtilizationStatistics.java | 4 +- .../impl/DefaultPackageScanClassResolver.java | 1 - .../impl/DefaultRuntimeEndpointRegistry.java | 4 +- .../org/apache/camel/impl/ProducerCache.java | 4 +- .../converter/BaseTypeConverterRegistry.java | 4 +- .../converter/PropertyEditorTypeConverter.java | 4 +- .../camel/language/simple/SimpleLanguage.java | 6 +- .../camel/management/MBeanInfoAssembler.java | 5 +- .../processor/aggregate/AggregateProcessor.java | 4 +- .../idempotent/FileIdempotentRepository.java | 16 ++-- .../idempotent/MemoryIdempotentRepository.java | 10 ++- .../camel/support/ReloadStrategySupport.java | 6 +- .../apache/camel/util/IntrospectionSupport.java | 3 +- .../java/org/apache/camel/util/LRUCache.java | 3 + .../org/apache/camel/util/LRUCacheFactory.java | 90 ++++++++++++++++---- .../org/apache/camel/util/LRUSoftCache.java | 3 + .../org/apache/camel/util/LRUWeakCache.java | 3 + .../camel/impl/DefaultCamelContextTest.java | 1 + .../camel/model/ModelSanityCheckerTest.java | 5 +- 24 files changed, 155 insertions(+), 47 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/camel/blob/847241f0/camel-core/src/main/java/org/apache/camel/component/bean/BeanComponent.java ---------------------------------------------------------------------- diff --git a/camel-core/src/main/java/org/apache/camel/component/bean/BeanComponent.java b/camel-core/src/main/java/org/apache/camel/component/bean/BeanComponent.java index fb3ecb4..bfffc4c 100644 --- a/camel-core/src/main/java/org/apache/camel/component/bean/BeanComponent.java +++ b/camel-core/src/main/java/org/apache/camel/component/bean/BeanComponent.java @@ -21,6 +21,7 @@ import java.util.Map; import org.apache.camel.Endpoint; import org.apache.camel.impl.UriEndpointComponent; import org.apache.camel.util.IntrospectionSupport; +import org.apache.camel.util.LRUCacheFactory; import org.apache.camel.util.LRUSoftCache; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -33,7 +34,8 @@ public class BeanComponent extends UriEndpointComponent { private static final Logger LOG = LoggerFactory.getLogger(BeanComponent.class); // use an internal soft cache for BeanInfo as they are costly to introspect // for example the bean language using OGNL expression runs much faster reusing the BeanInfo from this cache - private final LRUSoftCache<BeanInfoCacheKey, BeanInfo> cache = new LRUSoftCache<BeanInfoCacheKey, BeanInfo>(1000); + @SuppressWarnings("unchecked") + private final LRUSoftCache<BeanInfoCacheKey, BeanInfo> cache = LRUCacheFactory.newLRUSoftCache(1000); public BeanComponent() { super(BeanEndpoint.class); http://git-wip-us.apache.org/repos/asf/camel/blob/847241f0/camel-core/src/main/java/org/apache/camel/component/bean/MethodInfoCache.java ---------------------------------------------------------------------- diff --git a/camel-core/src/main/java/org/apache/camel/component/bean/MethodInfoCache.java b/camel-core/src/main/java/org/apache/camel/component/bean/MethodInfoCache.java index 527ddd9..33f8608 100644 --- a/camel-core/src/main/java/org/apache/camel/component/bean/MethodInfoCache.java +++ b/camel-core/src/main/java/org/apache/camel/component/bean/MethodInfoCache.java @@ -20,6 +20,7 @@ import java.lang.reflect.Method; import java.util.Map; import org.apache.camel.CamelContext; +import org.apache.camel.util.LRUCacheFactory; import org.apache.camel.util.LRUSoftCache; /** @@ -75,9 +76,10 @@ public class MethodInfoCache { return new BeanInfo(camelContext, declaringClass); } + @SuppressWarnings("unchecked") protected static <K, V> Map<K, V> createLruCache(int size) { // use a soft cache - return new LRUSoftCache<K, V>(size); + return LRUCacheFactory.newLRUSoftCache(size); } private static Map<Class<?>, BeanInfo> createClassCache(int size) { http://git-wip-us.apache.org/repos/asf/camel/blob/847241f0/camel-core/src/main/java/org/apache/camel/component/file/GenericFileProducer.java ---------------------------------------------------------------------- diff --git a/camel-core/src/main/java/org/apache/camel/component/file/GenericFileProducer.java b/camel-core/src/main/java/org/apache/camel/component/file/GenericFileProducer.java index a4769ec..d96884b 100644 --- a/camel-core/src/main/java/org/apache/camel/component/file/GenericFileProducer.java +++ b/camel-core/src/main/java/org/apache/camel/component/file/GenericFileProducer.java @@ -26,6 +26,7 @@ import org.apache.camel.impl.DefaultExchange; import org.apache.camel.impl.DefaultProducer; import org.apache.camel.util.FileUtil; import org.apache.camel.util.LRUCache; +import org.apache.camel.util.LRUCacheFactory; import org.apache.camel.util.ObjectHelper; import org.apache.camel.util.ServiceHelper; import org.apache.camel.util.StringHelper; @@ -40,14 +41,14 @@ public class GenericFileProducer<T> extends DefaultProducer { protected final GenericFileEndpoint<T> endpoint; protected GenericFileOperations<T> operations; // assume writing to 100 different files concurrently at most for the same file producer - private final LRUCache<String, Lock> locks = new LRUCache<String, Lock>(100); + private final LRUCache<String, Lock> locks = LRUCacheFactory.newLRUCache(100); protected GenericFileProducer(GenericFileEndpoint<T> endpoint, GenericFileOperations<T> operations) { super(endpoint); this.endpoint = endpoint; this.operations = operations; } - + public String getFileSeparator() { return File.separator; } @@ -396,14 +397,15 @@ public class GenericFileProducer<T> extends DefaultProducer { } @Override + @SuppressWarnings("unchecked") protected void doStart() throws Exception { - super.doStart(); ServiceHelper.startService(locks); + super.doStart(); } @Override protected void doStop() throws Exception { - ServiceHelper.stopService(locks); super.doStop(); + ServiceHelper.stopService(locks); } } http://git-wip-us.apache.org/repos/asf/camel/blob/847241f0/camel-core/src/main/java/org/apache/camel/component/properties/PropertiesComponent.java ---------------------------------------------------------------------- diff --git a/camel-core/src/main/java/org/apache/camel/component/properties/PropertiesComponent.java b/camel-core/src/main/java/org/apache/camel/component/properties/PropertiesComponent.java index b26cdac..2b6194a 100644 --- a/camel-core/src/main/java/org/apache/camel/component/properties/PropertiesComponent.java +++ b/camel-core/src/main/java/org/apache/camel/component/properties/PropertiesComponent.java @@ -31,6 +31,7 @@ import org.apache.camel.Endpoint; import org.apache.camel.impl.UriEndpointComponent; import org.apache.camel.spi.Metadata; import org.apache.camel.util.FilePathResolver; +import org.apache.camel.util.LRUCacheFactory; import org.apache.camel.util.LRUSoftCache; import org.apache.camel.util.ObjectHelper; import org.slf4j.Logger; @@ -90,7 +91,8 @@ public class PropertiesComponent extends UriEndpointComponent { public static final String OVERRIDE_PROPERTIES = PropertiesComponent.class.getName() + ".OverrideProperties"; private static final Logger LOG = LoggerFactory.getLogger(PropertiesComponent.class); - private final Map<CacheKey, Properties> cacheMap = new LRUSoftCache<CacheKey, Properties>(1000); + @SuppressWarnings("unchecked") + private final Map<CacheKey, Properties> cacheMap = LRUCacheFactory.newLRUSoftCache(1000); private final Map<String, PropertiesFunction> functions = new HashMap<String, PropertiesFunction>(); private PropertiesResolver propertiesResolver = new DefaultPropertiesResolver(this); private PropertiesParser propertiesParser = new DefaultPropertiesParser(this); http://git-wip-us.apache.org/repos/asf/camel/blob/847241f0/camel-core/src/main/java/org/apache/camel/impl/ConsumerCache.java ---------------------------------------------------------------------- diff --git a/camel-core/src/main/java/org/apache/camel/impl/ConsumerCache.java b/camel-core/src/main/java/org/apache/camel/impl/ConsumerCache.java index 4cb8ef4..7864bf9 100644 --- a/camel-core/src/main/java/org/apache/camel/impl/ConsumerCache.java +++ b/camel-core/src/main/java/org/apache/camel/impl/ConsumerCache.java @@ -31,6 +31,7 @@ import org.apache.camel.spi.ServicePool; import org.apache.camel.support.ServiceSupport; import org.apache.camel.util.CamelContextHelper; import org.apache.camel.util.LRUCache; +import org.apache.camel.util.LRUCacheFactory; import org.apache.camel.util.ServiceHelper; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -100,12 +101,13 @@ public class ConsumerCache extends ServiceSupport { * @param cacheSize the cache size * @return the cache */ + @SuppressWarnings("unchecked") protected static LRUCache<String, PollingConsumer> createLRUCache(int cacheSize) { // Use a regular cache as we want to ensure that the lifecycle of the consumers // being cache is properly handled, such as they are stopped when being evicted // or when this cache is stopped. This is needed as some consumers requires to // be stopped so they can shutdown internal resources that otherwise may cause leaks - return new LRUCache<String, PollingConsumer>(cacheSize); + return LRUCacheFactory.newLRUCache(cacheSize); } /** http://git-wip-us.apache.org/repos/asf/camel/blob/847241f0/camel-core/src/main/java/org/apache/camel/impl/DefaultEndpointUtilizationStatistics.java ---------------------------------------------------------------------- diff --git a/camel-core/src/main/java/org/apache/camel/impl/DefaultEndpointUtilizationStatistics.java b/camel-core/src/main/java/org/apache/camel/impl/DefaultEndpointUtilizationStatistics.java index 14efe2b..f849728 100644 --- a/camel-core/src/main/java/org/apache/camel/impl/DefaultEndpointUtilizationStatistics.java +++ b/camel-core/src/main/java/org/apache/camel/impl/DefaultEndpointUtilizationStatistics.java @@ -21,13 +21,15 @@ import java.util.Map; import org.apache.camel.spi.EndpointUtilizationStatistics; import org.apache.camel.util.LRUCache; +import org.apache.camel.util.LRUCacheFactory; public class DefaultEndpointUtilizationStatistics implements EndpointUtilizationStatistics { private final LRUCache<String, Long> map; + @SuppressWarnings("unchecked") public DefaultEndpointUtilizationStatistics(int maxCapacity) { - this.map = new LRUCache<String, Long>(16, maxCapacity, false); + this.map = LRUCacheFactory.newLRUCache(16, maxCapacity, false); } @Override http://git-wip-us.apache.org/repos/asf/camel/blob/847241f0/camel-core/src/main/java/org/apache/camel/impl/DefaultPackageScanClassResolver.java ---------------------------------------------------------------------- diff --git a/camel-core/src/main/java/org/apache/camel/impl/DefaultPackageScanClassResolver.java b/camel-core/src/main/java/org/apache/camel/impl/DefaultPackageScanClassResolver.java index 13dfa3d..202fe70 100644 --- a/camel-core/src/main/java/org/apache/camel/impl/DefaultPackageScanClassResolver.java +++ b/camel-core/src/main/java/org/apache/camel/impl/DefaultPackageScanClassResolver.java @@ -393,7 +393,6 @@ public class DefaultPackageScanClassResolver extends ServiceSupport implements P private void loadImplementationsInJar(PackageScanFilter test, String parent, InputStream stream, String urlPath, Set<Class<?>> classes, Map<String, List<String>> jarCache) { ObjectHelper.notNull(classes, "classes"); - ObjectHelper.notNull(jarCache, "jarCache"); List<String> entries = jarCache != null ? jarCache.get(urlPath) : null; if (entries == null) { http://git-wip-us.apache.org/repos/asf/camel/blob/847241f0/camel-core/src/main/java/org/apache/camel/impl/DefaultRuntimeEndpointRegistry.java ---------------------------------------------------------------------- diff --git a/camel-core/src/main/java/org/apache/camel/impl/DefaultRuntimeEndpointRegistry.java b/camel-core/src/main/java/org/apache/camel/impl/DefaultRuntimeEndpointRegistry.java index 706424f..3d5c4fe 100644 --- a/camel-core/src/main/java/org/apache/camel/impl/DefaultRuntimeEndpointRegistry.java +++ b/camel-core/src/main/java/org/apache/camel/impl/DefaultRuntimeEndpointRegistry.java @@ -39,6 +39,7 @@ import org.apache.camel.spi.RuntimeEndpointRegistry; import org.apache.camel.spi.UnitOfWork; import org.apache.camel.support.EventNotifierSupport; import org.apache.camel.util.LRUCache; +import org.apache.camel.util.LRUCacheFactory; import org.apache.camel.util.ObjectHelper; import org.apache.camel.util.ServiceHelper; @@ -211,6 +212,7 @@ public class DefaultRuntimeEndpointRegistry extends EventNotifierSupport impleme } @Override + @SuppressWarnings("unchecked") public void notify(EventObject event) throws Exception { if (event instanceof RouteAddedEvent) { RouteAddedEvent rse = (RouteAddedEvent) event; @@ -223,7 +225,7 @@ public class DefaultRuntimeEndpointRegistry extends EventNotifierSupport impleme inputs.put(routeId, uris); // use a LRUCache for outputs as we could potential have unlimited uris if dynamic routing is in use // and therefore need to have the limit in use - outputs.put(routeId, new LRUCache<String, String>(limit)); + outputs.put(routeId, LRUCacheFactory.newLRUCache(limit)); } else if (event instanceof RouteRemovedEvent) { RouteRemovedEvent rse = (RouteRemovedEvent) event; String routeId = rse.getRoute().getId(); http://git-wip-us.apache.org/repos/asf/camel/blob/847241f0/camel-core/src/main/java/org/apache/camel/impl/ProducerCache.java ---------------------------------------------------------------------- diff --git a/camel-core/src/main/java/org/apache/camel/impl/ProducerCache.java b/camel-core/src/main/java/org/apache/camel/impl/ProducerCache.java index 285f1ab..cc31dee 100644 --- a/camel-core/src/main/java/org/apache/camel/impl/ProducerCache.java +++ b/camel-core/src/main/java/org/apache/camel/impl/ProducerCache.java @@ -40,6 +40,7 @@ import org.apache.camel.util.AsyncProcessorConverterHelper; import org.apache.camel.util.CamelContextHelper; import org.apache.camel.util.EventHelper; import org.apache.camel.util.LRUCache; +import org.apache.camel.util.LRUCacheFactory; import org.apache.camel.util.ServiceHelper; import org.apache.camel.util.StopWatch; import org.slf4j.Logger; @@ -134,12 +135,13 @@ public class ProducerCache extends ServiceSupport { * @param cacheSize the cache size * @return the cache */ + @SuppressWarnings("unchecked") protected static LRUCache<String, Producer> createLRUCache(int cacheSize) { // Use a regular cache as we want to ensure that the lifecycle of the producers // being cache is properly handled, such as they are stopped when being evicted // or when this cache is stopped. This is needed as some producers requires to // be stopped so they can shutdown internal resources that otherwise may cause leaks - return new LRUCache<String, Producer>(cacheSize); + return LRUCacheFactory.newLRUCache(cacheSize); } public CamelContext getCamelContext() { http://git-wip-us.apache.org/repos/asf/camel/blob/847241f0/camel-core/src/main/java/org/apache/camel/impl/converter/BaseTypeConverterRegistry.java ---------------------------------------------------------------------- diff --git a/camel-core/src/main/java/org/apache/camel/impl/converter/BaseTypeConverterRegistry.java b/camel-core/src/main/java/org/apache/camel/impl/converter/BaseTypeConverterRegistry.java index bdd9f98..28a1d12 100644 --- a/camel-core/src/main/java/org/apache/camel/impl/converter/BaseTypeConverterRegistry.java +++ b/camel-core/src/main/java/org/apache/camel/impl/converter/BaseTypeConverterRegistry.java @@ -50,6 +50,7 @@ import org.apache.camel.spi.TypeConverterLoader; import org.apache.camel.spi.TypeConverterRegistry; import org.apache.camel.support.ServiceSupport; import org.apache.camel.util.CamelLogger; +import org.apache.camel.util.LRUCacheFactory; import org.apache.camel.util.LRUSoftCache; import org.apache.camel.util.MessageHelper; import org.apache.camel.util.ObjectHelper; @@ -67,7 +68,8 @@ public abstract class BaseTypeConverterRegistry extends ServiceSupport implement protected final OptimisedTypeConverter optimisedTypeConverter = new OptimisedTypeConverter(); protected final ConcurrentMap<TypeMapping, TypeConverter> typeMappings = new ConcurrentHashMap<TypeMapping, TypeConverter>(); // for misses use a soft reference cache map, as the classes may be un-deployed at runtime - protected final LRUSoftCache<TypeMapping, TypeMapping> misses = new LRUSoftCache<TypeMapping, TypeMapping>(1000); + @SuppressWarnings("unchecked") + protected final LRUSoftCache<TypeMapping, TypeMapping> misses = LRUCacheFactory.newLRUSoftCache(1000); protected final List<TypeConverterLoader> typeConverterLoaders = new ArrayList<TypeConverterLoader>(); protected final List<FallbackTypeConverter> fallbackConverters = new CopyOnWriteArrayList<FallbackTypeConverter>(); protected final PackageScanClassResolver resolver; http://git-wip-us.apache.org/repos/asf/camel/blob/847241f0/camel-core/src/main/java/org/apache/camel/impl/converter/PropertyEditorTypeConverter.java ---------------------------------------------------------------------- diff --git a/camel-core/src/main/java/org/apache/camel/impl/converter/PropertyEditorTypeConverter.java b/camel-core/src/main/java/org/apache/camel/impl/converter/PropertyEditorTypeConverter.java index 635f734..2e8ab0d 100644 --- a/camel-core/src/main/java/org/apache/camel/impl/converter/PropertyEditorTypeConverter.java +++ b/camel-core/src/main/java/org/apache/camel/impl/converter/PropertyEditorTypeConverter.java @@ -23,6 +23,7 @@ import java.util.Map; import org.apache.camel.Exchange; import org.apache.camel.TypeConverter; +import org.apache.camel.util.LRUCacheFactory; import org.apache.camel.util.LRUSoftCache; import org.apache.camel.util.ObjectHelper; import org.slf4j.Logger; @@ -42,7 +43,8 @@ public class PropertyEditorTypeConverter implements TypeConverter { private static final Logger LOG = LoggerFactory.getLogger(PropertyEditorTypeConverter.class); // use a soft bound cache to avoid using too much memory in case a lot of different classes // is being converted to string - private final Map<Class<?>, Class<?>> misses = new LRUSoftCache<Class<?>, Class<?>>(1000); + @SuppressWarnings("unchecked") + private final Map<Class<?>, Class<?>> misses = LRUCacheFactory.newLRUSoftCache(1000); // we don't anticipate so many property editors so we have unbounded map private final Map<Class<?>, PropertyEditor> cache = new HashMap<Class<?>, PropertyEditor>(); http://git-wip-us.apache.org/repos/asf/camel/blob/847241f0/camel-core/src/main/java/org/apache/camel/language/simple/SimpleLanguage.java ---------------------------------------------------------------------- diff --git a/camel-core/src/main/java/org/apache/camel/language/simple/SimpleLanguage.java b/camel-core/src/main/java/org/apache/camel/language/simple/SimpleLanguage.java index 1767dc3..de4fc92 100644 --- a/camel-core/src/main/java/org/apache/camel/language/simple/SimpleLanguage.java +++ b/camel-core/src/main/java/org/apache/camel/language/simple/SimpleLanguage.java @@ -23,6 +23,7 @@ import org.apache.camel.builder.ExpressionBuilder; import org.apache.camel.support.LanguageSupport; import org.apache.camel.util.CamelContextHelper; import org.apache.camel.util.LRUCache; +import org.apache.camel.util.LRUCacheFactory; import org.apache.camel.util.ObjectHelper; import org.apache.camel.util.PredicateToExpressionAdapter; import org.slf4j.Logger; @@ -112,13 +113,14 @@ public class SimpleLanguage extends LanguageSupport implements StaticService { } @Override + @SuppressWarnings("unchecked") public void start() throws Exception { // setup cache which requires CamelContext to be set first if (cacheExpression == null && cachePredicate == null && getCamelContext() != null) { int maxSize = CamelContextHelper.getMaximumSimpleCacheSize(getCamelContext()); if (maxSize > 0) { - cacheExpression = new LRUCache<>(16, maxSize, false); - cachePredicate = new LRUCache<>(16, maxSize, false); + cacheExpression = LRUCacheFactory.newLRUCache(16, maxSize, false); + cachePredicate = LRUCacheFactory.newLRUCache(16, maxSize, false); LOG.debug("Simple language predicate/expression cache size: {}", maxSize); } else { LOG.debug("Simple language disabled predicate/expression cache"); http://git-wip-us.apache.org/repos/asf/camel/blob/847241f0/camel-core/src/main/java/org/apache/camel/management/MBeanInfoAssembler.java ---------------------------------------------------------------------- diff --git a/camel-core/src/main/java/org/apache/camel/management/MBeanInfoAssembler.java b/camel-core/src/main/java/org/apache/camel/management/MBeanInfoAssembler.java index 4dfb0b7..07713a1 100644 --- a/camel-core/src/main/java/org/apache/camel/management/MBeanInfoAssembler.java +++ b/camel-core/src/main/java/org/apache/camel/management/MBeanInfoAssembler.java @@ -41,7 +41,6 @@ import org.apache.camel.api.management.ManagedResource; import org.apache.camel.util.IntrospectionSupport; import org.apache.camel.util.LRUCache; import org.apache.camel.util.LRUCacheFactory; -import org.apache.camel.util.LRUWeakCache; import org.apache.camel.util.ObjectHelper; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -78,7 +77,9 @@ public class MBeanInfoAssembler implements Service { if (LOG.isDebugEnabled()) { LOG.debug("Clearing cache[size={}, hits={}, misses={}, evicted={}]", new Object[]{cache.size(), cache.getHits(), cache.getMisses(), cache.getEvicted()}); } - cache.clear(); + if (cache != null) { + cache.clear(); + } } /** http://git-wip-us.apache.org/repos/asf/camel/blob/847241f0/camel-core/src/main/java/org/apache/camel/processor/aggregate/AggregateProcessor.java ---------------------------------------------------------------------- diff --git a/camel-core/src/main/java/org/apache/camel/processor/aggregate/AggregateProcessor.java b/camel-core/src/main/java/org/apache/camel/processor/aggregate/AggregateProcessor.java index bd1b9ed..53d048d 100644 --- a/camel-core/src/main/java/org/apache/camel/processor/aggregate/AggregateProcessor.java +++ b/camel-core/src/main/java/org/apache/camel/processor/aggregate/AggregateProcessor.java @@ -62,6 +62,7 @@ import org.apache.camel.support.ServiceSupport; import org.apache.camel.util.AsyncProcessorHelper; import org.apache.camel.util.ExchangeHelper; import org.apache.camel.util.LRUCache; +import org.apache.camel.util.LRUCacheFactory; import org.apache.camel.util.ObjectHelper; import org.apache.camel.util.ServiceHelper; import org.apache.camel.util.StopWatch; @@ -1283,6 +1284,7 @@ public class AggregateProcessor extends ServiceSupport implements AsyncProcessor } @Override + @SuppressWarnings("unchecked") protected void doStart() throws Exception { AggregationStrategy strategy = aggregationStrategy; if (strategy instanceof DelegateAggregationStrategy) { @@ -1306,7 +1308,7 @@ public class AggregateProcessor extends ServiceSupport implements AsyncProcessor if (getCloseCorrelationKeyOnCompletion() != null) { if (getCloseCorrelationKeyOnCompletion() > 0) { LOG.info("Using ClosedCorrelationKeys with a LRUCache with a capacity of " + getCloseCorrelationKeyOnCompletion()); - closedCorrelationKeys = new LRUCache<String, String>(getCloseCorrelationKeyOnCompletion()); + closedCorrelationKeys = LRUCacheFactory.newLRUCache(getCloseCorrelationKeyOnCompletion()); } else { LOG.info("Using ClosedCorrelationKeys with unbounded capacity"); closedCorrelationKeys = new ConcurrentHashMap<String, String>(); http://git-wip-us.apache.org/repos/asf/camel/blob/847241f0/camel-core/src/main/java/org/apache/camel/processor/idempotent/FileIdempotentRepository.java ---------------------------------------------------------------------- diff --git a/camel-core/src/main/java/org/apache/camel/processor/idempotent/FileIdempotentRepository.java b/camel-core/src/main/java/org/apache/camel/processor/idempotent/FileIdempotentRepository.java index a6352c2..f452346 100644 --- a/camel-core/src/main/java/org/apache/camel/processor/idempotent/FileIdempotentRepository.java +++ b/camel-core/src/main/java/org/apache/camel/processor/idempotent/FileIdempotentRepository.java @@ -31,6 +31,7 @@ import org.apache.camel.support.ServiceSupport; import org.apache.camel.util.FileUtil; import org.apache.camel.util.IOHelper; import org.apache.camel.util.LRUCache; +import org.apache.camel.util.LRUCacheFactory; import org.apache.camel.util.ObjectHelper; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -53,8 +54,6 @@ public class FileIdempotentRepository extends ServiceSupport implements Idempote private AtomicBoolean init = new AtomicBoolean(); public FileIdempotentRepository() { - // default use a 1st level cache - this.cache = new LRUCache<String, Object>(1000); } public FileIdempotentRepository(File fileStore, Map<String, Object> set) { @@ -79,8 +78,9 @@ public class FileIdempotentRepository extends ServiceSupport implements Idempote * @param fileStore the file store * @param cacheSize the cache size */ + @SuppressWarnings("unchecked") public static IdempotentRepository<String> fileIdempotentRepository(File fileStore, int cacheSize) { - return fileIdempotentRepository(fileStore, new LRUCache<String, Object>(cacheSize)); + return fileIdempotentRepository(fileStore, LRUCacheFactory.newLRUCache(cacheSize)); } /** @@ -91,8 +91,9 @@ public class FileIdempotentRepository extends ServiceSupport implements Idempote * @param cacheSize the cache size * @param maxFileStoreSize the max size in bytes for the filestore file */ + @SuppressWarnings("unchecked") public static IdempotentRepository<String> fileIdempotentRepository(File fileStore, int cacheSize, long maxFileStoreSize) { - FileIdempotentRepository repository = new FileIdempotentRepository(fileStore, new LRUCache<String, Object>(cacheSize)); + FileIdempotentRepository repository = new FileIdempotentRepository(fileStore, LRUCacheFactory.newLRUCache(cacheSize)); repository.setMaxFileStoreSize(maxFileStoreSize); return repository; } @@ -203,11 +204,12 @@ public class FileIdempotentRepository extends ServiceSupport implements Idempote /** * Sets the cache size */ + @SuppressWarnings("unchecked") public void setCacheSize(int size) { if (cache != null) { cache.clear(); } - cache = new LRUCache<String, Object>(size); + cache = LRUCacheFactory.newLRUCache(size); } @ManagedAttribute(description = "The current cache size") @@ -328,9 +330,13 @@ public class FileIdempotentRepository extends ServiceSupport implements Idempote } @Override + @SuppressWarnings("unchecked") protected void doStart() throws Exception { ObjectHelper.notNull(fileStore, "fileStore", this); + // default use a 1st level cache + this.cache = LRUCacheFactory.newLRUCache(1000); + // init store if not loaded before if (init.compareAndSet(false, true)) { loadStore(); http://git-wip-us.apache.org/repos/asf/camel/blob/847241f0/camel-core/src/main/java/org/apache/camel/processor/idempotent/MemoryIdempotentRepository.java ---------------------------------------------------------------------- diff --git a/camel-core/src/main/java/org/apache/camel/processor/idempotent/MemoryIdempotentRepository.java b/camel-core/src/main/java/org/apache/camel/processor/idempotent/MemoryIdempotentRepository.java index bbbd42e..ffeade5 100644 --- a/camel-core/src/main/java/org/apache/camel/processor/idempotent/MemoryIdempotentRepository.java +++ b/camel-core/src/main/java/org/apache/camel/processor/idempotent/MemoryIdempotentRepository.java @@ -24,6 +24,7 @@ import org.apache.camel.api.management.ManagedResource; import org.apache.camel.spi.IdempotentRepository; import org.apache.camel.support.ServiceSupport; import org.apache.camel.util.LRUCache; +import org.apache.camel.util.LRUCacheFactory; /** * A memory based implementation of {@link org.apache.camel.spi.IdempotentRepository}. @@ -38,8 +39,9 @@ public class MemoryIdempotentRepository extends ServiceSupport implements Idempo private Map<String, Object> cache; private int cacheSize; + @SuppressWarnings("unchecked") public MemoryIdempotentRepository() { - this.cache = new LRUCache<String, Object>(1000); + this.cache = LRUCacheFactory.newLRUCache(1000); } public MemoryIdempotentRepository(Map<String, Object> set) { @@ -59,8 +61,9 @@ public class MemoryIdempotentRepository extends ServiceSupport implements Idempo * * @param cacheSize the cache size */ + @SuppressWarnings("unchecked") public static IdempotentRepository<String> memoryIdempotentRepository(int cacheSize) { - return memoryIdempotentRepository(new LRUCache<String, Object>(cacheSize)); + return memoryIdempotentRepository(LRUCacheFactory.newLRUCache(cacheSize)); } /** @@ -128,9 +131,10 @@ public class MemoryIdempotentRepository extends ServiceSupport implements Idempo } @Override + @SuppressWarnings("unchecked") protected void doStart() throws Exception { if (cacheSize > 0) { - cache = new LRUCache<String, Object>(cacheSize); + cache = LRUCacheFactory.newLRUCache(cacheSize); } } http://git-wip-us.apache.org/repos/asf/camel/blob/847241f0/camel-core/src/main/java/org/apache/camel/support/ReloadStrategySupport.java ---------------------------------------------------------------------- diff --git a/camel-core/src/main/java/org/apache/camel/support/ReloadStrategySupport.java b/camel-core/src/main/java/org/apache/camel/support/ReloadStrategySupport.java index 44971f4..ecc040c 100644 --- a/camel-core/src/main/java/org/apache/camel/support/ReloadStrategySupport.java +++ b/camel-core/src/main/java/org/apache/camel/support/ReloadStrategySupport.java @@ -22,6 +22,7 @@ import java.util.ArrayList; import java.util.List; import java.util.Map; +import org.apache.camel.util.LRUCacheFactory; import org.w3c.dom.Document; import org.w3c.dom.Node; import org.w3c.dom.NodeList; @@ -47,8 +48,7 @@ import org.slf4j.LoggerFactory; public abstract class ReloadStrategySupport extends ServiceSupport implements ReloadStrategy { protected final Logger log = LoggerFactory.getLogger(getClass()); - // store state - protected final Map<String, Object> cache = new LRUCache<String, Object>(100); + protected Map<String, Object> cache; private CamelContext camelContext; @@ -198,8 +198,10 @@ public abstract class ReloadStrategySupport extends ServiceSupport implements Re } @Override + @SuppressWarnings("unchecked") protected void doStart() throws Exception { // noop + cache = LRUCacheFactory.newLRUCache(100); } @Override http://git-wip-us.apache.org/repos/asf/camel/blob/847241f0/camel-core/src/main/java/org/apache/camel/util/IntrospectionSupport.java ---------------------------------------------------------------------- diff --git a/camel-core/src/main/java/org/apache/camel/util/IntrospectionSupport.java b/camel-core/src/main/java/org/apache/camel/util/IntrospectionSupport.java index 9a75406..28e3956 100644 --- a/camel-core/src/main/java/org/apache/camel/util/IntrospectionSupport.java +++ b/camel-core/src/main/java/org/apache/camel/util/IntrospectionSupport.java @@ -66,7 +66,8 @@ public final class IntrospectionSupport { // use a cache to speedup introspecting for known classes during startup // use a weak cache as we dont want the cache to keep around as it reference classes // which could prevent classloader to unload classes if being referenced from this cache - private static final LRUCache<Class<?>, ClassInfo> CACHE = new LRUWeakCache<Class<?>, ClassInfo>(1000); + @SuppressWarnings("unchecked") + private static final LRUCache<Class<?>, ClassInfo> CACHE = LRUCacheFactory.newLRUWeakCache(1000); private static final Object LOCK = new Object(); static { http://git-wip-us.apache.org/repos/asf/camel/blob/847241f0/camel-core/src/main/java/org/apache/camel/util/LRUCache.java ---------------------------------------------------------------------- diff --git a/camel-core/src/main/java/org/apache/camel/util/LRUCache.java b/camel-core/src/main/java/org/apache/camel/util/LRUCache.java index 87c1fb0..41dc71f 100644 --- a/camel-core/src/main/java/org/apache/camel/util/LRUCache.java +++ b/camel-core/src/main/java/org/apache/camel/util/LRUCache.java @@ -36,7 +36,10 @@ import org.slf4j.LoggerFactory; * <p/> * If this cache stores {@link org.apache.camel.Service} then this implementation will on eviction * invoke the {@link org.apache.camel.Service#stop()} method, to auto-stop the service. + * <p/> + * Use {@link LRUCacheFactory} to create a new instance (do not use the constructor). * + * @see LRUCacheFactory * @see LRUSoftCache * @see LRUWeakCache */ http://git-wip-us.apache.org/repos/asf/camel/blob/847241f0/camel-core/src/main/java/org/apache/camel/util/LRUCacheFactory.java ---------------------------------------------------------------------- diff --git a/camel-core/src/main/java/org/apache/camel/util/LRUCacheFactory.java b/camel-core/src/main/java/org/apache/camel/util/LRUCacheFactory.java index 59b4620..052f72d3 100644 --- a/camel-core/src/main/java/org/apache/camel/util/LRUCacheFactory.java +++ b/camel-core/src/main/java/org/apache/camel/util/LRUCacheFactory.java @@ -16,6 +16,8 @@ */ package org.apache.camel.util; +import java.util.concurrent.atomic.AtomicBoolean; + import org.apache.camel.util.concurrent.ThreadHelper; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -25,35 +27,93 @@ import org.slf4j.LoggerFactory; */ public final class LRUCacheFactory { - // TODO: use LRUCacheFactory in other places to create the LRUCaches - private static final Logger LOG = LoggerFactory.getLogger(LRUCacheFactory.class); + private static final AtomicBoolean done = new AtomicBoolean(); + private LRUCacheFactory() { } @SuppressWarnings("unchecked") public static void warmUp() { - // create a dummy map in a separate thread to warmup the Caffeine cache - // as we want to do this as early as possible while creating CamelContext - // so when Camel is starting up its faster as the Caffeine cache has been initialized - Runnable warmup = () -> { - LOG.debug("Warming up LRUCache ..."); - newLRUCache(16); - LOG.debug("Warming up LRUCache complete"); - }; - - String threadName = ThreadHelper.resolveThreadName(null, "LRUCacheFactory"); - - Thread thread = new Thread(warmup, threadName); - thread.start(); + // create a dummy map in a separate thread to warm-up the Caffeine cache concurrently + // while Camel is starting up. This allows us to overall startup Camel a bit faster + // as Caffeine takes 150+ millis to initialize. + if (!done.compareAndSet(false, true)) { + Runnable warmup = () -> { + StopWatch watch = new StopWatch(); + LOG.debug("Warming up LRUCache ..."); + newLRUCache(16); + LOG.debug("Warming up LRUCache complete in {} millis", watch.taken()); + }; + + String threadName = ThreadHelper.resolveThreadName(null, "LRUCacheFactory"); + + Thread thread = new Thread(warmup, threadName); + thread.start(); + } } + /** + * Constructs an empty <tt>LRUCache</tt> instance with the + * specified maximumCacheSize, and will stop on eviction. + * + * @param maximumCacheSize the max capacity. + * @throws IllegalArgumentException if the initial capacity is negative + */ public static LRUCache newLRUCache(int maximumCacheSize) { + LOG.trace("Creating LRUCache with maximumCacheSize: {}", maximumCacheSize); return new LRUCache(maximumCacheSize); } + /** + * Constructs an empty <tt>LRUCache</tt> instance with the + * specified initial capacity, maximumCacheSize, and will stop on eviction. + * + * @param initialCapacity the initial capacity. + * @param maximumCacheSize the max capacity. + * @throws IllegalArgumentException if the initial capacity is negative + */ + public static LRUCache newLRUCache(int initialCapacity, int maximumCacheSize) { + LOG.trace("Creating LRUCache with initialCapacity: {}, maximumCacheSize: {}", initialCapacity, maximumCacheSize); + return new LRUCache(initialCapacity, maximumCacheSize); + } + + /** + * Constructs an empty <tt>LRUCache</tt> instance with the + * specified initial capacity, maximumCacheSize,load factor and ordering mode. + * + * @param initialCapacity the initial capacity. + * @param maximumCacheSize the max capacity. + * @param stopOnEviction whether to stop service on eviction. + * @throws IllegalArgumentException if the initial capacity is negative + */ + public static LRUCache newLRUCache(int initialCapacity, int maximumCacheSize, boolean stopOnEviction) { + LOG.trace("Creating LRUCache with initialCapacity: {}, maximumCacheSize: {}, stopOnEviction: {}", initialCapacity, maximumCacheSize, stopOnEviction); + return new LRUCache(initialCapacity, maximumCacheSize, stopOnEviction); + } + + /** + * Constructs an empty <tt>LRUSoftCache</tt> instance with the + * specified maximumCacheSize, and will stop on eviction. + * + * @param maximumCacheSize the max capacity. + * @throws IllegalArgumentException if the initial capacity is negative + */ + public static LRUSoftCache newLRUSoftCache(int maximumCacheSize) { + LOG.trace("Creating LRUSoftCache with maximumCacheSize: {}", maximumCacheSize); + return new LRUSoftCache(maximumCacheSize); + } + + /** + * Constructs an empty <tt>LRUWeakCache</tt> instance with the + * specified maximumCacheSize, and will stop on eviction. + * + * @param maximumCacheSize the max capacity. + * @throws IllegalArgumentException if the initial capacity is negative + */ public static LRUWeakCache newLRUWeakCache(int maximumCacheSize) { + LOG.trace("Creating LRUWeakCache with maximumCacheSize: {}", maximumCacheSize); return new LRUWeakCache(maximumCacheSize); } } http://git-wip-us.apache.org/repos/asf/camel/blob/847241f0/camel-core/src/main/java/org/apache/camel/util/LRUSoftCache.java ---------------------------------------------------------------------- diff --git a/camel-core/src/main/java/org/apache/camel/util/LRUSoftCache.java b/camel-core/src/main/java/org/apache/camel/util/LRUSoftCache.java index 4224d1d..39bcaf6 100644 --- a/camel-core/src/main/java/org/apache/camel/util/LRUSoftCache.java +++ b/camel-core/src/main/java/org/apache/camel/util/LRUSoftCache.java @@ -44,7 +44,10 @@ package org.apache.camel.util; * <p/> * Notice that if the JVM reclaim memory the content of this cache may be garbage collected, without any * eviction notifications. + * <p/> + * Use {@link LRUCacheFactory} to create a new instance (do not use the constructor). * + * @see LRUCacheFactory * @see LRUCache * @see LRUWeakCache */ http://git-wip-us.apache.org/repos/asf/camel/blob/847241f0/camel-core/src/main/java/org/apache/camel/util/LRUWeakCache.java ---------------------------------------------------------------------- diff --git a/camel-core/src/main/java/org/apache/camel/util/LRUWeakCache.java b/camel-core/src/main/java/org/apache/camel/util/LRUWeakCache.java index e624f44..6147e6a 100644 --- a/camel-core/src/main/java/org/apache/camel/util/LRUWeakCache.java +++ b/camel-core/src/main/java/org/apache/camel/util/LRUWeakCache.java @@ -44,7 +44,10 @@ package org.apache.camel.util; * <p/> * Notice that if the JVM reclaim memory the content of this cache may be garbage collected, without any * eviction notifications. + * <p/> + * Use {@link LRUCacheFactory} to create a new instance (do not use the constructor). * + * @see LRUCacheFactory * @see LRUCache * @see LRUSoftCache */ http://git-wip-us.apache.org/repos/asf/camel/blob/847241f0/camel-core/src/test/java/org/apache/camel/impl/DefaultCamelContextTest.java ---------------------------------------------------------------------- diff --git a/camel-core/src/test/java/org/apache/camel/impl/DefaultCamelContextTest.java b/camel-core/src/test/java/org/apache/camel/impl/DefaultCamelContextTest.java index 2487a52..1b9d429 100644 --- a/camel-core/src/test/java/org/apache/camel/impl/DefaultCamelContextTest.java +++ b/camel-core/src/test/java/org/apache/camel/impl/DefaultCamelContextTest.java @@ -133,6 +133,7 @@ public class DefaultCamelContextTest extends TestSupport { ctx.disableJMX(); ctx.getEndpoint("log:foo"); ctx.getEndpoint("log:bar"); + ctx.start(); Collection<Endpoint> list = ctx.removeEndpoints("log:foo"); assertEquals(1, list.size()); http://git-wip-us.apache.org/repos/asf/camel/blob/847241f0/camel-core/src/test/java/org/apache/camel/model/ModelSanityCheckerTest.java ---------------------------------------------------------------------- diff --git a/camel-core/src/test/java/org/apache/camel/model/ModelSanityCheckerTest.java b/camel-core/src/test/java/org/apache/camel/model/ModelSanityCheckerTest.java index f9d4b14..333e696 100644 --- a/camel-core/src/test/java/org/apache/camel/model/ModelSanityCheckerTest.java +++ b/camel-core/src/test/java/org/apache/camel/model/ModelSanityCheckerTest.java @@ -38,8 +38,9 @@ public class ModelSanityCheckerTest extends TestCase { private static final Logger LOG = LoggerFactory.getLogger(ModelSanityCheckerTest.class); - private Set<Class<?>> discoverJaxbClasses() { - PackageScanClassResolver resolver = new DefaultPackageScanClassResolver(); + private Set<Class<?>> discoverJaxbClasses() throws Exception { + DefaultPackageScanClassResolver resolver = new DefaultPackageScanClassResolver(); + resolver.start(); String[] packages = Constants.JAXB_CONTEXT_PACKAGES.split(":"); return resolver.findAnnotated(XmlAccessorType.class, packages); }