redis/jedis · error · JedisCacheException
Failed to find compatible constructor for custom cache…
Error message
Failed to find compatible constructor for custom cache type! Provide one of these;
- ${className}(int maxSize, EvictionPolicy evictionPolicy)
- ${className}(int maxSize, EvictionPolicy evictionPolicy, Cacheable cacheable) What it means
getConstructor looks for a public constructor matching (int, EvictionPolicy) on the configured custom cache class; if absent, it throws JedisCacheException listing the two accepted constructor signatures — with or without a trailing Cacheable parameter. This tells the developer their custom Cache class does not expose a constructor shape CacheFactory can invoke.
Solutions
- Add a public constructor X(int maxSize, EvictionPolicy evictionPolicy) to your custom cache class.
- Alternatively add X(int maxSize, EvictionPolicy evictionPolicy, Cacheable cacheable) so the cacheable-aware path can be used.
- If you cannot change the constructor, adapt with a thin subclass exposing the required (int, EvictionPolicy) constructor.
- Verify the class is public and the constructor is public (non-public constructors are invisible to getConstructor).
Example fix
// before
public class MyCache implements Cache {
public MyCache() { ... } // no matching constructor
}
// after
public class MyCache implements Cache {
public MyCache(int maxSize, EvictionPolicy evictionPolicy) { ... }
} Defensive patterns
Strategy: validation
Validate before calling
static void requireCompatibleCacheCtor(Class<? extends Cache> type) {
boolean ok = Arrays.stream(type.getConstructors()).anyMatch(c ->
Arrays.equals(c.getParameterTypes(), new Class[]{int.class, EvictionPolicy.class}) ||
Arrays.equals(c.getParameterTypes(), new Class[]{int.class, EvictionPolicy.class, Cacheable.class}));
if (!ok) throw new IllegalArgumentException(type.getName() +
" must expose public (int, EvictionPolicy) or (int, EvictionPolicy, Cacheable) constructor");
} Try / catch
try {
Cache cache = CacheFactory.getCache(config);
} catch (JedisCacheException e) {
if (e.getMessage().contains("Failed to find compatible constructor")) {
// add or expose the required constructor in the custom cache class
} else throw e;
} Prevention
- Give every custom Cache class a public (int maxSize, EvictionPolicy) constructor as a convention
- Do not rely on builder/factory patterns as the only construction path for cacheClass
- Write a unit test asserting the constructor signature exists before wiring it into CacheConfig
When it happens
Trigger: config.setCacheClass(X.class) where X has no public constructor of shape (int maxSize, EvictionPolicy) or (int maxSize, EvictionPolicy, Cacheable) — e.g. only a no-arg constructor, only builders, or the 2-arg constructor is private/protected.
Common situations: Implementing a custom cache with dependency injection (no matching constructor); wrapping a third-party cache (e.g. Caffeine) whose constructors have different parameters; forgetting that the (int, EvictionPolicy, Cacheable) hint only works if findConstructorWithCacheable's path applies.
Related errors
- Failed to insantiate custom cache type!
- Must not instantiate this class
- is not supported. Value: " ".
- Failed to serialize object
- Failed to deserialize object
AI-assisted analysis of redis/jedis@6dac31d4c2 (2026-09-08).
Data as JSON: /api/errors/e5b63aa35b9455b5.
Report an issue: GitHub.
Appendix: source
Thrown at src/main/java/redis/clients/jedis/csc/CacheFactory.java:48
return (Cache) ctor.newInstance(config.getMaxSize(), getEvictionPolicy(config));
} catch (InstantiationException | IllegalAccessException | IllegalArgumentException | InvocationTargetException
| SecurityException e) {
throw new JedisCacheException("Failed to insantiate custom cache type!", e);
}
}
private static Constructor findConstructorWithCacheable(Class customCacheType) {
return Arrays.stream(customCacheType.getConstructors())
.filter(ctor -> Arrays.equals(ctor.getParameterTypes(), new Class[] { int.class, EvictionPolicy.class, Cacheable.class }))
.findFirst().orElse(null);
}
private static Constructor getConstructor(Class customCacheType) {
try {
return customCacheType.getConstructor(int.class, EvictionPolicy.class);
} catch (NoSuchMethodException e) {
String className = customCacheType.getName();
throw new JedisCacheException(String.format(
"Failed to find compatible constructor for custom cache type! Provide one of these;"
// give hints about the compatible constructors
+ "\n - %s(int maxSize, EvictionPolicy evictionPolicy)\n - %s(int maxSize, EvictionPolicy evictionPolicy, Cacheable cacheable)",
className, className), e);
}
}
private static EvictionPolicy getEvictionPolicy(CacheConfig config) {
if (config.getEvictionPolicy() == null) {
// It will be default to LRUEviction, until we have other eviction implementations
return new LRUEviction(config.getMaxSize());
}
return config.getEvictionPolicy();
}
}View on GitHub (pinned to 6dac31d4c2)