diff --git a/src/com/fsck/k9/controller/MessagingController.java b/src/com/fsck/k9/controller/MessagingController.java index 4d0dcf2cc..7578591ab 100644 --- a/src/com/fsck/k9/controller/MessagingController.java +++ b/src/com/fsck/k9/controller/MessagingController.java @@ -3560,6 +3560,47 @@ public class MessagingController implements Runnable { } } + public void deleteThreads(final Message[] messages) { + actOnMessages(messages, new MessageActor() { + + @Override + public void act(final Account account, final Folder folder, + final List accountMessages) { + + for (Message message : accountMessages) { + suppressMessage(account, folder.getName(), message); + } + + putBackground("deleteThreads", null, new Runnable() { + @Override + public void run() { + deleteThreadsSynchronous(account, folder.getName(), accountMessages); + } + }); + } + }); + } + + public void deleteThreadsSynchronous(Account account, String folderName, + List messages) { + + try { + LocalStore localStore = account.getLocalStore(); + + List messagesToDelete = new ArrayList(); + for (Message message : messages) { + long rootId = ((LocalMessage) message).getRootId(); + Message[] messagesInThread = localStore.getMessagesInThread(rootId); + Collections.addAll(messagesToDelete, messagesInThread); + } + + deleteMessagesSynchronous(account, folderName, + messagesToDelete.toArray(EMPTY_MESSAGE_ARRAY), null); + } catch (MessagingException e) { + Log.e(K9.LOG_TAG, "Something went wrong while deleting threads", e); + } + } + public void deleteMessages(final Message[] messages, final MessagingListener listener) { actOnMessages(messages, new MessageActor() { diff --git a/src/com/fsck/k9/fragment/MessageListFragment.java b/src/com/fsck/k9/fragment/MessageListFragment.java index 9e9d00467..04b789d07 100644 --- a/src/com/fsck/k9/fragment/MessageListFragment.java +++ b/src/com/fsck/k9/fragment/MessageListFragment.java @@ -1068,7 +1068,11 @@ public class MessageListFragment extends SherlockFragment implements OnItemClick } private void onDelete(Message[] messages) { - mController.deleteMessages(messages, null); + if (mThreadedList) { + mController.deleteThreads(messages); + } else { + mController.deleteMessages(messages, null); + } } @Override @@ -2563,7 +2567,7 @@ public class MessageListFragment extends SherlockFragment implements OnItemClick } private Message[] getCheckedMessages() { - Message[] messages = new Message[mSelectedCount]; + Message[] messages = new Message[mSelected.size()]; int out = 0; for (int position = 0, end = mAdapter.getCount(); position < end; position++) { if (mSelected.get(position, false)) { diff --git a/src/com/fsck/k9/mail/store/LocalStore.java b/src/com/fsck/k9/mail/store/LocalStore.java index 9d8ca9d9b..f4120408a 100644 --- a/src/com/fsck/k9/mail/store/LocalStore.java +++ b/src/com/fsck/k9/mail/store/LocalStore.java @@ -73,6 +73,9 @@ import com.fsck.k9.mail.store.StorageManager.StorageProvider; import com.fsck.k9.provider.AttachmentProvider; import com.fsck.k9.provider.EmailProvider; import com.fsck.k9.search.LocalSearch; +import com.fsck.k9.search.SearchSpecification.Attribute; +import com.fsck.k9.search.SearchSpecification.SearchCondition; +import com.fsck.k9.search.SearchSpecification.Searchfield; import com.fsck.k9.search.SqlQueryBuilder; /** @@ -963,7 +966,10 @@ public class LocalStore extends Store implements Serializable { List queryArgs = new ArrayList(); SqlQueryBuilder.buildWhereClause(mAccount, search.getConditions(), query, queryArgs); - String where = query.toString(); + // Avoid "ambiguous column name" error by prefixing "id" with the message table name + String where = SqlQueryBuilder.addPrefixToSelection(new String[] { "id" }, + "messages.", query.toString()); + String[] selectionArgs = queryArgs.toArray(EMPTY_STRING_ARRAY); String sqlQuery = "SELECT " + GET_MESSAGES_COLS + "FROM messages " + @@ -1036,6 +1042,16 @@ public class LocalStore extends Store implements Serializable { } + public Message[] getMessagesInThread(final long rootId) throws MessagingException { + String rootIdString = Long.toString(rootId); + + LocalSearch search = new LocalSearch(); + search.and(Searchfield.THREAD_ROOT, rootIdString, Attribute.EQUALS); + search.or(new SearchCondition(Searchfield.ID, Attribute.EQUALS, rootIdString)); + + return searchForMessages(null, search); + } + public AttachmentInfo getAttachmentInfo(final String attachmentId) throws UnavailableStorageException { return database.execute(false, new DbCallback() { @Override diff --git a/src/com/fsck/k9/provider/EmailProvider.java b/src/com/fsck/k9/provider/EmailProvider.java index 38ebb9cdc..150c272dc 100644 --- a/src/com/fsck/k9/provider/EmailProvider.java +++ b/src/com/fsck/k9/provider/EmailProvider.java @@ -15,6 +15,7 @@ import com.fsck.k9.mail.store.LockableDatabase; import com.fsck.k9.mail.store.LockableDatabase.DbCallback; import com.fsck.k9.mail.store.LockableDatabase.WrappedException; import com.fsck.k9.mail.store.UnavailableStorageException; +import com.fsck.k9.search.SqlQueryBuilder; import android.annotation.TargetApi; import android.content.ContentProvider; @@ -257,9 +258,11 @@ public class EmailProvider extends ContentProvider { query.append(" FROM messages m " + "LEFT JOIN folders f ON (m.folder_id = f.id) " + "WHERE "); - query.append(addPrefixToSelection(MESSAGES_COLUMNS, "m.", where)); + query.append(SqlQueryBuilder.addPrefixToSelection(MESSAGES_COLUMNS, + "m.", where)); query.append(" ORDER BY "); - query.append(addPrefixToSelection(MESSAGES_COLUMNS, "m.", sortOrder)); + query.append(SqlQueryBuilder.addPrefixToSelection(MESSAGES_COLUMNS, + "m.", sortOrder)); cursor = db.rawQuery(query.toString(), selectionArgs); } else { @@ -332,7 +335,8 @@ public class EmailProvider extends ContentProvider { if (!StringUtils.isNullOrEmpty(selection)) { query.append("AND ("); - query.append(addPrefixToSelection(MESSAGES_COLUMNS, "h.", selection)); + query.append(SqlQueryBuilder.addPrefixToSelection(MESSAGES_COLUMNS, + "h.", selection)); query.append(") "); } @@ -340,7 +344,8 @@ public class EmailProvider extends ContentProvider { if (!StringUtils.isNullOrEmpty(sortOrder)) { query.append(" ORDER BY "); - query.append(addPrefixToSelection(MESSAGES_COLUMNS, "m.", sortOrder)); + query.append(SqlQueryBuilder.addPrefixToSelection(MESSAGES_COLUMNS, + "m.", sortOrder)); } return db.rawQuery(query.toString(), selectionArgs); @@ -351,15 +356,6 @@ public class EmailProvider extends ContentProvider { } } - private String addPrefixToSelection(String[] columnNames, String prefix, String selection) { - String result = selection; - for (String columnName : columnNames) { - result = result.replaceAll("\\b" + columnName + "\\b", prefix + columnName); - } - - return result; - } - private Account getAccount(String accountUuid) { if (mPreferences == null) { Context appContext = getContext().getApplicationContext(); diff --git a/src/com/fsck/k9/search/SqlQueryBuilder.java b/src/com/fsck/k9/search/SqlQueryBuilder.java index 478ecc7da..22d087ba0 100644 --- a/src/com/fsck/k9/search/SqlQueryBuilder.java +++ b/src/com/fsck/k9/search/SqlQueryBuilder.java @@ -220,4 +220,13 @@ public class SqlQueryBuilder { } } } + + public static String addPrefixToSelection(String[] columnNames, String prefix, String selection) { + String result = selection; + for (String columnName : columnNames) { + result = result.replaceAll("\\b" + columnName + "\\b", prefix + columnName); + } + + return result; + } }