mirror of
https://github.com/the-djmaze/snappymail.git
synced 2026-09-06 07:57:02 +03:00
Add Search Filters Plugin with Gmail-like Functionality
Introducing a new plugin for enhanced email organization: Search Filters, inspired by similar features in Gmail (Search Filters) and Outlook (Rules). The plugin allows you to define custom search queries that automatically perform one or more actions on matching emails based on their priority level (1-10). Available actions include marking as seen, flagging/starring, and moving to a designated folder. This plugin is designed to work seamlessly with both old and new emails in your inbox, taking into account the specified search query criteria. However, please be aware of an outstanding bug that affects the display of unread email counts beside folders; this issue has yet to be resolved. I have developed this plugin as a freelance project for a client on their custom server setup. Unfortunately, I never received any feedback or response from my client after completion of the work. Nonetheless, I hope that sharing it here will benefit others and contribute to the ongoing advancement of this open-source project. Please note: This plugin is offered as-is with no warranties or guarantees. Make sure to thoroughly test and verify its functionality before using it in a production environment. Thank you to everyone who has contributed to making this project a reality.
This commit is contained in:
parent
e4316e6665
commit
4a56d2d087
6 changed files with 724 additions and 0 deletions
|
|
@ -0,0 +1,82 @@
|
|||
<header>
|
||||
<a href="#" class="close" data-bind="click: close">×</a>
|
||||
<h3 data-i18n="SEARCH/TITLE_ADV"></h3>
|
||||
</header>
|
||||
<form id="advsearchform" class="modal-body form-horizontal" action="#/" autocomplete="off" spellcheck="false"
|
||||
data-bind="submit: submitForm">
|
||||
<div>
|
||||
<div class="control-group">
|
||||
<label data-i18n="GLOBAL/FROM"></label>
|
||||
<input type="text" autofocus="" autocomplete="off" autocorrect="off" autocapitalize="off"
|
||||
data-bind="value: from">
|
||||
</div>
|
||||
<div class="control-group">
|
||||
<label data-i18n="GLOBAL/TO"></label>
|
||||
<input type="text" autocomplete="off" autocorrect="off" autocapitalize="off" data-bind="value: to">
|
||||
</div>
|
||||
<div class="control-group">
|
||||
<label data-i18n="GLOBAL/SUBJECT"></label>
|
||||
<input type="text" autocomplete="off" autocorrect="off" autocapitalize="off" data-bind="value: subject">
|
||||
</div>
|
||||
<div class="control-group">
|
||||
<label data-i18n="SEARCH/TEXT"></label>
|
||||
<input type="text" autocomplete="off" autocorrect="off" autocapitalize="off" data-bind="value: text">
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<div class="control-group">
|
||||
<label data-i18n="SEARCH/DATE"></label>
|
||||
<div data-bind="component: {
|
||||
name: 'Select',
|
||||
params: {
|
||||
options: selectedDates,
|
||||
value: selectedDateValue,
|
||||
optionsText: 'name',
|
||||
optionsValue: 'id'
|
||||
}
|
||||
}"></div>
|
||||
</div>
|
||||
<div class="control-group">
|
||||
<label data-i18n="SEARCH/REPLIED"></label>
|
||||
<div data-bind="component: {
|
||||
name: 'Select',
|
||||
params: {
|
||||
options: repliedOptions,
|
||||
value: repliedValue,
|
||||
optionsText: 'name',
|
||||
optionsValue: 'id'
|
||||
}
|
||||
}"></div>
|
||||
</div>
|
||||
<div class="control-group">
|
||||
<label></label>
|
||||
<div>
|
||||
<div data-bind="component: {
|
||||
name: 'Checkbox',
|
||||
params: {
|
||||
label: 'SEARCH/UNSEEN',
|
||||
value: unseen
|
||||
}
|
||||
}"></div>
|
||||
<div data-bind="component: {
|
||||
name: 'Checkbox',
|
||||
params: {
|
||||
label: 'SEARCH/FLAGGED',
|
||||
value: starred
|
||||
}
|
||||
}"></div>
|
||||
<div data-bind="component: {
|
||||
name: 'Checkbox',
|
||||
params: {
|
||||
label: 'SEARCH/HAS_ATTACHMENT',
|
||||
value: hasAttachment
|
||||
}
|
||||
}"></div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</form>
|
||||
<footer style="display: flex; justify-content: space-between;">
|
||||
<button class="btn" data-i18n="SFILTERS/EDIT_FILTERS" data-bind="click: editFilters"></button>
|
||||
<button form="advsearchform" class="btn" data-icon="✔" data-i18n="SFILTERS/SAVE"></button>
|
||||
</footer>
|
||||
54
plugins/search-filters/templates/PopupsSearchFilters.html
Normal file
54
plugins/search-filters/templates/PopupsSearchFilters.html
Normal file
|
|
@ -0,0 +1,54 @@
|
|||
<header>
|
||||
<a href="#" class="close" data-bind="click: close">×</a>
|
||||
<h3 data-i18n="SFILTERS/WHEN_MESSAGE_MATCH_SEARCH_CRITERIA"></h3>
|
||||
</header>
|
||||
<form id="search-filters-form" class="modal-body form-horizontal" action="#/" autocomplete="off" spellcheck="false"
|
||||
data-bind="submit: submitForm">
|
||||
<div>
|
||||
<div class="control-group">
|
||||
<div data-bind="component: {
|
||||
name: 'Checkbox',
|
||||
params: {
|
||||
label: 'SFILTERS/MOVE_TO_FOLDER',
|
||||
value: usefFolder
|
||||
}
|
||||
}"></div>
|
||||
<select data-bind="
|
||||
options: folders,
|
||||
value: fFolder,
|
||||
optionsText: 'name',
|
||||
optionsValue: 'name',
|
||||
enable: usefFolder
|
||||
"></select>
|
||||
</div>
|
||||
<div class="control-group">
|
||||
<div data-bind="component: {
|
||||
name: 'Checkbox',
|
||||
params: {
|
||||
label: 'SFILTERS/MARK_AS_READ',
|
||||
value: fSeen
|
||||
}
|
||||
}"></div>
|
||||
</div>
|
||||
<div class="control-group">
|
||||
<div data-bind="component: {
|
||||
name: 'Checkbox',
|
||||
params: {
|
||||
label: 'SFILTERS/STAR_IT',
|
||||
value: fFlag
|
||||
}
|
||||
}"></div>
|
||||
</div>
|
||||
<div class="control-group">
|
||||
<label for="priority" data-i18n="SFILTERS/PRIORITY_LABLE"></label>
|
||||
<select data-bind="
|
||||
options: Priorities,
|
||||
value: priority,
|
||||
"></select>
|
||||
</div>
|
||||
</div>
|
||||
</form>
|
||||
<footer>
|
||||
<button form="search-filters-form" class="btn buttonSearchFilters" data-icon="✔"
|
||||
data-i18n="SFILTERS/CREATE_FILTER"></button>
|
||||
</footer>
|
||||
39
plugins/search-filters/templates/STabSearchFilters.html
Normal file
39
plugins/search-filters/templates/STabSearchFilters.html
Normal file
|
|
@ -0,0 +1,39 @@
|
|||
<div>
|
||||
<div class="form-horizontal">
|
||||
<div class="legend">
|
||||
<span data-i18n="SFILTERS/THE_FOLLOWING_FILTERS_ARE_APPLIED"></span>
|
||||
|
||||
<i class="icon-spinner animated" style="margin-top: 5px" data-bind="visible: loading"></i>
|
||||
</div>
|
||||
|
||||
<div data-bind="visible: ioFilters().length == 0">
|
||||
<span data-i18n="SFILTERS/NO_FILTERS"> </span>
|
||||
</div>
|
||||
|
||||
<!-- ko foreach: ioFilters -->
|
||||
<label class="control-label">
|
||||
<span data-bind="text: $root.i18n('MATCHES')"> </span>
|
||||
<span data-bind="text: searchQ"></span>
|
||||
|
||||
<span data-bind="text: $root.i18n('PRIORITY_POINTS')"></span>
|
||||
:
|
||||
|
||||
<span data-bind="text: priority"></span>
|
||||
<br>
|
||||
<span data-bind="text: $root.i18n('DO_THIS')"></span>
|
||||
<span data-bind="visible: fFolder, text: $root.i18n('MOVE_TO_FOLDER')"></span>
|
||||
<span data-bind="visible: fFolder, text: fFolder"></span>
|
||||
|
||||
<span data-bind="visible: fSeen, text: $root.i18n('MARK_AS_READ')"></span>
|
||||
|
||||
<span data-bind="visible: fFlag, text: $root.i18n('STAR_IT')"></span>
|
||||
</label>
|
||||
<div class="controls">
|
||||
<button class="btn" data-bind="click: $root.edit, text: $root.i18n('EDIT')"></button>
|
||||
<button class="btn" data-bind="click: $root.remove, text: $root.i18n('REMOVE')"></button>
|
||||
</div>
|
||||
<br>
|
||||
<!-- /ko -->
|
||||
|
||||
</div>
|
||||
</div>
|
||||
Loading…
Add table
Add a link
Reference in a new issue