我在创建查询请求时遇到问题,该请求允许我从多个表中检索对象。
数据流的目标是在ContentProvider上进行请求调用'insert'或'update',然后让我的视图从ContentProvider加载数据,而不是网络调用(用于离线持久缓存)。
我正在使用GSON进行json序列化和反序列化。
所以说从Web服务收到的Expense对象如下:
{
"name" : "Expense1",
"amount" : 10.10
"date" : "2014-03-23 12:32:22"
"is_reimbursement" : false,
"note" : "This is a note :)",
"spends" : [
{
"user_id" : 3,
"amount_credited" : 0,
"amount_debited" : 10.3
}, {
"user_id" : 2,
"amount_credited" : 10.3,
"amount_debited" : 0
}
],
"debts" : [
{
"amount" : 10.3,
"receiver_data" : {
"confirmation" : "wait",
"user_id" : 2
},
"giver_data" : {
"confirmation" : "wait",
"user_id" : 3
}
}
]
}
这是我对应的POJO字段:
@SerializedName("is_reimbursement")
private boolean IsReimbursement;
@SerializedName("name")
private String Name;
@SerializedName("amount")
private double Amount;
@SerializedName("date")
private Timestamp Date;
@SerializedName("note")
private String Note;
@SerializedName("created_by_id")
private int CreatedById;
@SerializedName("spends")
private List<ExpenseSpend> Spends;
@SerializedName("debts")
private List<ExpenseDebt> Debts;
@SerializedName("pictures")
private List<ExpensePicture> Pictures;
然后我有一个用于EXPENSES的SQL表,以及一个用于每个子项的表(Expense_Pictures的表,一个用于Expense_Debts,一个用于ExpenseSpend)。
要插入我的数据库,我在ContentProvider中创建了插入URI,并使用ContentProvider的getContentResolver().applyBatch(ContentProvider.AUTHORITY, ops);
方法插入ExpenseObject,其中一个插入操作用于费用,然后一个用于每个子节点
这成功将上面复制的JSON对象插入到我的数据库的所有表中。
现在的问题是如何使用ContentProvider.query(...)
检索同一个POJO?
要用不同的方式表达,如何向ContentProvider发出请求,返回数据库中的所有费用(POJO,有关系)?
现在,我的查询没有返回完整的POJO信息(它没有我的费用POJO的关系字段的信息):
@Override
public Cursor query(Uri uri, String[] projection, String selection, String[] selectionArgs, String sortOrder) {
int requestType = _uriMatcher.match(uri);
SQLiteQueryBuilder queryBuilder = new SQLiteQueryBuilder();
switch(requestType){
case EXPENSES:
queryBuilder.setTables(DatabaseHelper.TABLE_EXPENSE);
queryBuilder.appendWhere(DatabaseHelper.KEY_ID + "=" + uri.getLastPathSegment());
break;
case EXPENSE_ID:
queryBuilder.setTables(DatabaseHelper.TABLE_EXPENSE);
queryBuilder.appendWhere(DatabaseHelper.KEY_ID + "=" + uri.getLastPathSegment());
break;
default:
throw new IllegalArgumentException("Content provider error, could not match URI: " + uri);
}
SQLiteDatabase sqlDB = _db.getWritableDatabase();
Cursor cursor = queryBuilder.query(sqlDB, projection, selection, selectionArgs, null, null, sortOrder);
cursor.setNotificationUri(getContext().getContentResolver(), uri);
return cursor;
}
数据库创建代码,供参考:
//EXPENSE Table create statement
private static final String CREATE_TABLE_EXPENSE = "CREATE TABLE "
+ TABLE_EXPENSE + "("
+ KEY_ID + " INTEGER PRIMARY KEY,"
+ KEY_IS_REIMBURSEMENT + " INTEGER,"
+ KEY_NAME + " TEXT,"
+ KEY_AMOUNT + " NUMERIC,"
+ KEY_DATE + " TEXT,"
+ KEY_NOTE + " TEXT,"
+ KEY_CREATED_BY_ID + " INTEGER,"
+ KEY_CREATED_AT + " TEXT,"
+ KEY_UPDATED_AT + " TEXT,"
+ KEY_DELETED_AT + " TEXT)";
//EXPENSE_DEBT Table create statement
private static final String CREATE_TABLE_EXPENSE_DEBT = "CREATE TABLE "
+ TABLE_EXPENSE_DEBT + "("
+ KEY_ID + " INTEGER PRIMARY KEY,"
+ KEY_EXPENSE_ID + " INTEGER,"
+ KEY_AMOUNT + " NUMERIC,"
+ KEY_GIVER_DATA_ID + " INTEGER,"
+ KEY_RECEIVER_DATA_ID + " INTEGER)";
//EXPENSE_DEBT_DATA Table create statement
private static final String CREATE_TABLE_EXPENSE_DEBT_DATA = "CREATE TABLE "
+ TABLE_EXPENSE_DEBT_DATA + "("
+ KEY_ID + " INTEGER PRIMARY KEY,"
+ KEY_USER_ID + " INTEGER,"
+ KEY_CONFIRMATION + " TEXT,"
+ KEY_CREATED_AT + " INTEGER,"
+ KEY_UPDATED_AT + " INTEGER)";
//EXPENSE_SPEND Table create statement
private static final String CREATE_TABLE_EXPENSE_SPEND = "CREATE TABLE "
+ TABLE_EXPENSE_SPEND + "("
+ KEY_ID + " INTEGER PRIMARY KEY,"
+ KEY_EXPENSE_ID + " INTEGER,"
+ KEY_USER_ID + " INTEGER,"
+ KEY_AMOUNT_CREDITED + " NUMERIC,"
+ KEY_AMOUNT_DEBITED + " NUMERIC)";
//EXPENSE_PICTURE Table create statement
private static final String CREATE_TABLE_EXPENSE_PICTURE = "CREATE TABLE "
+ TABLE_EXPENSE_PICTURE + "("
+ KEY_ID + " INTEGER PRIMARY KEY,"
+ KEY_EXPENSE_ID + " INTEGER,"
+ KEY_USER_ID + " INTEGER,"
+ KEY_DELETED_AT + " TEXT)";
一如既往,请不要犹豫,告诉我数据库创建代码是否有问题(如果我应该在这种情况下加入表格),或者另一种方法更适合我想要做的事情。