Merge "Introduce a SearchCursorLoader"

This commit is contained in:
Ben Komalo 2011-06-27 17:32:25 -07:00 committed by Android (Google) Code Review
commit f8acc29628
4 changed files with 83 additions and 48 deletions

View File

@ -208,21 +208,6 @@ public class EmailActivity extends Activity implements View.OnClickListener, Fra
final MessageListContext viewContext = MessageListContext.forIntent(this, intent); final MessageListContext viewContext = MessageListContext.forIntent(this, intent);
final long messageId = intent.getLongExtra(EXTRA_MESSAGE_ID, Message.NO_MESSAGE); final long messageId = intent.getLongExtra(EXTRA_MESSAGE_ID, Message.NO_MESSAGE);
if (viewContext.isSearch()) {
EmailAsyncTask.runAsyncParallel(new Runnable() {
@Override
public void run() {
try {
Controller controller = Controller.getInstance(EmailActivity.this);
controller.searchMessages(
viewContext.mAccountId, viewContext.getSearchParams());
} catch (MessagingException e) {
// TODO: handle.
Log.e(Logging.LOG_TAG, "Got exception while searching " + e);
}
}});
}
mUIController.open(viewContext, messageId); mUIController.open(viewContext, messageId);
} }

View File

@ -288,6 +288,11 @@ public class MessageListFragment extends ListFragment
return getMailboxId() < 0; return getMailboxId() < 0;
} }
public MessageListContext getListContext() {
initializeArgCache();
return mListContext;
}
@Override @Override
public void onAttach(Activity activity) { public void onAttach(Activity activity) {
if (Logging.DEBUG_LIFECYCLE && Email.DEBUG) { if (Logging.DEBUG_LIFECYCLE && Email.DEBUG) {
@ -1033,7 +1038,6 @@ public class MessageListFragment extends ListFragment
} }
determineFooterMode(); determineFooterMode();
if (mListFooterMode != LIST_FOOTER_MODE_NONE) { if (mListFooterMode != LIST_FOOTER_MODE_NONE) {
lv.addFooterView(mListFooterView); lv.addFooterView(mListFooterView);
lv.setAdapter(mListAdapter); lv.setAdapter(mListAdapter);
@ -1134,13 +1138,13 @@ public class MessageListFragment extends ListFragment
@Override @Override
public Loader<Cursor> onCreateLoader(int id, Bundle args) { public Loader<Cursor> onCreateLoader(int id, Bundle args) {
final long mailboxId = getMailboxId(); final MessageListContext listContext = getListContext();
if (Logging.DEBUG_LIFECYCLE && Email.DEBUG) { if (Logging.DEBUG_LIFECYCLE && Email.DEBUG) {
Log.d(Logging.LOG_TAG, MessageListFragment.this Log.d(Logging.LOG_TAG, MessageListFragment.this
+ " onCreateLoader(messages) mailboxId=" + mailboxId); + " onCreateLoader(messages) listContext=" + listContext);
} }
mIsFirstLoad = true; mIsFirstLoad = true;
return MessagesAdapter.createLoader(getActivity(), mailboxId); return MessagesAdapter.createLoader(getActivity(), listContext);
} }
@Override @Override
@ -1149,8 +1153,7 @@ public class MessageListFragment extends ListFragment
Log.d(Logging.LOG_TAG, MessageListFragment.this Log.d(Logging.LOG_TAG, MessageListFragment.this
+ " onLoadFinished(messages) mailboxId=" + getMailboxId()); + " onLoadFinished(messages) mailboxId=" + getMailboxId());
} }
MessagesAdapter.CursorWithExtras cursor = MessagesAdapter.CursorWithExtras cursor = (MessagesAdapter.CursorWithExtras) c;
(MessagesAdapter.CursorWithExtras) c;
if (!cursor.mIsFound) { if (!cursor.mIsFound) {
mCallback.onMailboxNotFound(); mCallback.onMailboxNotFound();
@ -1195,7 +1198,7 @@ public class MessageListFragment extends ListFragment
updateSelectionMode(); updateSelectionMode();
showSendCommandIfNecessary(); showSendCommandIfNecessary();
showNoMessageText((cursor.getCount() == 0) showNoMessageText((cursor.getCount() == 0)
&& (mListFooterMode == LIST_FOOTER_MODE_NONE)); && (getListContext().isSearch() || (mListFooterMode == LIST_FOOTER_MODE_NONE)));
// We want to make visible the selection only for the first load. // We want to make visible the selection only for the first load.
// Re-load caused by content changed events shouldn't scroll the list. // Re-load caused by content changed events shouldn't scroll the list.

View File

@ -16,18 +16,6 @@
package com.android.email.activity; package com.android.email.activity;
import com.android.email.Email;
import com.android.email.ResourceHelper;
import com.android.email.data.ThrottlingCursorLoader;
import com.android.emailcommon.Logging;
import com.android.emailcommon.provider.Account;
import com.android.emailcommon.provider.EmailContent;
import com.android.emailcommon.provider.EmailContent.Message;
import com.android.emailcommon.provider.EmailContent.MessageColumns;
import com.android.emailcommon.provider.Mailbox;
import com.android.emailcommon.utility.TextUtilities;
import com.android.emailcommon.utility.Utility;
import android.content.Context; import android.content.Context;
import android.content.Loader; import android.content.Loader;
import android.database.Cursor; import android.database.Cursor;
@ -39,6 +27,22 @@ import android.view.View;
import android.view.ViewGroup; import android.view.ViewGroup;
import android.widget.CursorAdapter; import android.widget.CursorAdapter;
import com.android.email.Controller;
import com.android.email.Email;
import com.android.email.MessageListContext;
import com.android.email.ResourceHelper;
import com.android.email.data.ThrottlingCursorLoader;
import com.android.emailcommon.Logging;
import com.android.emailcommon.mail.MessagingException;
import com.android.emailcommon.provider.Account;
import com.android.emailcommon.provider.EmailContent;
import com.android.emailcommon.provider.EmailContent.Message;
import com.android.emailcommon.provider.EmailContent.MessageColumns;
import com.android.emailcommon.provider.Mailbox;
import com.android.emailcommon.utility.TextUtilities;
import com.android.emailcommon.utility.Utility;
import com.google.common.base.Preconditions;
import java.util.HashSet; import java.util.HashSet;
import java.util.Set; import java.util.Set;
@ -259,16 +263,17 @@ import java.util.Set;
* *
* @return always of {@link CursorWithExtras}. * @return always of {@link CursorWithExtras}.
*/ */
public static Loader<Cursor> createLoader(Context context, long mailboxId) { public static Loader<Cursor> createLoader(Context context, MessageListContext listContext) {
if (Logging.DEBUG_LIFECYCLE && Email.DEBUG) { if (Logging.DEBUG_LIFECYCLE && Email.DEBUG) {
Log.d(Logging.LOG_TAG, "MessagesAdapter createLoader mailboxId=" + mailboxId); Log.d(Logging.LOG_TAG, "MessagesAdapter createLoader listContext=" + listContext);
} }
return new MessagesCursorLoader(context, mailboxId); return listContext.isSearch()
? new SearchCursorLoader(context, listContext)
: new MessagesCursorLoader(context, listContext.getMailboxId());
} }
static private class MessagesCursorLoader extends ThrottlingCursorLoader { private static class MessagesCursorLoader extends ThrottlingCursorLoader {
private final Context mContext; protected final Context mContext;
private final long mMailboxId; private final long mMailboxId;
public MessagesCursorLoader(Context context, long mailboxId) { public MessagesCursorLoader(Context context, long mailboxId) {
@ -334,4 +339,41 @@ import java.util.Set;
isRefreshable, countAccounts); isRefreshable, countAccounts);
} }
} }
/**
* A special loader used to perform a search.
*/
private static class SearchCursorLoader extends MessagesCursorLoader {
private final MessageListContext mListContext;
private boolean mResultCountAvailable = false;
public SearchCursorLoader(Context context, MessageListContext listContext) {
super(context, listContext.getMailboxId());
Preconditions.checkArgument(listContext.isSearch());
mListContext = listContext;
}
@Override
public Cursor loadInBackground() {
if (mResultCountAvailable) {
return super.loadInBackground();
}
// The search results info hasn't even been loaded yet, so the Controller has not yet
// initialized the search mailbox properly. Kick off the search first.
Controller controller = Controller.getInstance(mContext);
try {
// TODO: wire through search count information and pad it into the cursor returned
// so that the caller knows how many is in the entire result set.
controller.searchMessages(mListContext.mAccountId, mListContext.getSearchParams());
} catch (MessagingException e) {
// TODO: handle.
}
mResultCountAvailable = true;
// Return whatever the super would do, now that we know the results are ready.
return super.loadInBackground();
}
}
} }

View File

@ -17,6 +17,7 @@
package com.android.email.activity; package com.android.email.activity;
import com.android.email.DBTestHelper; import com.android.email.DBTestHelper;
import com.android.email.MessageListContext;
import com.android.email.provider.ProviderTestUtils; import com.android.email.provider.ProviderTestUtils;
import com.android.emailcommon.provider.Account; import com.android.emailcommon.provider.Account;
import com.android.emailcommon.provider.Mailbox; import com.android.emailcommon.provider.Mailbox;
@ -56,9 +57,11 @@ public class MessagesAdapterTests extends LoaderTestCase {
return box.mId; return box.mId;
} }
private MessagesAdapter.CursorWithExtras getLoaderResult(long mailboxId) { private MessagesAdapter.CursorWithExtras getLoaderResult(long accountId, long mailboxId) {
return (MessagesAdapter.CursorWithExtras) getLoaderResultSynchronously( return (MessagesAdapter.CursorWithExtras) getLoaderResultSynchronously(
MessagesAdapter.createLoader(mProviderContext, mailboxId)); MessagesAdapter.createLoader(
mProviderContext,
MessageListContext.forMailbox(accountId, mailboxId)));
} }
/** /**
@ -68,7 +71,7 @@ public class MessagesAdapterTests extends LoaderTestCase {
final long accountId = createAccount(false); final long accountId = createAccount(false);
final long mailboxId = createMailbox(accountId, Mailbox.TYPE_MAIL); final long mailboxId = createMailbox(accountId, Mailbox.TYPE_MAIL);
MessagesAdapter.CursorWithExtras result = getLoaderResult(mailboxId); MessagesAdapter.CursorWithExtras result = getLoaderResult(accountId, mailboxId);
assertTrue(result.mIsFound); assertTrue(result.mIsFound);
assertEquals(accountId, result.mAccount.mId); assertEquals(accountId, result.mAccount.mId);
assertEquals(mailboxId, result.mMailbox.mId); assertEquals(mailboxId, result.mMailbox.mId);
@ -83,7 +86,7 @@ public class MessagesAdapterTests extends LoaderTestCase {
final long accountId = createAccount(true); final long accountId = createAccount(true);
final long mailboxId = createMailbox(accountId, Mailbox.TYPE_MAIL); final long mailboxId = createMailbox(accountId, Mailbox.TYPE_MAIL);
MessagesAdapter.CursorWithExtras result = getLoaderResult(mailboxId); MessagesAdapter.CursorWithExtras result = getLoaderResult(accountId, mailboxId);
assertTrue(result.mIsFound); assertTrue(result.mIsFound);
assertEquals(accountId, result.mAccount.mId); assertEquals(accountId, result.mAccount.mId);
assertEquals(mailboxId, result.mMailbox.mId); assertEquals(mailboxId, result.mMailbox.mId);
@ -98,7 +101,7 @@ public class MessagesAdapterTests extends LoaderTestCase {
final long accountId = createAccount(false); final long accountId = createAccount(false);
final long mailboxId = createMailbox(accountId, Mailbox.TYPE_DRAFTS); final long mailboxId = createMailbox(accountId, Mailbox.TYPE_DRAFTS);
MessagesAdapter.CursorWithExtras result = getLoaderResult(mailboxId); MessagesAdapter.CursorWithExtras result = getLoaderResult(accountId, mailboxId);
assertTrue(result.mIsFound); assertTrue(result.mIsFound);
assertEquals(accountId, result.mAccount.mId); assertEquals(accountId, result.mAccount.mId);
assertEquals(mailboxId, result.mMailbox.mId); assertEquals(mailboxId, result.mMailbox.mId);
@ -110,7 +113,8 @@ public class MessagesAdapterTests extends LoaderTestCase {
* Mailbox not found. * Mailbox not found.
*/ */
public void testMailboxNotFound() { public void testMailboxNotFound() {
MessagesAdapter.CursorWithExtras result = getLoaderResult(NO_SUCH_MAILBOX_ID); MessagesAdapter.CursorWithExtras result = getLoaderResult(
createAccount(false), NO_SUCH_MAILBOX_ID);
assertFalse(result.mIsFound); assertFalse(result.mIsFound);
assertNull(result.mAccount); assertNull(result.mAccount);
assertNull(result.mMailbox); assertNull(result.mMailbox);
@ -124,7 +128,7 @@ public class MessagesAdapterTests extends LoaderTestCase {
public void testAccountNotFound() { public void testAccountNotFound() {
final long mailboxId = createMailbox(NO_SUCH_ACCOUNT_ID, Mailbox.TYPE_MAIL); final long mailboxId = createMailbox(NO_SUCH_ACCOUNT_ID, Mailbox.TYPE_MAIL);
MessagesAdapter.CursorWithExtras result = getLoaderResult(mailboxId); MessagesAdapter.CursorWithExtras result = getLoaderResult(NO_SUCH_ACCOUNT_ID, mailboxId);
assertFalse(result.mIsFound); assertFalse(result.mIsFound);
assertNull(result.mAccount); assertNull(result.mAccount);
assertNull(result.mMailbox); assertNull(result.mMailbox);
@ -136,7 +140,8 @@ public class MessagesAdapterTests extends LoaderTestCase {
* Magic mailbox. (always found) * Magic mailbox. (always found)
*/ */
public void testMagicMailbox() { public void testMagicMailbox() {
MessagesAdapter.CursorWithExtras result = getLoaderResult(Mailbox.QUERY_ALL_INBOXES); MessagesAdapter.CursorWithExtras result = getLoaderResult(
Account.ACCOUNT_ID_COMBINED_VIEW, Mailbox.QUERY_ALL_INBOXES);
assertTrue(result.mIsFound); assertTrue(result.mIsFound);
assertNull(result.mAccount); assertNull(result.mAccount);
assertNull(result.mMailbox); assertNull(result.mMailbox);