From b821702b8dc03575419a5b583611b68ad2691ccc Mon Sep 17 00:00:00 2001 From: Koen De Groote Date: Fri, 31 Mar 2017 13:30:01 +0200 Subject: [PATCH] Moving defaultservercache implementation to use nanoseconds to determine whether or not something needs to be evicted from the cache. (#998) The old implementation used System.currentTimeMillis(), which might be unreliable, for instance during a jump in DST. Thanks @rPraml for noticing and suggesting the fix. --- .../ebeaninternal/api/ScopedTransaction.java | 1 - .../server/cache/DefaultServerCache.java | 18 +++++++++--------- .../server/persist/BatchedPstmtHolder.java | 1 - .../server/transaction/JdbcTransaction.java | 1 - 4 files changed, 9 insertions(+), 12 deletions(-) diff --git a/src/main/java/io/ebeaninternal/api/ScopedTransaction.java b/src/main/java/io/ebeaninternal/api/ScopedTransaction.java index 145491135..fdd2914c5 100644 --- a/src/main/java/io/ebeaninternal/api/ScopedTransaction.java +++ b/src/main/java/io/ebeaninternal/api/ScopedTransaction.java @@ -13,7 +13,6 @@ import io.ebeaninternal.server.persist.BatchControl; import io.ebeanservice.docstore.api.DocStoreTransaction; import javax.persistence.PersistenceException; -import java.io.IOException; import java.sql.Connection; import java.sql.SQLException; diff --git a/src/main/java/io/ebeaninternal/server/cache/DefaultServerCache.java b/src/main/java/io/ebeaninternal/server/cache/DefaultServerCache.java index 5a12d19d8..47cb08a09 100644 --- a/src/main/java/io/ebeaninternal/server/cache/DefaultServerCache.java +++ b/src/main/java/io/ebeaninternal/server/cache/DefaultServerCache.java @@ -8,8 +8,8 @@ import org.slf4j.Logger; import org.slf4j.LoggerFactory; import java.io.Serializable; +import java.util.List; import java.util.ArrayList; -import java.util.Collections; import java.util.Comparator; import java.util.Iterator; import java.util.Map; @@ -276,19 +276,19 @@ public class DefaultServerCache implements ServerCache { long trimmedByTTL = 0; long trimmedByLRU = 0; - ArrayList activeList = new ArrayList<>(map.size()); + List activeList = new ArrayList<>(map.size()); - long idleExpire = System.currentTimeMillis() - (maxIdleSecs * 1000); - long ttlExpire = System.currentTimeMillis() - (maxSecsToLive * 1000); + long idleExpireNano = startNanos - TimeUnit.SECONDS.toNanos(maxIdleSecs); + long ttlExpireNano = startNanos - TimeUnit.SECONDS.toNanos(maxSecsToLive); Iterator it = map.values().iterator(); while (it.hasNext()) { CacheEntry cacheEntry = it.next(); - if (maxIdleSecs > 0 && idleExpire > cacheEntry.getLastAccessTime()) { + if (maxIdleSecs > 0 && idleExpireNano > cacheEntry.getLastAccessTime()) { it.remove(); trimmedByIdle++; - } else if (maxSecsToLive > 0 && ttlExpire > cacheEntry.getCreateTime()) { + } else if (maxSecsToLive > 0 && ttlExpireNano > cacheEntry.getCreateTime()) { it.remove(); trimmedByTTL++; @@ -301,7 +301,7 @@ public class DefaultServerCache implements ServerCache { trimmedByLRU = activeList.size() - maxSize; if (trimmedByLRU > 0) { // sort into last access time ascending - Collections.sort(activeList, BY_LAST_ACCESS); + activeList.sort(BY_LAST_ACCESS); int trimSize = getTrimSize(); for (int i = trimSize; i < activeList.size(); i++) { // remove if still in the cache @@ -365,7 +365,7 @@ public class DefaultServerCache implements ServerCache { public CacheEntry(Object key, Object value) { this.key = key; this.value = value; - this.createTime = System.currentTimeMillis(); + this.createTime = System.nanoTime(); this.lastAccessTime = createTime; } @@ -381,7 +381,7 @@ public class DefaultServerCache implements ServerCache { */ public Object getValue() { // long assignment should be atomic these days (Ref Cliff Click) - lastAccessTime = System.currentTimeMillis(); + lastAccessTime = System.nanoTime(); return value; } diff --git a/src/main/java/io/ebeaninternal/server/persist/BatchedPstmtHolder.java b/src/main/java/io/ebeaninternal/server/persist/BatchedPstmtHolder.java index b47b41a36..b981614ed 100644 --- a/src/main/java/io/ebeaninternal/server/persist/BatchedPstmtHolder.java +++ b/src/main/java/io/ebeaninternal/server/persist/BatchedPstmtHolder.java @@ -3,7 +3,6 @@ package io.ebeaninternal.server.persist; import org.slf4j.Logger; import org.slf4j.LoggerFactory; -import javax.persistence.PersistenceException; import java.sql.PreparedStatement; import java.sql.SQLException; import java.util.LinkedHashMap; diff --git a/src/main/java/io/ebeaninternal/server/transaction/JdbcTransaction.java b/src/main/java/io/ebeaninternal/server/transaction/JdbcTransaction.java index 9b9d31ce7..ae3404b82 100644 --- a/src/main/java/io/ebeaninternal/server/transaction/JdbcTransaction.java +++ b/src/main/java/io/ebeaninternal/server/transaction/JdbcTransaction.java @@ -22,7 +22,6 @@ import org.slf4j.LoggerFactory; import javax.persistence.PersistenceException; import javax.persistence.RollbackException; -import java.io.IOException; import java.sql.Connection; import java.sql.SQLException; import java.util.ArrayList;