From 7652bc4f84dd8ffcff560c7764370d9dab8a97c7 Mon Sep 17 00:00:00 2001 From: Shubham Goyal Date: Wed, 4 Dec 2024 12:13:02 +0530 Subject: [PATCH 1/4] Refactor entityLoaderTask to use a helper class --- .../org/commcare/tasks/EntityLoaderHelper.kt | 65 +++++++++++++++++++ .../org/commcare/tasks/EntityLoaderTask.java | 56 ++++------------ 2 files changed, 76 insertions(+), 45 deletions(-) create mode 100644 app/src/org/commcare/tasks/EntityLoaderHelper.kt diff --git a/app/src/org/commcare/tasks/EntityLoaderHelper.kt b/app/src/org/commcare/tasks/EntityLoaderHelper.kt new file mode 100644 index 0000000000..d1b048fff5 --- /dev/null +++ b/app/src/org/commcare/tasks/EntityLoaderHelper.kt @@ -0,0 +1,65 @@ +package org.commcare.tasks + +import android.util.Pair +import io.reactivex.functions.Cancellable +import org.commcare.activities.EntitySelectActivity +import org.commcare.cases.entity.AsyncNodeEntityFactory +import org.commcare.cases.entity.Entity +import org.commcare.cases.entity.EntityStorageCache +import org.commcare.cases.entity.NodeEntityFactory +import org.commcare.models.database.user.models.CommCareEntityStorageCache +import org.commcare.preferences.DeveloperPreferences +import org.commcare.suite.model.Detail +import org.javarosa.core.model.condition.EvaluationContext +import org.javarosa.core.model.instance.TreeReference + +class EntityLoaderHelper( + detail: Detail, + evalCtx: EvaluationContext +) : Cancellable { + + var focusTargetIndex: Int = -1 + private var stopLoading: Boolean = false + var factory: NodeEntityFactory + + init { + evalCtx.addFunctionHandler(EntitySelectActivity.getHereFunctionHandler()) + if (detail.useAsyncStrategy()) { + val entityStorageCache: EntityStorageCache = CommCareEntityStorageCache("case") + factory = AsyncNodeEntityFactory(detail, evalCtx, entityStorageCache) + } else { + factory = NodeEntityFactory(detail, evalCtx) + if (DeveloperPreferences.collectAndDisplayEntityTraces()) { + factory.activateDebugTraceOutput() + } + } + } + + fun loadEntities(nodeset: TreeReference): Pair>, List>? { + val references = factory.expandReferenceList(nodeset) + val full: MutableList> = ArrayList() + focusTargetIndex = -1 + var indexInFullList = 0 + for (ref in references) { + if (stopLoading) { + return null + } + val e = factory.getEntity(ref) + if (e != null) { + full.add(e) + if (e.shouldReceiveFocus()) { + focusTargetIndex = indexInFullList + } + indexInFullList++ + } + } + + factory.prepareEntities(full) + factory.printAndClearTraces("build") + return Pair>, List>(full, references) + } + + override fun cancel() { + stopLoading = true + } +} diff --git a/app/src/org/commcare/tasks/EntityLoaderTask.java b/app/src/org/commcare/tasks/EntityLoaderTask.java index 3bbaec7adf..2681b3783c 100644 --- a/app/src/org/commcare/tasks/EntityLoaderTask.java +++ b/app/src/org/commcare/tasks/EntityLoaderTask.java @@ -2,15 +2,9 @@ import android.util.Pair; -import org.commcare.activities.EntitySelectActivity; import org.commcare.android.logging.ForceCloseLogger; -import org.commcare.cases.entity.AsyncNodeEntityFactory; import org.commcare.cases.entity.Entity; -import org.commcare.cases.entity.EntityStorageCache; -import org.commcare.cases.entity.NodeEntityFactory; import org.commcare.logging.XPathErrorLogger; -import org.commcare.models.database.user.models.CommCareEntityStorageCache; -import org.commcare.preferences.DeveloperPreferences; import org.commcare.suite.model.Detail; import org.commcare.tasks.templates.ManagedAsyncTask; import org.javarosa.core.model.condition.EvaluationContext; @@ -18,7 +12,6 @@ import org.javarosa.core.services.Logger; import org.javarosa.xpath.XPathException; -import java.util.ArrayList; import java.util.List; /** @@ -30,53 +23,20 @@ public class EntityLoaderTask private final static Object lock = new Object(); private static EntityLoaderTask pendingTask = null; - private final NodeEntityFactory factory; private EntityLoaderListener listener; + private final EntityLoaderHelper entityLoaderHelper; private Exception mException = null; - private int focusTargetIndex; public EntityLoaderTask(Detail detail, EvaluationContext evalCtx) { - evalCtx.addFunctionHandler(EntitySelectActivity.getHereFunctionHandler()); - if (detail.useAsyncStrategy()) { - EntityStorageCache entityStorageCache = new CommCareEntityStorageCache("case"); - this.factory = new AsyncNodeEntityFactory(detail, evalCtx, entityStorageCache); - } else { - this.factory = new NodeEntityFactory(detail, evalCtx); - if (DeveloperPreferences.collectAndDisplayEntityTraces()) { - this.factory.activateDebugTraceOutput(); - } - } + entityLoaderHelper = new EntityLoaderHelper(detail, evalCtx); } @Override protected Pair>, List> doInBackground(TreeReference... nodeset) { try { - List references = factory.expandReferenceList(nodeset[0]); - - List> full = new ArrayList<>(); - focusTargetIndex = -1; - int indexInFullList = 0; - for (TreeReference ref : references) { - if (this.isCancelled()) { - return null; - } - - Entity e = factory.getEntity(ref); - if (e != null) { - full.add(e); - if (e.shouldReceiveFocus()) { - focusTargetIndex = indexInFullList; - } - indexInFullList++; - } - } - - factory.prepareEntities(full); - factory.printAndClearTraces("build"); - return new Pair<>(full, references); + return entityLoaderHelper.loadEntities(nodeset[0]); } catch (XPathException xe) { XPathErrorLogger.INSTANCE.logErrorToCurrentApp(xe); - xe.printStackTrace(); Logger.exception("Error during EntityLoaderTask: " + ForceCloseLogger.getStackTrace(xe), xe); mException = xe; return null; @@ -99,8 +59,8 @@ protected void onPostExecute(Pair>, List Date: Thu, 5 Dec 2024 16:02:38 +0530 Subject: [PATCH 2/4] rename var --- app/src/org/commcare/tasks/EntityLoaderHelper.kt | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/app/src/org/commcare/tasks/EntityLoaderHelper.kt b/app/src/org/commcare/tasks/EntityLoaderHelper.kt index d1b048fff5..35cd11c992 100644 --- a/app/src/org/commcare/tasks/EntityLoaderHelper.kt +++ b/app/src/org/commcare/tasks/EntityLoaderHelper.kt @@ -37,7 +37,7 @@ class EntityLoaderHelper( fun loadEntities(nodeset: TreeReference): Pair>, List>? { val references = factory.expandReferenceList(nodeset) - val full: MutableList> = ArrayList() + val entities: MutableList> = ArrayList() focusTargetIndex = -1 var indexInFullList = 0 for (ref in references) { @@ -46,7 +46,7 @@ class EntityLoaderHelper( } val e = factory.getEntity(ref) if (e != null) { - full.add(e) + entities.add(e) if (e.shouldReceiveFocus()) { focusTargetIndex = indexInFullList } @@ -54,9 +54,9 @@ class EntityLoaderHelper( } } - factory.prepareEntities(full) + factory.prepareEntities(entities) factory.printAndClearTraces("build") - return Pair>, List>(full, references) + return Pair>, List>(entities, references) } override fun cancel() { From 36bbe678f8a6de4708cf6d18fa5f99d37bafb068 Mon Sep 17 00:00:00 2001 From: Shubham Goyal Date: Thu, 5 Dec 2024 16:09:35 +0530 Subject: [PATCH 3/4] separate loading of entities from references into a method --- .../org/commcare/tasks/EntityLoaderHelper.kt | 21 ++++++++++++++----- 1 file changed, 16 insertions(+), 5 deletions(-) diff --git a/app/src/org/commcare/tasks/EntityLoaderHelper.kt b/app/src/org/commcare/tasks/EntityLoaderHelper.kt index 35cd11c992..e55c753545 100644 --- a/app/src/org/commcare/tasks/EntityLoaderHelper.kt +++ b/app/src/org/commcare/tasks/EntityLoaderHelper.kt @@ -35,8 +35,22 @@ class EntityLoaderHelper( } } - fun loadEntities(nodeset: TreeReference): Pair>, List>? { + /** + * Loads and prepares a list of entities derived from the given nodeset + */ + fun loadEntities(nodeset: TreeReference): Pair>, List> { val references = factory.expandReferenceList(nodeset) + val entities = loadEntitiesWithReferences(references) + factory.prepareEntities(entities) + factory.printAndClearTraces("build") + return Pair>, List>(entities, references) + } + + + /** + * Loads a list of entities corresponding to the given references + */ + private fun loadEntitiesWithReferences(references: List): MutableList>? { val entities: MutableList> = ArrayList() focusTargetIndex = -1 var indexInFullList = 0 @@ -53,10 +67,7 @@ class EntityLoaderHelper( indexInFullList++ } } - - factory.prepareEntities(entities) - factory.printAndClearTraces("build") - return Pair>, List>(entities, references) + return entities } override fun cancel() { From 10f35489c326b768bfbd8b84681f7f3ebc9bc57e Mon Sep 17 00:00:00 2001 From: Shubham Goyal Date: Thu, 5 Dec 2024 16:24:54 +0530 Subject: [PATCH 4/4] Null Handling --- app/src/org/commcare/tasks/EntityLoaderHelper.kt | 11 +++++++---- app/src/org/commcare/tasks/EntityLoaderTask.java | 4 ++++ 2 files changed, 11 insertions(+), 4 deletions(-) diff --git a/app/src/org/commcare/tasks/EntityLoaderHelper.kt b/app/src/org/commcare/tasks/EntityLoaderHelper.kt index e55c753545..d4b40aeaf7 100644 --- a/app/src/org/commcare/tasks/EntityLoaderHelper.kt +++ b/app/src/org/commcare/tasks/EntityLoaderHelper.kt @@ -38,12 +38,15 @@ class EntityLoaderHelper( /** * Loads and prepares a list of entities derived from the given nodeset */ - fun loadEntities(nodeset: TreeReference): Pair>, List> { + fun loadEntities(nodeset: TreeReference): Pair>, List>? { val references = factory.expandReferenceList(nodeset) val entities = loadEntitiesWithReferences(references) - factory.prepareEntities(entities) - factory.printAndClearTraces("build") - return Pair>, List>(entities, references) + entities?.let { + factory.prepareEntities(entities) + factory.printAndClearTraces("build") + return Pair>, List>(entities, references) + } + return null } diff --git a/app/src/org/commcare/tasks/EntityLoaderTask.java b/app/src/org/commcare/tasks/EntityLoaderTask.java index 2681b3783c..2f4b6ac58d 100644 --- a/app/src/org/commcare/tasks/EntityLoaderTask.java +++ b/app/src/org/commcare/tasks/EntityLoaderTask.java @@ -59,6 +59,10 @@ protected void onPostExecute(Pair>, List