Skip to content

Commit c76b358

Browse files
committed
feat(notifications): trigger sent folder not found when folder is missing
1 parent 40c17ef commit c76b358

5 files changed

Lines changed: 80 additions & 40 deletions

File tree

legacy/ui/legacy/src/main/java/com/fsck/k9/activity/MessageCompose.java

Lines changed: 47 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22

33

44
import java.io.File;
5+
import java.util.ArrayList;
56
import java.util.Date;
67
import java.util.HashMap;
78
import java.util.List;
@@ -128,13 +129,18 @@
128129
import net.thunderbird.core.featureflag.compat.FeatureFlagProviderCompat;
129130
import net.thunderbird.core.preference.GeneralSettingsManager;
130131
import net.thunderbird.core.ui.theme.manager.ThemeManager;
132+
import net.thunderbird.feature.notification.api.content.NotificationFactoryCoroutineCompat;
133+
import net.thunderbird.feature.notification.api.content.SentFolderNotFoundNotification;
134+
import net.thunderbird.feature.notification.api.sender.NotificationSender;
135+
import net.thunderbird.feature.notification.api.sender.compat.NotificationSenderCompat;
131136
import net.thunderbird.feature.search.legacy.LocalMessageSearch;
132137
import org.openintents.openpgp.OpenPgpApiManager;
133138
import org.openintents.openpgp.util.OpenPgpIntentStarter;
134139
import net.thunderbird.core.logging.legacy.Log;
135140
import static com.fsck.k9.activity.compose.AttachmentPresenter.REQUEST_CODE_ATTACHMENT_URI;
136141
import static app.k9mail.core.android.common.camera.CameraCaptureHandler.CAMERA_PERMISSION_REQUEST_CODE;
137142
import static app.k9mail.core.android.common.camera.CameraCaptureHandler.REQUEST_IMAGE_CAPTURE;
143+
import static net.thunderbird.feature.notification.api.content.SentFolderNotFoundNotificationKt.SentFolderNotFoundNotification;
138144

139145

140146
@SuppressWarnings("deprecation") // TODO get rid of activity dialogs and indeterminate progress bars
@@ -208,6 +214,8 @@ public class MessageCompose extends K9Activity implements OnClickListener,
208214

209215
private final CameraCaptureHandler cameraCaptureHandler = DI.get(CameraCaptureHandler.class);
210216
private final FeatureFlagProvider featureFlagProvider = DI.get(FeatureFlagProvider.class);
217+
private final NotificationSender notificationSender = DI.get(NotificationSender.class);
218+
private final NotificationSenderCompat notificationSenderCompat = new NotificationSenderCompat(notificationSender);
211219

212220
private QuotedMessagePresenter quotedMessagePresenter;
213221
private MessageLoaderHelper messageLoaderHelper;
@@ -293,16 +301,7 @@ public void onCreate(Bundle savedInstanceState) {
293301

294302
final Intent intent = getIntent();
295303

296-
String messageReferenceString = intent.getStringExtra(EXTRA_MESSAGE_REFERENCE);
297-
relatedMessageReference = MessageReference.parse(messageReferenceString);
298-
299-
final String accountUuid = (relatedMessageReference != null) ?
300-
relatedMessageReference.getAccountUuid() :
301-
intent.getStringExtra(EXTRA_ACCOUNT);
302-
303-
if (accountUuid != null) {
304-
account = preferences.getAccount(accountUuid);
305-
}
304+
fetchAccount(intent);
306305

307306
if (account == null) {
308307
account = preferences.getDefaultAccount();
@@ -540,10 +539,36 @@ public void onTextChanged(CharSequence s, int start, int before, int count) {
540539
}
541540
}
542541

542+
private void fetchAccount(Intent intent) {
543+
String messageReferenceString = intent.getStringExtra(EXTRA_MESSAGE_REFERENCE);
544+
relatedMessageReference = MessageReference.parse(messageReferenceString);
545+
546+
final String accountUuid = (relatedMessageReference != null) ?
547+
relatedMessageReference.getAccountUuid() :
548+
intent.getStringExtra(EXTRA_ACCOUNT);
549+
550+
if (accountUuid != null) {
551+
account = preferences.getAccount(accountUuid);
552+
}
553+
}
554+
543555
@Override
544556
protected void onResume() {
545557
super.onResume();
546558
messagingController.addListener(messagingListener);
559+
560+
if (account == null) {
561+
fetchAccount(getIntent());
562+
}
563+
564+
if (account != null && account.getSentFolderId() == null) {
565+
final SentFolderNotFoundNotification notification = NotificationFactoryCoroutineCompat.create(
566+
continuation -> SentFolderNotFoundNotification(account.getUuid(), continuation)
567+
);
568+
notificationSenderCompat.send(notification, outcome -> {
569+
Log.v("notificationSender outcome = " + outcome);
570+
});
571+
}
547572
}
548573

549574
@Override
@@ -1748,8 +1773,9 @@ private void initializeInAppNotificationFragment() {
17481773
return;
17491774
}
17501775

1751-
if (account == null) {
1752-
Log.w("Can't initialize in-app notifications. Account is currently null");
1776+
final List<LegacyAccountDto> accounts = preferences.getAccounts();
1777+
if (accounts.isEmpty()) {
1778+
Log.w("Can't initialize in-app notifications. No accounts were found.");
17531779
return;
17541780
}
17551781
final FragmentManager fragmentManager = getSupportFragmentManager();
@@ -1760,13 +1786,17 @@ private void initializeInAppNotificationFragment() {
17601786
return;
17611787
}
17621788

1789+
final ArrayList<String> uuids = new ArrayList<>();
1790+
for (LegacyAccountDto legacyAccountDto : accounts) {
1791+
uuids.add(legacyAccountDto.getUuid());
1792+
}
17631793
final MessageComposeInAppNotificationFragment inAppNotificationFragment =
1764-
MessageComposeInAppNotificationFragment.newInstance(account.getUuid());
1794+
MessageComposeInAppNotificationFragment.newInstance(uuids);
17651795
fragmentManager
1766-
.beginTransaction()
1767-
.add(R.id.message_compose_in_app_notifications_container, inAppNotificationFragment,
1768-
MessageComposeInAppNotificationFragment.FRAGMENT_TAG)
1769-
.commit();
1796+
.beginTransaction()
1797+
.add(R.id.message_compose_in_app_notifications_container, inAppNotificationFragment,
1798+
MessageComposeInAppNotificationFragment.FRAGMENT_TAG)
1799+
.commit();
17701800
}
17711801

17721802
// TODO We miss callbacks for this listener if they happens while we are paused!

legacy/ui/legacy/src/main/java/com/fsck/k9/activity/compose/MessageComposeInAppNotificationFragment.kt

Lines changed: 22 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -6,14 +6,13 @@ import android.view.View
66
import android.view.ViewGroup
77
import androidx.compose.ui.platform.ComposeView
88
import androidx.compose.ui.platform.ViewCompositionStrategy
9-
import androidx.core.os.bundleOf
109
import androidx.fragment.app.Fragment
10+
import com.fsck.k9.ui.settings.account.AccountSettingsActivity
11+
import com.fsck.k9.ui.settings.account.AccountSettingsFragment
1112
import com.google.android.material.snackbar.Snackbar
1213
import kotlinx.collections.immutable.persistentSetOf
1314
import net.thunderbird.core.logging.Logger
1415
import net.thunderbird.core.ui.theme.api.FeatureThemeProvider
15-
import net.thunderbird.feature.account.AccountId
16-
import net.thunderbird.feature.account.AccountIdFactory
1716
import net.thunderbird.feature.notification.api.ui.InAppNotificationHost
1817
import net.thunderbird.feature.notification.api.ui.action.NotificationAction
1918
import net.thunderbird.feature.notification.api.ui.host.DisplayInAppNotificationFlag
@@ -27,13 +26,13 @@ class MessageComposeInAppNotificationFragment : Fragment() {
2726
private val themeProvider: FeatureThemeProvider by inject()
2827
private val logger: Logger by inject()
2928
private var parentView: View? = null
30-
private var accountId: AccountId? = null
29+
private var accountIds: Set<String> = emptySet()
3130

3231
override fun onCreate(savedInstanceState: Bundle?) {
3332
super.onCreate(savedInstanceState)
3433
arguments?.let { arg ->
35-
accountId = requireNotNull(arg.getString(ARG_ACCOUNT_ID)?.let { AccountIdFactory.of(it) }) {
36-
"Argument $ARG_ACCOUNT_ID is required"
34+
accountIds = requireNotNull(arg.getStringArray(ARG_ACCOUNT_IDS)?.toSet()) {
35+
"Missing argument $ARG_ACCOUNT_IDS"
3736
}
3837
}
3938
}
@@ -53,7 +52,7 @@ class MessageComposeInAppNotificationFragment : Fragment() {
5352
onSnackbarNotificationEvent = ::onSnackbarInAppNotificationEvent,
5453
eventFilter = { event ->
5554
val accountUuid = event.notification.accountUuid
56-
accountUuid != null && accountUuid == accountId?.asRaw()
55+
accountUuid != null && accountUuid in accountIds
5756
},
5857
)
5958
}
@@ -88,19 +87,28 @@ class MessageComposeInAppNotificationFragment : Fragment() {
8887

8988
private fun onNotificationActionClick(action: NotificationAction) {
9089
logger.verbose(TAG) { "onNotificationActionClick() called with: action = $action" }
90+
when (action) {
91+
is NotificationAction.AssignSentFolder ->
92+
AccountSettingsActivity.start(
93+
context = requireContext(),
94+
accountUuid = action.accountUuid,
95+
startScreenKey = AccountSettingsFragment.PREFERENCE_FOLDERS,
96+
)
97+
98+
else -> Unit
99+
}
91100
}
92101

93102
companion object {
94-
private const val ARG_ACCOUNT_ID = "MessageComposeInAppNotificationFragment_account_id"
103+
private const val ARG_ACCOUNT_IDS = "MessageComposeInAppNotificationFragment_account_ids"
95104
const val FRAGMENT_TAG = "MessageComposeInAppNotificationFragment"
96105

97-
fun newInstance(accountId: AccountId): MessageComposeInAppNotificationFragment =
106+
@JvmStatic
107+
fun newInstance(accountUuids: List<String>): MessageComposeInAppNotificationFragment =
98108
MessageComposeInAppNotificationFragment().apply {
99-
arguments = bundleOf(ARG_ACCOUNT_ID to accountId.asRaw())
109+
arguments = Bundle().apply {
110+
putStringArray(ARG_ACCOUNT_IDS, accountUuids.toTypedArray())
111+
}
100112
}
101-
102-
@JvmStatic
103-
fun newInstance(accountUuid: String): MessageComposeInAppNotificationFragment =
104-
newInstance(AccountIdFactory.of(accountUuid))
105113
}
106114
}

legacy/ui/legacy/src/main/java/com/fsck/k9/ui/messagelist/MessageListFragment.kt

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -95,6 +95,7 @@ import net.thunderbird.core.ui.theme.api.FeatureThemeProvider
9595
import net.thunderbird.feature.mail.folder.api.OutboxFolderManager
9696
import net.thunderbird.feature.mail.message.list.domain.DomainContract
9797
import net.thunderbird.feature.mail.message.list.ui.dialog.SetupArchiveFolderDialogFragmentFactory
98+
import net.thunderbird.feature.notification.api.content.SentFolderNotFoundNotification
9899
import net.thunderbird.feature.notification.api.ui.InAppNotificationHost
99100
import net.thunderbird.feature.notification.api.ui.host.DisplayInAppNotificationFlag
100101
import net.thunderbird.feature.notification.api.ui.host.visual.SnackbarVisual
@@ -509,8 +510,11 @@ class MessageListFragment :
509510
),
510511
onSnackbarNotificationEvent = ::onSnackbarInAppNotificationEvent,
511512
eventFilter = { event ->
512-
val accountUuid = event.notification.accountUuid
513-
accountUuid != null && accountUuid in accountUuids
513+
val notification = event.notification
514+
val accountUuid = notification.accountUuid
515+
notification !is SentFolderNotFoundNotification &&
516+
accountUuid != null &&
517+
accountUuid in accountUuids
514518
},
515519
modifier = Modifier
516520
.animateContentSize()

legacy/ui/legacy/src/main/java/com/fsck/k9/ui/settings/account/AccountSettingsActivity.kt

Lines changed: 4 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -126,20 +126,18 @@ class AccountSettingsActivity : K9Activity(), OnPreferenceStartScreenCallback {
126126
private const val ARG_START_SCREEN_KEY = "startScreen"
127127

128128
@JvmStatic
129-
fun start(context: Context, accountUuid: String) {
129+
@JvmOverloads
130+
fun start(context: Context, accountUuid: String, startScreenKey: String? = null) {
130131
val intent = Intent(context, AccountSettingsActivity::class.java).apply {
131132
putExtra(ARG_ACCOUNT_UUID, accountUuid)
133+
startScreenKey?.let { putExtra(ARG_START_SCREEN_KEY, it) }
132134
}
133135
context.startActivity(intent)
134136
}
135137

136138
@JvmStatic
137139
fun startCryptoSettings(context: Context, accountUuid: String) {
138-
val intent = Intent(context, AccountSettingsActivity::class.java).apply {
139-
putExtra(ARG_ACCOUNT_UUID, accountUuid)
140-
putExtra(ARG_START_SCREEN_KEY, AccountSettingsFragment.PREFERENCE_OPENPGP)
141-
}
142-
context.startActivity(intent)
140+
start(context, accountUuid, AccountSettingsFragment.PREFERENCE_OPENPGP)
143141
}
144142
}
145143
}

legacy/ui/legacy/src/main/java/com/fsck/k9/ui/settings/account/AccountSettingsFragment.kt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -490,7 +490,7 @@ class AccountSettingsFragment : PreferenceFragmentCompat(), ConfirmationDialogFr
490490
private const val PREFERENCE_OPENPGP_ENABLE = "openpgp_provider"
491491
private const val PREFERENCE_OPENPGP_KEY = "openpgp_key"
492492
private const val PREFERENCE_AUTOCRYPT_TRANSFER = "autocrypt_transfer"
493-
private const val PREFERENCE_FOLDERS = "folders"
493+
internal const val PREFERENCE_FOLDERS = "folders"
494494
private const val PREFERENCE_AUTO_EXPAND_FOLDER = "account_setup_auto_expand_folder"
495495
private const val PREFERENCE_SUBSCRIBED_FOLDERS_ONLY = "subscribed_folders_only"
496496
private const val PREFERENCE_ARCHIVE_FOLDER = "archive_folder"

0 commit comments

Comments
 (0)