mirror of https://github.com/tasks/tasks
You cannot select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
171 lines
5.0 KiB
Java
171 lines
5.0 KiB
Java
/**
|
|
* Copyright (c) 2012 Todoroo Inc
|
|
*
|
|
* See the file "LICENSE" for the full license governing this code.
|
|
*/
|
|
package com.todoroo.andlib.data;
|
|
|
|
import java.lang.reflect.Constructor;
|
|
import java.lang.reflect.InvocationTargetException;
|
|
import java.util.Set;
|
|
|
|
import android.content.ContentResolver;
|
|
import android.content.ContentValues;
|
|
import android.content.Context;
|
|
import android.database.Cursor;
|
|
import android.net.Uri;
|
|
import android.util.Log;
|
|
|
|
import com.todoroo.andlib.service.Autowired;
|
|
import com.todoroo.andlib.service.DependencyInjectionService;
|
|
import com.todoroo.andlib.sql.Criterion;
|
|
import com.todoroo.andlib.sql.Query;
|
|
import com.todoroo.andlib.utility.AndroidUtilities;
|
|
|
|
|
|
/**
|
|
* DAO for reading and writing values from an Android ContentResolver
|
|
*
|
|
* @author Tim Su <tim@todoroo.com>
|
|
*
|
|
* @param <TYPE> model type
|
|
*/
|
|
public class ContentResolverDao<TYPE extends AbstractModel> {
|
|
|
|
/** class of model */
|
|
private final Class<TYPE> modelClass;
|
|
|
|
/** base content uri */
|
|
private final Uri baseUri;
|
|
|
|
/** content resolver */
|
|
private final ContentResolver cr;
|
|
|
|
@Autowired
|
|
protected Boolean debug;
|
|
|
|
public ContentResolverDao(Class<TYPE> modelClass, Context context, Uri baseUri) {
|
|
DependencyInjectionService.getInstance().inject(this);
|
|
this.modelClass = modelClass;
|
|
if(debug == null)
|
|
debug = false;
|
|
this.baseUri = baseUri;
|
|
|
|
cr = context.getContentResolver();
|
|
}
|
|
|
|
/**
|
|
* Returns a URI for a single id
|
|
* @param id
|
|
* @return
|
|
*/
|
|
private Uri uriWithId(long id) {
|
|
return Uri.withAppendedPath(baseUri, Long.toString(id));
|
|
}
|
|
|
|
/**
|
|
* Delete specific item from the given table
|
|
* @param id
|
|
* @return number of rows affected
|
|
*/
|
|
public int delete(long id) {
|
|
return cr.delete(uriWithId(id), null, null);
|
|
}
|
|
|
|
/**
|
|
* Delete by criteria
|
|
* @param where
|
|
* @return number of rows affected
|
|
*/
|
|
public int deleteWhere(Criterion where) {
|
|
return cr.delete(baseUri, where.toString(), null);
|
|
}
|
|
|
|
/**
|
|
* Query content provider
|
|
* @param query
|
|
* @return
|
|
*/
|
|
public TodorooCursor<TYPE> query(Query query) {
|
|
if(debug)
|
|
Log.i("SQL-" + modelClass.getSimpleName(), query.toString()); //$NON-NLS-1$
|
|
Cursor cursor = query.queryContentResolver(cr, baseUri);
|
|
return new TodorooCursor<TYPE>(cursor, query.getFields());
|
|
}
|
|
|
|
/**
|
|
* Create new or save existing model
|
|
* @param model
|
|
* @return true if data was written to the db, false otherwise
|
|
*/
|
|
public boolean save(TYPE model) {
|
|
writeTransitoriesToModelContentValues(model);
|
|
if(model.isSaved()) {
|
|
if(model.getSetValues() == null)
|
|
return false;
|
|
if(cr.update(uriWithId(model.getId()), model.getSetValues(), null, null) != 0)
|
|
return true;
|
|
}
|
|
Uri uri = cr.insert(baseUri, model.getMergedValues());
|
|
long id = Long.parseLong(uri.getLastPathSegment());
|
|
model.setId(id);
|
|
model.markSaved();
|
|
return true;
|
|
}
|
|
|
|
private void writeTransitoriesToModelContentValues(AbstractModel model) {
|
|
Set<String> keys = model.getAllTransitoryKeys();
|
|
if (keys != null) {
|
|
ContentValues transitories = new ContentValues();
|
|
for (String key : keys) {
|
|
String newKey = AbstractModel.RETAIN_TRANSITORY_PREFIX + key;
|
|
Object value = model.getTransitory(key);
|
|
AndroidUtilities.putInto(transitories, newKey, value, false);
|
|
}
|
|
model.mergeWith(transitories);
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Returns object corresponding to the given identifier
|
|
*
|
|
* @param database
|
|
* @param table
|
|
* name of table
|
|
* @param properties
|
|
* properties to read
|
|
* @param id
|
|
* id of item
|
|
* @return null if no item found
|
|
*/
|
|
public TYPE fetch(long id, Property<?>... properties) {
|
|
TodorooCursor<TYPE> cursor = query(
|
|
Query.select(properties).where(AbstractModel.ID_PROPERTY.eq(id)));
|
|
try {
|
|
if (cursor.getCount() == 0)
|
|
return null;
|
|
cursor.moveToFirst();
|
|
Constructor<TYPE> constructor = modelClass.getConstructor(TodorooCursor.class);
|
|
return constructor.newInstance(cursor);
|
|
} catch (SecurityException e) {
|
|
throw new RuntimeException(e);
|
|
} catch (NoSuchMethodException e) {
|
|
throw new RuntimeException(e);
|
|
} catch (IllegalArgumentException e) {
|
|
throw new RuntimeException(e);
|
|
} catch (InstantiationException e) {
|
|
throw new RuntimeException(e);
|
|
} catch (IllegalAccessException e) {
|
|
throw new RuntimeException(e);
|
|
} catch (InvocationTargetException e) {
|
|
throw new RuntimeException(e);
|
|
} finally {
|
|
try {
|
|
cursor.close();
|
|
} catch (NullPointerException e) {
|
|
// cursor was not open
|
|
}
|
|
}
|
|
}
|
|
}
|