@Override public void record(long key) { Object value = cache.get(key); if (value == null) { if (cache.size() == cache.getMaxSize()) { policyStats.recordEviction(); } cache.put(key, key); policyStats.recordMiss(); } else { policyStats.recordHit(); } }
public ExpiringMapPolicy(Config config) { policyStats = new PolicyStats("product.ExpiringMap"); ExpiringMapSettings settings = new ExpiringMapSettings(config); cache = ExpiringMap.builder() .expirationPolicy(settings.policy()) .maxSize(settings.maximumSize()) .build(); }
@Override public boolean compareAndSet(String key, byte[] expected, byte[] value, long ttl) { Objects.requireNonNull(key); // clone is not needed if the comparison fails // but we are optimistic and prefer to do the clone outside the lock value = clone(value); // we don't use ExpiringMap.replace because it deals with null differently writeLock.lock(); try { byte[] current = map.get(key); boolean equal = Arrays.equals(expected, current); if (equal) { if (value == null) { map.remove(key); } else { map.put(key, value); doSetTTL(key, ttl); } } return equal; } finally { writeLock.unlock(); } }
@Override public void deleteMessage(String applicationId, String messageId) throws TException { checkThat(applicationId, messageId) .throwing(InvalidArgumentException.class) .are(nonEmptyString()); if (!messages.containsKey(messageId)) { return; } Message message = messages.remove(messageId); String appId = message.applicationId; Set<String> appMessages = messagesByApplication.getOrDefault(appId, Sets.create()); appMessages.remove(messageId); messagesByApplication.put(appId, appMessages); }
/** * @see #put(Object, Object, ExpirationPolicy, long, TimeUnit) */ public V put(K key, V value, long duration, TimeUnit timeUnit) { return put(key, value, expirationPolicy.get(), duration, timeUnit); }
@Override public boolean remove(Object value) { return ExpiringMap.this.remove(value) != null; }
private void scanEntries() { for (String key : cache.keySet()) { CachedValueWrapper wrapper = cache.get(key); if (wrapper.getRedisCacheAnn().redisFor() == StoreValue) continue; long expiration = RedisCacheUtils.redisExpirationSeconds(key, appContext); long cacheExpiration = cache.getExpiration(key); if (expiration == cacheExpiration) continue; CachedValueWrapper removed = cache.remove(key); if (removed == null) continue; Logger logger = wrapper.getLogger(); logger.debug("invalidate cache {} because of redis refresh seconds changed to {} ", key, expiration); } }
private ConcurrentMap<String, Long> getMap(String key, int longestDuration) { // Currently unable to putIfAbsent when using jodah's expiry map so will wrap in a lock return lockManager.executeLocked(key, () -> { ConcurrentMap<String, Long> keyMap = expiringKeyMap.get(key); if (keyMap == null) { keyMap = new ConcurrentHashMap<>(); expiringKeyMap.put(key, keyMap, ExpirationPolicy.CREATED, longestDuration, TimeUnit.SECONDS); } return keyMap; }); }
Object getLocalCache() { CachedValueWrapper cachedValue = localCache.get(valueKey); if (cachedValue != null) { long expectedExpiration = getExpectedExpirationSeconds(); logger.debug("got local {} = {} with expiration {} seconds", valueKey, cachedValue.getValue(), expectedExpiration); if (expectedExpiration >= 0) this.value = cachedValue.getValue(); else localCache.remove(valueKey); } else { logger.debug("got local {} = null", valueKey); } return this.value; }
@Override public void expired(String key, Message value) { if(isNullOrEmpty(key)) { return; } if(Objects.isNull(value)) { return; } String appId = value.applicationId; Set<String> appMessages = messagesByApplication.getOrDefault(appId, Sets.create()); appMessages.remove(key); messagesByApplication.put(appId, appMessages); }
private V load(K key) { if (entryLoader == null && expiringEntryLoader == null) return null; writeLock.lock(); try { // Double check for entry ExpiringEntry<K, V> entry = getEntry(key); if (entry != null) return entry.getValue(); if (entryLoader != null) { V value = entryLoader.load(key); put(key, value); return value; } else { ExpiringValue<? extends V> expiringValue = expiringEntryLoader.load(key); if (expiringValue == null) { put(key, null); return null; } else { long duration = expiringValue.getTimeUnit() == null ? expirationNanos.get() : expiringValue.getDuration(); TimeUnit timeUnit = expiringValue.getTimeUnit() == null ? TimeUnit.NANOSECONDS : expiringValue.getTimeUnit(); put(key, expiringValue.getValue(), expiringValue.getExpirationPolicy() == null ? expirationPolicy.get() : expiringValue.getExpirationPolicy(), duration, timeUnit); return expiringValue.getValue(); } } } finally { writeLock.unlock(); } }
@Override public byte[] get(String key) { Objects.requireNonNull(key); byte[] value = map.get(key); return clone(value); }
@Override public List<Message> getByApplication(String applicationId) throws TException { checkThat(applicationId) .throwing(InvalidArgumentException.class) .is(validApplicationId()); return messagesByApplication.getOrDefault(applicationId, Sets.emptySet()) .stream() .map(id -> messages.get(id)) .filter(Objects::nonNull) .collect(toList()); }
/** * Creates a new instance of ExpiringMap with ExpirationPolicy.CREATED and an expiration of 60 seconds. */ @SuppressWarnings("unchecked") public static <K, V> ExpiringMap<K, V> create() { return new ExpiringMap<K, V>((Builder<K, V>) ExpiringMap.builder()); }
@Override public int size() { return ExpiringMap.this.size(); } };
@Override public boolean contains(Object key) { return containsKey(key); }
@Override public void clear() { ExpiringMap.this.clear(); }
@Override public void deleteMessage(String applicationId, String messageId) throws TException { checkThat(applicationId, messageId) .throwing(InvalidArgumentException.class) .are(nonEmptyString()); if (!messages.containsKey(messageId)) { return; } Message message = messages.remove(messageId); String appId = message.applicationId; Set<String> appMessages = messagesByApplication.getOrDefault(appId, Sets.create()); appMessages.remove(messageId); messagesByApplication.put(appId, appMessages); }
/** * @see #put(Object, Object, ExpirationPolicy, long, TimeUnit) */ public V put(K key, V value, long duration, TimeUnit timeUnit) { return put(key, value, expirationPolicy.get(), duration, timeUnit); }