in evcache-core/src/main/java/com/netflix/evcache/EVCacheImpl.java [2592:2675]
protected <T> EVCacheLatch set(String key, T value, Transcoder<T> tc, int timeToLive, Policy policy, EVCacheClient[] clients, int latchCount) throws EVCacheException {
if ((null == key) || (null == value)) throw new IllegalArgumentException();
checkTTL(timeToLive, Call.SET);
final boolean throwExc = doThrowException();
if (clients.length == 0) {
incrementFastFail(EVCacheMetricsFactory.NULL_CLIENT, Call.SET);
if (throwExc) throw new EVCacheException("Could not find a client to set the data");
return new EVCacheLatchImpl(policy, 0, _appName); // Fast failure
}
final EVCacheKey evcKey = getEVCacheKey(key);
final EVCacheEvent event = createEVCacheEvent(Arrays.asList(clients), Call.SET);
if (event != null) {
event.setEVCacheKeys(Arrays.asList(evcKey));
try {
if (shouldThrottle(event)) {
incrementFastFail(EVCacheMetricsFactory.THROTTLED, Call.SET);
if (throwExc) throw new EVCacheException("Request Throttled for app " + _appName + " & key " + key);
return new EVCacheLatchImpl(policy, 0, _appName);
}
} catch(EVCacheException ex) {
if(throwExc) throw ex;
incrementFastFail(EVCacheMetricsFactory.THROTTLED, Call.SET);
return null;
}
startEvent(event);
}
final long start = EVCacheMetricsFactory.getInstance().getRegistry().clock().wallTime();
String status = EVCacheMetricsFactory.SUCCESS;
final EVCacheLatchImpl latch = new EVCacheLatchImpl(policy == null ? Policy.ALL_MINUS_1 : policy, latchCount, _appName);
try {
CachedData cd = null;
CachedData cdHashed = null;
for (EVCacheClient client : clients) {
final String canonicalKey = evcKey.getCanonicalKey(client.isDuetClient());
final String hashKey = evcKey.getHashKey(client.isDuetClient(), client.getHashingAlgorithm(), client.shouldEncodeHashKey(), client.getMaxDigestBytes(), client.getMaxHashLength(), client.getBaseEncoder());
if(cd == null) {
if (tc != null) {
cd = tc.encode(value);
} else if (_transcoder != null) {
cd = ((Transcoder<Object>) _transcoder).encode(value);
} else {
cd = client.getTranscoder().encode(value);
}
}
if (hashKey != null) {
if(cdHashed == null) {
final EVCacheValue val = new EVCacheValue(canonicalKey, cd.getData(), cd.getFlags(), timeToLive, System.currentTimeMillis());
cdHashed = evcacheValueTranscoder.encode(val);
}
final Future<Boolean> future = client.set(hashKey, cdHashed, timeToLive, latch);
if (log.isDebugEnabled() && shouldLog()) log.debug("SET : APP " + _appName + ", Future " + future + " for hashed key : " + evcKey);
} else {
final Future<Boolean> future = client.set(canonicalKey, cd, timeToLive, latch);
if (log.isDebugEnabled() && shouldLog()) log.debug("SET : APP " + _appName + ", Future " + future + " for key : " + evcKey);
}
}
if (event != null) {
event.setTTL(timeToLive);
event.setCachedData(cd);
if(_eventsUsingLatchFP.get()) {
latch.setEVCacheEvent(event);
latch.scheduledFutureValidation();
} else {
endEvent(event);
}
}
return latch;
} catch (Exception ex) {
if (log.isDebugEnabled() && shouldLog()) log.debug("Exception setting the data for APP " + _appName + ", key : " + evcKey, ex);
if (event != null) endEvent(event);
status = EVCacheMetricsFactory.ERROR;
if (!throwExc) return new EVCacheLatchImpl(policy, 0, _appName);
throw new EVCacheException("Exception setting data for APP " + _appName + ", key : " + evcKey, ex);
} finally {
final long duration = EVCacheMetricsFactory.getInstance().getRegistry().clock().wallTime()- start;
getTTLDistributionSummary(Call.SET.name(), EVCacheMetricsFactory.WRITE, EVCacheMetricsFactory.TTL).record(timeToLive);
getTimer(Call.SET.name(), EVCacheMetricsFactory.WRITE, null, status, 1, maxWriteDuration.get().intValue(), null).record(duration, TimeUnit.MILLISECONDS);
if (log.isDebugEnabled() && shouldLog()) log.debug("SET : APP " + _appName + ", Took " + duration + " milliSec for key : " + evcKey);
}
}