Add Uri for Message queries that include a LIMIT

* Use a query parameter (e.g. ?limit=2); LIMIT works with any
  query

Change-Id: Idd106ab4b61aec237ac9676a201e797c4f65f15b
This commit is contained in:
Marc Blank 2010-09-27 18:29:50 -07:00
parent 9ffb4fa0ec
commit 0efe738e05
3 changed files with 65 additions and 3 deletions

View File

@ -64,6 +64,8 @@ import java.util.UUID;
public abstract class EmailContent {
public static final String AUTHORITY = EmailProvider.EMAIL_AUTHORITY;
public static final Uri CONTENT_URI = Uri.parse("content://" + AUTHORITY);
public static final String LIMIT_PARAMETER = "limit";
// All classes share this
public static final String RECORD_ID = "_id";
@ -171,6 +173,11 @@ public abstract class EmailContent {
return count(context, uri, null, null);
}
static public Uri uriWithLimit(Uri uri, int limit) {
return uri.buildUpon().appendQueryParameter(EmailContent.LIMIT_PARAMETER,
Integer.toString(limit)).build();
}
/**
* no public constructor since this is a utility class
*/

View File

@ -1143,6 +1143,7 @@ public class EmailProvider extends ContentProvider {
// See the comment at delete(), above
SQLiteDatabase db = getDatabase(context);
int table = match >> BASE_SHIFT;
String limit = uri.getQueryParameter(EmailContent.LIMIT_PARAMETER);
String id;
if (Email.LOGD) {
@ -1160,7 +1161,7 @@ public class EmailProvider extends ContentProvider {
case ACCOUNT:
case HOSTAUTH:
c = db.query(TABLE_NAMES[table], projection,
selection, selectionArgs, null, null, sortOrder);
selection, selectionArgs, null, null, sortOrder, limit);
break;
case BODY_ID:
case MESSAGE_ID:
@ -1172,14 +1173,15 @@ public class EmailProvider extends ContentProvider {
case HOSTAUTH_ID:
id = uri.getPathSegments().get(1);
c = db.query(TABLE_NAMES[table], projection,
whereWithId(id, selection), selectionArgs, null, null, sortOrder);
whereWithId(id, selection), selectionArgs, null, null, sortOrder,
limit);
break;
case ATTACHMENTS_MESSAGE_ID:
// All attachments for the given message
id = uri.getPathSegments().get(2);
c = db.query(Attachment.TABLE_NAME, projection,
whereWith(Attachment.MESSAGE_KEY + "=" + id, selection),
selectionArgs, null, null, sortOrder);
selectionArgs, null, null, sortOrder, limit);
break;
default:
throw new IllegalArgumentException("Unknown URI " + uri);

View File

@ -796,6 +796,59 @@ public class ProviderTests extends ProviderTestCase2<EmailProvider> {
assertNotNull(loadBodyForMessageId(message2Id));
}
/**
* Note that we can't use EmailContent.count() here because it uses a projection including
* count(*), and count(*) is incompatible with a LIMIT (i.e. the limit would be applied to the
* single column returned with count(*), rather than to the query itself)
*/
private int count(Context context, Uri uri, String selection, String[] selectionArgs) {
Cursor c = context.getContentResolver().query(uri, EmailContent.ID_PROJECTION, selection,
selectionArgs, null);
try {
return c.getCount();
} finally {
c.close();
}
}
public void testMessageQueryWithLimit() {
final Context context = mMockContext;
// Create account and two mailboxes
Account acct = ProviderTestUtils.setupAccount("orphaned body", true, context);
Mailbox box1 = ProviderTestUtils.setupMailbox("box1", acct.mId, true, context);
Mailbox box2 = ProviderTestUtils.setupMailbox("box2", acct.mId, true, context);
// Create 4 messages in box1
ProviderTestUtils.setupMessage("message1", acct.mId, box1.mId, false, true, context);
ProviderTestUtils.setupMessage("message2", acct.mId, box1.mId, false, true, context);
ProviderTestUtils.setupMessage("message3", acct.mId, box1.mId, false, true, context);
ProviderTestUtils.setupMessage("message4", acct.mId, box1.mId, false, true, context);
// Create 4 messages in box2
ProviderTestUtils.setupMessage("message1", acct.mId, box2.mId, false, true, context);
ProviderTestUtils.setupMessage("message2", acct.mId, box2.mId, false, true, context);
ProviderTestUtils.setupMessage("message3", acct.mId, box2.mId, false, true, context);
ProviderTestUtils.setupMessage("message4", acct.mId, box2.mId, false, true, context);
// Check normal case, special case (limit 1), and arbitrary limits
assertEquals(8, count(mMockContext, Message.CONTENT_URI, null, null));
assertEquals(1, count(mMockContext, EmailContent.uriWithLimit(Message.CONTENT_URI, 1),
null, null));
assertEquals(3, count(mMockContext, EmailContent.uriWithLimit(Message.CONTENT_URI, 3),
null, null));
assertEquals(8, count(mMockContext, EmailContent.uriWithLimit(Message.CONTENT_URI, 100),
null, null));
// Check that it works with selection/selection args
String[] args = new String[] {Long.toString(box1.mId)};
assertEquals(4, count(mMockContext, Message.CONTENT_URI,
MessageColumns.MAILBOX_KEY + "=?", args));
assertEquals(1, count(mMockContext,
EmailContent.uriWithLimit(Message.CONTENT_URI, 1),
MessageColumns.MAILBOX_KEY + "=?", args));
}
/**
* Test delete orphan messages
* 1. create message without body (message id 1)