diff --git a/FAQ.md b/FAQ.md index 5a6a5a1eec..8384a746b8 100644 --- a/FAQ.md +++ b/FAQ.md @@ -3415,22 +3415,25 @@ Message classification will attempt to automatically group emails into classes, using [Bayesian statistics](https://en.wikipedia.org/wiki/Bayesian_statistics). In the context of FairEmail, a folder is a class. -You can enable 'learning' mode in the miscellaneous settings. +You can enable message classification in the miscellaneous settings. +This will enable learning mode only. -Each folder has an option to enable auto classification. +Each folder has an option to enable automatic message classification. When this is turned on, new messages in other folders which the classifier thinks belong to that folder will be automatically moved. Classification should be considered as a best guess - it might be a wrong guess, or the classifier might not be confident enough to make any guess. If the classifier is unsure, it will simply leave an email where it is. Classification will be done for new messages in the inbox, spam folder and user folders only. -You can clear local messages (long press a folder in the folder list) and synchronize the messages again to classify existing messages. +You can clear local messages (long press a folder in the folder list of an account) and synchronize the messages again to classify existing messages. Moving a message on the device will reclassify the message. -Moving a message from another email client will not result in reclassification because IMAP does not support MOVED notifications. +Moving a message from another email client will not result in reclassification because IMAP does not support 'moved' notifications. Classification is optimized to use as little resources as possible, but will inevitably use some extra battery power. +Automatic message classification is a pro feature, except for the spam folder. +
## Get support diff --git a/PLAYSTORE.txt b/PLAYSTORE.txt index ae8f1a8eb3..ffb4d455f8 100644 --- a/PLAYSTORE.txt +++ b/PLAYSTORE.txt @@ -79,6 +79,7 @@ All pro features are convenience or advanced features. * Accept/decline calendar invitations * Add message to calendar * Filter rules +* Automatic message classification * Search indexing, search on server * Keyword management * S/MIME sign/encrypt diff --git a/README.md b/README.md index 87856940f2..cd10761eba 100644 --- a/README.md +++ b/README.md @@ -96,6 +96,7 @@ All pro features are convenience or advanced features. * Accept/decline calendar invitations * Add message to calendar * Filter rules ([instructions](https://github.com/M66B/FairEmail/blob/master/FAQ.md#user-content-faq71)) +* Automatic message classification ([instructions](https://github.com/M66B/FairEmail/blob/master/FAQ.md#user-content-faq163)) * Search indexing, search on server ([instructions](https://github.com/M66B/FairEmail/blob/master/FAQ.md#user-content-faq13)) * Keyword management * S/MIME sign/encrypt ([instructions](https://github.com/M66B/FairEmail/blob/master/FAQ.md#user-content-faq12)) diff --git a/app/src/main/java/eu/faircode/email/FragmentFolder.java b/app/src/main/java/eu/faircode/email/FragmentFolder.java index 581628978e..7b918c2cd6 100644 --- a/app/src/main/java/eu/faircode/email/FragmentFolder.java +++ b/app/src/main/java/eu/faircode/email/FragmentFolder.java @@ -70,6 +70,7 @@ public class FragmentFolder extends FragmentBase { private TextView tvPoll; private CheckBox cbDownload; private CheckBox cbAutoClassify; + private TextView tvAutoClassifyPro; private Button btnInfo; private EditText etSyncDays; private EditText etKeepDays; @@ -131,6 +132,7 @@ public class FragmentFolder extends FragmentBase { tvPoll = view.findViewById(R.id.tvPoll); cbDownload = view.findViewById(R.id.cbDownload); cbAutoClassify = view.findViewById(R.id.cbAutoClassify); + tvAutoClassifyPro = view.findViewById(R.id.tvAutoClassifyPro); btnInfo = view.findViewById(R.id.btnInfo); etSyncDays = view.findViewById(R.id.etSyncDays); etKeepDays = view.findViewById(R.id.etKeepDays); @@ -177,6 +179,8 @@ public class FragmentFolder extends FragmentBase { } }); + Helper.linkPro(tvAutoClassifyPro); + btnInfo.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { @@ -218,6 +222,7 @@ public class FragmentFolder extends FragmentBase { tvParent.setText(parent); grpParent.setVisibility(parent == null ? View.GONE : View.VISIBLE); cbAutoClassify.setVisibility(View.GONE); + tvAutoClassifyPro.setVisibility(View.GONE); grpAutoDelete.setVisibility(View.GONE); btnSave.setEnabled(false); pbSave.setVisibility(View.GONE); @@ -300,15 +305,19 @@ public class FragmentFolder extends FragmentBase { Helper.setViewsEnabled(view, true); boolean always = (!ondemand && (pollInterval == 0 || exempted)); + boolean canAutoClassify = (imap && + MessageClassifier.isEnabled(getContext()) && + (folder == null || MessageClassifier.canClassify(folder.type))); + boolean isJunk = (folder != null && EntityFolder.JUNK.equals(folder.type)); etName.setEnabled(folder == null || EntityFolder.USER.equals(folder.type)); cbPoll.setEnabled(cbSynchronize.isChecked() && always); etPoll.setEnabled(cbSynchronize.isChecked() && always); tvPoll.setEnabled(cbSynchronize.isChecked() && always); grpPoll.setVisibility(imap && cbPoll.isEnabled() && cbPoll.isChecked() ? View.VISIBLE : View.GONE); - cbAutoClassify.setVisibility(MessageClassifier.isEnabled(getContext()) && - (folder == null || MessageClassifier.canClassify(folder.type)) - ? View.VISIBLE : View.GONE); + cbAutoClassify.setEnabled(canAutoClassify && (isJunk || ActivityBilling.isPro(getContext()))); + cbAutoClassify.setVisibility(canAutoClassify ? View.VISIBLE : View.GONE); + tvAutoClassifyPro.setVisibility(canAutoClassify && !cbAutoClassify.isEnabled() ? View.VISIBLE : View.GONE); etKeepDays.setEnabled(!cbKeepAll.isChecked()); cbAutoDelete.setEnabled(!cbKeepAll.isChecked()); cbAutoDelete.setText(folder != null && EntityFolder.TRASH.equals(folder.type) diff --git a/app/src/main/java/eu/faircode/email/MessageClassifier.java b/app/src/main/java/eu/faircode/email/MessageClassifier.java index 96d1d85c7d..9bcb0ee9ab 100644 --- a/app/src/main/java/eu/faircode/email/MessageClassifier.java +++ b/app/src/main/java/eu/faircode/email/MessageClassifier.java @@ -110,7 +110,8 @@ public class MessageClassifier { if (classified != null) { EntityFolder f = db.folder().getFolderByName(account.id, classified); - if (f != null && !f.id.equals(folder.id) && f.auto_classify) + if (f != null && !f.id.equals(folder.id) && f.auto_classify && + (EntityFolder.JUNK.equals(f.type) || ActivityBilling.isPro(context))) try { db.beginTransaction(); diff --git a/app/src/main/res/layout/fragment_folder.xml b/app/src/main/res/layout/fragment_folder.xml index e9eeb7861f..929140c07d 100644 --- a/app/src/main/res/layout/fragment_folder.xml +++ b/app/src/main/res/layout/fragment_folder.xml @@ -206,6 +206,16 @@ app:layout_constraintStart_toStartOf="parent" app:layout_constraintTop_toBottomOf="@id/cbDownload" /> + + + app:layout_constraintTop_toBottomOf="@id/tvAutoClassifyPro" /> diff --git a/metadata/en-US/full_description.txt b/metadata/en-US/full_description.txt index 29c091e7ea..4dc718acd1 100644 --- a/metadata/en-US/full_description.txt +++ b/metadata/en-US/full_description.txt @@ -79,6 +79,7 @@ All pro features are convenience or advanced features. * Accept/decline calendar invitations * Add message to calendar * Filter rules +* Automatic message classification * Search indexing, search on server * Keyword management * S/MIME sign/encrypt