diff --git a/ebean-api/src/main/java/io/ebean/bean/PersistenceContext.java b/ebean-api/src/main/java/io/ebean/bean/PersistenceContext.java
index 9d67499d1..ed03080cd 100644
--- a/ebean-api/src/main/java/io/ebean/bean/PersistenceContext.java
+++ b/ebean-api/src/main/java/io/ebean/bean/PersistenceContext.java
@@ -60,21 +60,15 @@ public interface PersistenceContext {
int size(Class> rootType);
/**
- * Return a copy of the Persistence context to use for large query iteration.
+ * Signalizes the PersistenceContext, the begin for large query iteration.
*/
- PersistenceContext forIterate();
+ void beginIterate();
/**
- * Return a new Persistence context during iteration of large query result.
+ * Signalizes the PersistenceContext, the end for large query iteration.
*/
- PersistenceContext forIterateReset();
-
- /**
- * Return true if the persistence context has grown and hit the 'reset limit'
- * during large query iteration.
- */
- boolean resetLimit();
-
+ void endIterate();
+
/**
* Wrapper on a bean to also indicate if a bean has been deleted.
*
diff --git a/ebean-api/src/main/java/io/ebean/text/json/JsonBeanReader.java b/ebean-api/src/main/java/io/ebean/text/json/JsonBeanReader.java
index fc948016f..7acdb976f 100644
--- a/ebean-api/src/main/java/io/ebean/text/json/JsonBeanReader.java
+++ b/ebean-api/src/main/java/io/ebean/text/json/JsonBeanReader.java
@@ -20,7 +20,7 @@ public interface JsonBeanReader {
/**
* Create a new reader taking the context from the existing one but using a new JsonParser.
*/
- JsonBeanReader forJson(JsonParser moreJson, boolean resetContext);
+ JsonBeanReader forJson(JsonParser moreJson);
/**
* Add a bean explicitly to the persistence context.
diff --git a/ebean-core/src/main/java/io/ebeaninternal/api/LoadContext.java b/ebean-core/src/main/java/io/ebeaninternal/api/LoadContext.java
index 51f02826c..b23a183bb 100644
--- a/ebean-core/src/main/java/io/ebeaninternal/api/LoadContext.java
+++ b/ebean-core/src/main/java/io/ebeaninternal/api/LoadContext.java
@@ -36,14 +36,6 @@ public interface LoadContext {
*/
PersistenceContext getPersistenceContext();
- /**
- * Set the persistence context used by this query and future lazy loading.
- *
- * Used by query iterator when processing large result sets.
- *
- */
- void resetPersistenceContext(PersistenceContext persistenceContext);
-
/**
* Register a Bean for lazy loading.
*/
diff --git a/ebean-core/src/main/java/io/ebeaninternal/api/json/SpiJsonReader.java b/ebean-core/src/main/java/io/ebeaninternal/api/json/SpiJsonReader.java
index aaf4e2ce8..4594cbe25 100644
--- a/ebean-core/src/main/java/io/ebeaninternal/api/json/SpiJsonReader.java
+++ b/ebean-core/src/main/java/io/ebeaninternal/api/json/SpiJsonReader.java
@@ -14,7 +14,7 @@ public interface SpiJsonReader {
PersistenceContext getPersistenceContext();
- SpiJsonReader forJson(JsonParser moreJson, boolean resetContext);
+ SpiJsonReader forJson(JsonParser moreJson);
void persistenceContextPut(Object beanId, T currentBean);
diff --git a/ebean-core/src/main/java/io/ebeaninternal/server/core/OrmQueryRequest.java b/ebean-core/src/main/java/io/ebeaninternal/server/core/OrmQueryRequest.java
index 85d89ffe2..6ef1e352b 100644
--- a/ebean-core/src/main/java/io/ebeaninternal/server/core/OrmQueryRequest.java
+++ b/ebean-core/src/main/java/io/ebeaninternal/server/core/OrmQueryRequest.java
@@ -225,6 +225,9 @@ public final class OrmQueryRequest extends BeanRequest implements SpiOrmQuery
createdTransaction = true;
}
persistenceContext = persistenceContext(query, transaction);
+ if (Type.ITERATE == query.getType()) {
+ persistenceContext.beginIterate();
+ }
loadContext = new DLoadContext(this, secondaryQueries);
}
@@ -233,6 +236,9 @@ public final class OrmQueryRequest extends BeanRequest implements SpiOrmQuery
*/
@Override
public void rollbackTransIfRequired() {
+ if (Type.ITERATE == query.getType()) {
+ persistenceContext.endIterate();
+ }
if (createdTransaction) {
try {
transaction.end();
@@ -263,20 +269,6 @@ public final class OrmQueryRequest extends BeanRequest implements SpiOrmQuery
return jsonRead;
}
- /**
- * For iterate queries reset the persistenceContext and loadContext.
- */
- public void flushPersistenceContextOnIterate() {
- if (persistenceContext.resetLimit()) {
- persistenceContext = persistenceContext.forIterateReset();
- loadContext.resetPersistenceContext(persistenceContext);
- if (jsonRead != null) {
- jsonRead.setPersistenceContext(persistenceContext);
- jsonRead.setLoadContext(loadContext);
- }
- }
- }
-
/**
* Get the TransactionContext either explicitly set on the query or
* transaction scoped.
@@ -292,11 +284,7 @@ public final class OrmQueryRequest extends BeanRequest implements SpiOrmQuery
if (scope == PersistenceContextScope.QUERY || t == null) {
return new DefaultPersistenceContext();
}
- if (Type.ITERATE == query.getType()) {
- return t.getPersistenceContext().forIterate();
- } else {
- return t.getPersistenceContext();
- }
+ return t.getPersistenceContext();
}
/**
@@ -306,6 +294,9 @@ public final class OrmQueryRequest extends BeanRequest implements SpiOrmQuery
*/
@Override
public void endTransIfRequired() {
+ if (Type.ITERATE == query.getType()) {
+ persistenceContext.endIterate();
+ }
if (createdTransaction && transaction.isActive()) {
transaction.commit();
if (query.getType().isUpdate()) {
diff --git a/ebean-core/src/main/java/io/ebeaninternal/server/deploy/BeanDescriptorJsonHelp.java b/ebean-core/src/main/java/io/ebeaninternal/server/deploy/BeanDescriptorJsonHelp.java
index 5abb988c7..b11c987bb 100644
--- a/ebean-core/src/main/java/io/ebeaninternal/server/deploy/BeanDescriptorJsonHelp.java
+++ b/ebean-core/src/main/java/io/ebeaninternal/server/deploy/BeanDescriptorJsonHelp.java
@@ -90,7 +90,7 @@ final class BeanDescriptorJsonHelp {
return null;
}
JsonParser newParser = node.traverse();
- SpiJsonReader newReader = jsonRead.forJson(newParser, false);
+ SpiJsonReader newReader = jsonRead.forJson(newParser);
// check for the discriminator value to determine the correct sub type
String discColumn = inheritInfo.getRoot().getDiscriminatorColumn();
diff --git a/ebean-core/src/main/java/io/ebeaninternal/server/loadcontext/DLoadBeanContext.java b/ebean-core/src/main/java/io/ebeaninternal/server/loadcontext/DLoadBeanContext.java
index 2dd6c1378..427d59de2 100644
--- a/ebean-core/src/main/java/io/ebeaninternal/server/loadcontext/DLoadBeanContext.java
+++ b/ebean-core/src/main/java/io/ebeaninternal/server/loadcontext/DLoadBeanContext.java
@@ -46,7 +46,7 @@ final class DLoadBeanContext extends DLoadBaseContext implements LoadBeanContext
/**
* Reset the buffers after a query iterator reset.
*/
- public void clear() {
+ private void clear() {
if (bufferList != null) {
bufferList.clear();
}
diff --git a/ebean-core/src/main/java/io/ebeaninternal/server/loadcontext/DLoadContext.java b/ebean-core/src/main/java/io/ebeaninternal/server/loadcontext/DLoadContext.java
index 018a9f647..bfef45804 100644
--- a/ebean-core/src/main/java/io/ebeaninternal/server/loadcontext/DLoadContext.java
+++ b/ebean-core/src/main/java/io/ebeaninternal/server/loadcontext/DLoadContext.java
@@ -57,7 +57,7 @@ public final class DLoadContext implements LoadContext {
private final ProfileLocation profileLocation;
private final ProfilingListener profilingListener;
private final Map nodePathMap = new HashMap<>();
- private PersistenceContext persistenceContext;
+ private final PersistenceContext persistenceContext;
private List secQuery;
private Object tenantId;
@@ -251,19 +251,6 @@ public final class DLoadContext implements LoadContext {
return persistenceContext;
}
- @Override
- public void resetPersistenceContext(PersistenceContext persistenceContext) {
- this.persistenceContext = persistenceContext;
- // clear the load contexts for beans and beanCollections
- for (DLoadBeanContext beanContext : beanMap.values()) {
- beanContext.clear();
- }
- for (DLoadManyContext manyContext : manyMap.values()) {
- manyContext.clear();
- }
- this.rootBeanContext.clear();
- }
-
@Override
public void register(String path, EntityBeanIntercept ebi) {
getBeanContext(path).register(ebi);
diff --git a/ebean-core/src/main/java/io/ebeaninternal/server/loadcontext/DLoadManyContext.java b/ebean-core/src/main/java/io/ebeaninternal/server/loadcontext/DLoadManyContext.java
index 8473e148b..68bd61d81 100644
--- a/ebean-core/src/main/java/io/ebeaninternal/server/loadcontext/DLoadManyContext.java
+++ b/ebean-core/src/main/java/io/ebeaninternal/server/loadcontext/DLoadManyContext.java
@@ -48,7 +48,7 @@ final class DLoadManyContext extends DLoadBaseContext implements LoadManyContext
/**
* Reset the buffers for a query iterator reset.
*/
- public void clear() {
+ private void clear() {
if (bufferList != null) {
bufferList.clear();
}
diff --git a/ebean-core/src/main/java/io/ebeaninternal/server/query/CQueryIteratorSimple.java b/ebean-core/src/main/java/io/ebeaninternal/server/query/CQueryIteratorSimple.java
index d438ec747..6d183b936 100644
--- a/ebean-core/src/main/java/io/ebeaninternal/server/query/CQueryIteratorSimple.java
+++ b/ebean-core/src/main/java/io/ebeaninternal/server/query/CQueryIteratorSimple.java
@@ -26,7 +26,6 @@ final class CQueryIteratorSimple implements QueryIterator {
public boolean hasNext() {
boolean ret = false;
try {
- request.flushPersistenceContextOnIterate();
ret = cquery.hasNext();
return ret;
} catch (SQLException e) {
diff --git a/ebean-core/src/main/java/io/ebeaninternal/server/query/CQueryIteratorWithBuffer.java b/ebean-core/src/main/java/io/ebeaninternal/server/query/CQueryIteratorWithBuffer.java
index ad1a924b5..3df436716 100644
--- a/ebean-core/src/main/java/io/ebeaninternal/server/query/CQueryIteratorWithBuffer.java
+++ b/ebean-core/src/main/java/io/ebeaninternal/server/query/CQueryIteratorWithBuffer.java
@@ -35,8 +35,6 @@ final class CQueryIteratorWithBuffer implements QueryIterator {
try {
if (buffer.isEmpty() && moreToLoad) {
// load buffer
- request.flushPersistenceContextOnIterate();
-
int i = -1;
while (moreToLoad && ++i < bufferSize) {
if (cquery.hasNext()) {
diff --git a/ebean-core/src/main/java/io/ebeaninternal/server/text/json/DJsonBeanReader.java b/ebean-core/src/main/java/io/ebeaninternal/server/text/json/DJsonBeanReader.java
index 8193d397c..79465e037 100644
--- a/ebean-core/src/main/java/io/ebeaninternal/server/text/json/DJsonBeanReader.java
+++ b/ebean-core/src/main/java/io/ebeaninternal/server/text/json/DJsonBeanReader.java
@@ -45,7 +45,7 @@ public final class DJsonBeanReader implements JsonBeanReader {
}
@Override
- public JsonBeanReader forJson(JsonParser moreJson, boolean resetContext) {
- return new DJsonBeanReader<>(desc, readJson.forJson(moreJson, resetContext));
+ public JsonBeanReader forJson(JsonParser moreJson) {
+ return new DJsonBeanReader<>(desc, readJson.forJson(moreJson));
}
}
diff --git a/ebean-core/src/main/java/io/ebeaninternal/server/text/json/ReadJson.java b/ebean-core/src/main/java/io/ebeaninternal/server/text/json/ReadJson.java
index f685188b6..7acf4e531 100644
--- a/ebean-core/src/main/java/io/ebeaninternal/server/text/json/ReadJson.java
+++ b/ebean-core/src/main/java/io/ebeaninternal/server/text/json/ReadJson.java
@@ -50,22 +50,14 @@ public final class ReadJson implements SpiJsonReader {
/**
* Construct when transferring load context, persistence context, object mapper etc to a new ReadJson instance.
*/
- private ReadJson(JsonParser moreJson, ReadJson source, boolean resetContext) {
+ private ReadJson(JsonParser moreJson, ReadJson source) {
this.parser = moreJson;
this.rootDesc = source.rootDesc;
this.pathStack = source.pathStack;
this.visitorMap = source.visitorMap;
this.objectMapper = source.objectMapper;
- if (resetContext) {
- this.persistenceContext = new DefaultPersistenceContext();
- this.loadContext = source.loadContext;
- if (loadContext != null) {
- loadContext.resetPersistenceContext(persistenceContext);
- }
- } else {
- this.persistenceContext = source.persistenceContext;
- this.loadContext = source.loadContext;
- }
+ this.persistenceContext = source.persistenceContext;
+ this.loadContext = source.loadContext;
}
private LoadContext initLoadContext(BeanDescriptor> desc, JsonReadOptions readOptions) {
@@ -96,8 +88,8 @@ public final class ReadJson implements SpiJsonReader {
* Return a new instance of ReadJson using the existing context but with a new JsonParser.
*/
@Override
- public SpiJsonReader forJson(JsonParser moreJson, boolean resetContext) {
- return new ReadJson(moreJson, this, resetContext);
+ public SpiJsonReader forJson(JsonParser moreJson) {
+ return new ReadJson(moreJson, this);
}
/**
diff --git a/ebean-core/src/main/java/io/ebeaninternal/server/transaction/DefaultPersistenceContext.java b/ebean-core/src/main/java/io/ebeaninternal/server/transaction/DefaultPersistenceContext.java
index 169ca59a3..1ff3d44fa 100644
--- a/ebean-core/src/main/java/io/ebeaninternal/server/transaction/DefaultPersistenceContext.java
+++ b/ebean-core/src/main/java/io/ebeaninternal/server/transaction/DefaultPersistenceContext.java
@@ -6,6 +6,9 @@ import io.ebeaninternal.api.SpiBeanType;
import io.ebeaninternal.api.SpiBeanTypeManager;
import io.ebeaninternal.api.SpiPersistenceContext;
+import java.lang.ref.Reference;
+import java.lang.ref.ReferenceQueue;
+import java.lang.ref.WeakReference;
import java.util.*;
import java.util.concurrent.locks.ReentrantLock;
@@ -25,14 +28,16 @@ import java.util.concurrent.locks.ReentrantLock;
*/
public final class DefaultPersistenceContext implements SpiPersistenceContext {
- /**
- * Map used hold caches. One cache per bean type.
- */
private final HashMap, ClassContext> typeCache = new HashMap<>();
-
private final ReentrantLock lock = new ReentrantLock();
+ private final ReferenceQueue