diff --git a/distribution/pom.xml b/distribution/pom.xml
index a1db657935a3..20038bf90333 100644
--- a/distribution/pom.xml
+++ b/distribution/pom.xml
@@ -152,4 +152,53 @@
+
+
+ java8
+
+ 1.8
+
+
+
+
+ org.codehaus.mojo
+ exec-maven-plugin
+
+
+ pull-deps-jdk8
+ package
+
+ exec
+
+
+ java
+
+ -classpath
+
+ -Ddruid.extensions.loadList=[]
+ -Ddruid.extensions.directory=${project.build.directory}/extensions
+
+
+ -Ddruid.extensions.hadoopDependenciesDir=${project.build.directory}/hadoop-dependencies
+
+ io.druid.cli.Main
+ tools
+ pull-deps
+ --defaultVersion
+ ${project.parent.version}
+ -l
+ ${settings.localRepository}
+
+ --no-default-hadoop
+ -c
+ io.druid.extensions:druid-caffeine-cache
+
+
+
+
+
+
+
+
+
diff --git a/docs/content/development/extensions-core/caffeine-cache.md b/docs/content/development/extensions-core/caffeine-cache.md
new file mode 100644
index 000000000000..b9d739904b2d
--- /dev/null
+++ b/docs/content/development/extensions-core/caffeine-cache.md
@@ -0,0 +1,39 @@
+---
+layout: doc_page
+---
+
+Druid Caffeine Cache
+--------------------
+
+A highly performant local cache implementation for Druid based on [Caffeine](https://github.com/ben-manes/caffeine). Requires a JRE8u60 or higher
+
+# Configuration
+Below are the configuration options known to this module:
+
+|`runtime.properties`|Description|Default|
+|--------------------|-----------|-------|
+|`druid.cache.sizeInBytes`|The maximum size of the cache in bytes on heap.|None (unlimited)|
+|`druid.cache.expireAfter`|The time (in ms) after an access for which a cache entry may be expired|None (no time limit)|
+|`druid.cache.cacheExecutorFactory`|The executor factory to use for Caffeine maintenance. One of `COMMON_FJP`, `SINGLE_THREAD`, or `SAME_THREAD`|ForkJoinPool common pool (`COMMON_FJP`)|
+|`druid.cache.evictOnClose`|If a close of a namespace (ex: removing a segment from a node) should cause an eager eviction of associated cache values|`false`|
+
+## `druid.cache.cacheExecutorFactory`
+
+Here are the possible values for `druid.cache.cacheExecutorFactory`, which controls how maintenance tasks are run
+
+* `COMMON_FJP` (default) use the common ForkJoinPool. Do NOT use this option unless you are running 8u60 or higher
+* `SINGLE_THREAD` Use a single-threaded executor
+* `SAME_THREAD` Cache maintenance is done eagerly
+
+# Enabling
+
+To enable the caffeine cache, include this module on the loadList and set `druid.cache.type` to `caffeine` in your properties.
+
+# Metrics
+In addition to the normal cache metrics, the caffeine cache implementation also reports the following in both `total` and `delta`
+
+|Metric|Description|Normal value|
+|------|-----------|------------|
+|`query/cache/caffeine/*/requests`|Count of hits or misses|hit + miss|
+|`query/cache/caffeine/*/loadTime`|Length of time caffeine spends loading new values (unused feature)|0|
+|`query/cache/caffeine/*/evictionBytes`|Size in bytes that have been evicted from the cache|Varies, should tune cache `sizeInBytes` so that `sizeInBytes`/`evictionBytes` is approximately the rate of cache churn you desire|
diff --git a/docs/content/development/extensions.md b/docs/content/development/extensions.md
index 14dbeb389cc3..e95c397149dd 100644
--- a/docs/content/development/extensions.md
+++ b/docs/content/development/extensions.md
@@ -22,6 +22,7 @@ Core extensions are maintained by Druid committers.
|Name|Description|Docs|
|----|-----------|----|
|druid-avro-extensions|Support for data in Apache Avro data format.|[link](../development/extensions-core/avro.html)|
+|druid-caffeine-cache|A local cache implementation backed by Caffeine.|[link](../development/extensions-core/caffeine-cache.html)|
|druid-datasketches|Support for approximate counts and set operations with [DataSketches](http://datasketches.github.io/).|[link](../development/extensions-core/datasketches-aggregators.html)|
|druid-hdfs-storage|HDFS deep storage.|[link](../development/extensions-core/hdfs.html)|
|druid-histogram|Approximate histograms and quantiles aggregator.|[link](../development/extensions-core/approximate-histograms.html)|
diff --git a/extensions-core/caffeine-cache/pom.xml b/extensions-core/caffeine-cache/pom.xml
new file mode 100644
index 000000000000..5d3da168ca5c
--- /dev/null
+++ b/extensions-core/caffeine-cache/pom.xml
@@ -0,0 +1,80 @@
+
+
+
+
+
+ 4.0.0
+
+ io.druid.extensions
+ druid-caffeine-cache
+ druid-caffeine-cache
+ Local cache implementation for Druid using Caffeine https://github.com/ben-manes/caffeine as the underlying implementation
+
+
+ io.druid
+ druid
+ 0.9.2-SNAPSHOT
+ ../../pom.xml
+
+
+
+
+ io.druid
+ druid-api
+ provided
+ ${project.parent.version}
+
+
+ io.druid
+ druid-server
+ ${project.parent.version}
+ provided
+
+
+ com.github.ben-manes.caffeine
+ caffeine
+ 2.3.1
+
+
+ net.jpountz.lz4
+ lz4
+ provided
+
+
+
+
+ junit
+ junit
+ test
+
+
+
+
+
+ org.apache.maven.plugins
+ maven-compiler-plugin
+
+ 1.8
+ 1.8
+
+
+
+
+
diff --git a/extensions-core/caffeine-cache/src/main/java/io/druid/client/cache/CacheExecutorFactory.java b/extensions-core/caffeine-cache/src/main/java/io/druid/client/cache/CacheExecutorFactory.java
new file mode 100644
index 000000000000..a2c26159882e
--- /dev/null
+++ b/extensions-core/caffeine-cache/src/main/java/io/druid/client/cache/CacheExecutorFactory.java
@@ -0,0 +1,58 @@
+/*
+ * Licensed to Metamarkets Group Inc. (Metamarkets) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. Metamarkets licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package io.druid.client.cache;
+
+import com.fasterxml.jackson.annotation.JsonCreator;
+import io.druid.concurrent.Execs;
+import java.util.concurrent.Executor;
+import java.util.concurrent.ForkJoinPool;
+
+public enum CacheExecutorFactory
+{
+ COMMON_FJP {
+ @Override
+ public Executor createExecutor()
+ {
+ return ForkJoinPool.commonPool();
+ }
+ },
+ SINGLE_THREAD {
+ @Override
+ public Executor createExecutor()
+ {
+ return Execs.singleThreaded("CaffeineWorker-%s");
+ }
+ },
+ SAME_THREAD {
+ @Override
+ public Executor createExecutor()
+ {
+ return Runnable::run;
+ }
+ };
+
+ public abstract Executor createExecutor();
+
+ @JsonCreator
+ public static CacheExecutorFactory from(String str)
+ {
+ return Enum.valueOf(CacheExecutorFactory.class, str.toUpperCase());
+ }
+}
diff --git a/extensions-core/caffeine-cache/src/main/java/io/druid/client/cache/CaffeineCache.java b/extensions-core/caffeine-cache/src/main/java/io/druid/client/cache/CaffeineCache.java
new file mode 100644
index 000000000000..5903183a287f
--- /dev/null
+++ b/extensions-core/caffeine-cache/src/main/java/io/druid/client/cache/CaffeineCache.java
@@ -0,0 +1,192 @@
+/*
+ * Licensed to Metamarkets Group Inc. (Metamarkets) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. Metamarkets licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package io.druid.client.cache;
+
+import com.github.benmanes.caffeine.cache.Cache;
+import com.github.benmanes.caffeine.cache.Caffeine;
+import com.github.benmanes.caffeine.cache.stats.CacheStats;
+import com.google.common.annotations.VisibleForTesting;
+import com.google.common.collect.ImmutableMap;
+import com.google.common.collect.Maps;
+import com.google.common.primitives.Chars;
+import com.google.common.primitives.Ints;
+import com.metamx.common.logger.Logger;
+import com.metamx.emitter.service.ServiceEmitter;
+import com.metamx.emitter.service.ServiceMetricEvent;
+import net.jpountz.lz4.LZ4Compressor;
+import net.jpountz.lz4.LZ4Factory;
+import net.jpountz.lz4.LZ4FastDecompressor;
+
+import java.nio.ByteBuffer;
+import java.util.Map;
+import java.util.OptionalLong;
+import java.util.concurrent.Executor;
+import java.util.concurrent.TimeUnit;
+import java.util.concurrent.atomic.AtomicReference;
+
+public class CaffeineCache implements io.druid.client.cache.Cache
+{
+ private static final Logger log = new Logger(CaffeineCache.class);
+ private static final int FIXED_COST = 8; // Minimum cost in "weight" per entry;
+ private static final LZ4Factory LZ4_FACTORY = LZ4Factory.fastestInstance();
+ private static final LZ4FastDecompressor LZ4_DECOMPRESSOR = LZ4_FACTORY.fastDecompressor();
+ private static final LZ4Compressor LZ4_COMPRESSOR = LZ4_FACTORY.fastCompressor();
+
+ private final Cache cache;
+ private final AtomicReference priorStats = new AtomicReference<>(CacheStats.empty());
+ private final CaffeineCacheConfig config;
+
+
+ public static CaffeineCache create(final CaffeineCacheConfig config)
+ {
+ return create(config, config.createExecutor());
+ }
+
+ // Used in testing
+ public static CaffeineCache create(final CaffeineCacheConfig config, final Executor executor)
+ {
+ Caffeine