diff --git a/src/main/java/com/todoroo/andlib/data/DatabaseDao.java b/src/main/java/com/todoroo/andlib/data/DatabaseDao.java index 7b2742dcf..1643ed76d 100644 --- a/src/main/java/com/todoroo/andlib/data/DatabaseDao.java +++ b/src/main/java/com/todoroo/andlib/data/DatabaseDao.java @@ -14,7 +14,6 @@ import com.todoroo.astrid.dao.Database; import org.tasks.BuildConfig; -import java.util.ArrayList; import java.util.List; import java.util.concurrent.atomic.AtomicBoolean; @@ -53,9 +52,7 @@ public class DatabaseDao { // --- dao methods public List toList(Query query) { - final List result = new ArrayList<>(); - query(result::add, query); - return result; + return query(query).toList(); } public void query(Query query, Callback callback) { @@ -63,36 +60,11 @@ public class DatabaseDao { } public void query(Callback callback, Query query) { - TodorooCursor cursor = query(query); - try { - for (cursor.moveToFirst(); !cursor.isAfterLast(); cursor.moveToNext()) { - callback.apply(fromCursor(cursor)); - } - } finally { - cursor.close(); - } + query(query).forEach(callback); } public TYPE getFirst(Query query) { - TodorooCursor cursor = query(query); - try { - return cursor.moveToFirst() ? fromCursor(cursor) : null; - } finally { - cursor.close(); - } - } - - private TYPE fromCursor(TodorooCursor cursor) { - TYPE instance; - try { - instance = modelClass.newInstance(); - } catch (InstantiationException e) { - throw new RuntimeException(e); - } catch (IllegalAccessException e) { - throw new RuntimeException(e); - } - instance.readPropertiesFromCursor(cursor); - return instance; + return query(query).first(); } /** @@ -105,7 +77,7 @@ public class DatabaseDao { Timber.v(queryString); } Cursor cursor = database.rawQuery(queryString); - return new TodorooCursor<>(cursor, query.getFields()); + return new TodorooCursor<>(modelClass, cursor, query.getFields()); } /** @@ -116,7 +88,7 @@ public class DatabaseDao { for(int i = 0; i < properties.length; i++) { fields[i] = properties[i].name; } - return new TodorooCursor<>(database.getDatabase().query(table.name, + return new TodorooCursor<>(modelClass, database.getDatabase().query(table.name, fields, selection, selectionArgs, null, null, null), properties); } @@ -269,11 +241,6 @@ public class DatabaseDao { // --- helper methods public int count(Query query) { - TodorooCursor cursor = query(query); - try { - return cursor.getCount(); - } finally { - cursor.close(); - } + return query(query).count(); } } diff --git a/src/main/java/com/todoroo/andlib/data/TodorooCursor.java b/src/main/java/com/todoroo/andlib/data/TodorooCursor.java index 523d0ee9e..540153e6e 100644 --- a/src/main/java/com/todoroo/andlib/data/TodorooCursor.java +++ b/src/main/java/com/todoroo/andlib/data/TodorooCursor.java @@ -10,6 +10,8 @@ import android.database.CursorWrapper; import com.todoroo.andlib.data.Property.PropertyVisitor; +import java.util.ArrayList; +import java.util.List; import java.util.WeakHashMap; /** @@ -23,6 +25,7 @@ import java.util.WeakHashMap; */ public class TodorooCursor extends CursorWrapper { + private final Class modelClass; /** Properties read by this cursor */ private final Property[] properties; @@ -39,13 +42,63 @@ public class TodorooCursor extends CursorWrapper { * * @param properties properties read from this cursor */ - public TodorooCursor(Cursor cursor, Property[] properties) { + public TodorooCursor(Class modelClass, Cursor cursor, Property[] properties) { super(cursor); + this.modelClass = modelClass; this.properties = properties; columnIndexCache = new WeakHashMap<>(); } + public List toList() { + try { + List result = new ArrayList<>(); + forEach(result::add); + return result; + } finally { + close(); + } + } + + public void forEach(Callback function) { + try { + for (moveToFirst() ; !isAfterLast() ; moveToNext()) { + function.apply(toModel()); + } + } finally { + close(); + } + } + + public TYPE toModel() { + TYPE instance; + try { + instance = modelClass.newInstance(); + } catch (InstantiationException e) { + throw new RuntimeException(e); + } catch (IllegalAccessException e) { + throw new RuntimeException(e); + } + instance.readPropertiesFromCursor(this); + return instance; + } + + public int count() { + try { + return getCount(); + } finally { + close(); + } + } + + public TYPE first() { + try { + return moveToFirst() ? toModel() : null; + } finally { + close(); + } + } + /** * Get the value for the given property on the underlying {@link Cursor} *