aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--mail/ChangeLog15
-rw-r--r--mail/em-filter-folder-element.c34
-rw-r--r--mail/em-filter-folder-element.h1
-rw-r--r--mail/em-format-html-display.c2
-rw-r--r--mail/em-vfolder-context.c9
-rw-r--r--mail/searchtypes.xml317
-rw-r--r--mail/vfoldertypes.xml253
7 files changed, 624 insertions, 7 deletions
diff --git a/mail/ChangeLog b/mail/ChangeLog
index fe9ebb2b84..d339229443 100644
--- a/mail/ChangeLog
+++ b/mail/ChangeLog
@@ -1,3 +1,18 @@
+2009-01-08 Milan Crha <mcrha@redhat.com>
+
+ ** Fix for bug #565376
+
+ * vfoldertypes.xml:
+ * searchtypes.xml: Merge some search types together.
+ * em-vfolder-context.c: (vfolder_new_element): More elements.
+ * em-filter-folder-element.h: (struct _EMFilterFolderElement):
+ * em-filter-folder-element.c: (xml_encode), (xml_decode),
+ (folder_selected), (get_widget), (format_sexp):
+ Support storing folder uri in a camel's way.
+
+ * em-format-html-display.c: (efhd_use_component):
+ Compiler warning fix.
+
2008-12-29 Matthew Barnes <mbarnes@redhat.com>
** Fixes bug #565857
diff --git a/mail/em-filter-folder-element.c b/mail/em-filter-folder-element.c
index 3539881290..a95a4dd88d 100644
--- a/mail/em-filter-folder-element.c
+++ b/mail/em-filter-folder-element.c
@@ -180,7 +180,10 @@ xml_encode(FilterElement *fe)
value = xmlNewNode(NULL, (unsigned const char *)"value");
xmlSetProp(value, (unsigned const char *)"name", (unsigned char *)fe->name);
- xmlSetProp(value, (unsigned const char *)"type", (unsigned const char *)"folder");
+ if (ff->store_camel_uri)
+ xmlSetProp(value, (unsigned const char *)"type", (unsigned const char *)"folder-curi");
+ else
+ xmlSetProp(value, (unsigned const char *)"type", (unsigned const char *)"folder");
work = xmlNewChild(value, NULL, (unsigned const char *)"folder", NULL);
xmlSetProp(work, (unsigned const char *)"uri", (unsigned const char *)ff->uri);
@@ -193,12 +196,21 @@ xml_decode(FilterElement *fe, xmlNodePtr node)
{
EMFilterFolderElement *ff = (EMFilterFolderElement *)fe;
xmlNodePtr n;
+ xmlChar *type;
d(printf("Decoding folder from xml %p\n", fe));
xmlFree(fe->name);
fe->name = (char *)xmlGetProp(node, (unsigned const char *)"name");
+ type = xmlGetProp (node, (unsigned const char *)"type");
+ if (type) {
+ ff->store_camel_uri = g_str_equal ((const char *)type, "folder-curi");
+ xmlFree (type);
+ } else {
+ ff->store_camel_uri = FALSE;
+ }
+
n = node->children;
while(n) {
if (!strcmp((char *)n->name, "folder")) {
@@ -223,7 +235,11 @@ folder_selected(EMFolderSelectionButton *button, EMFilterFolderElement *ff)
uri = em_folder_selection_button_get_selection(button);
g_free(ff->uri);
- ff->uri = uri!=NULL?em_uri_from_camel(uri):NULL;
+
+ if (ff->store_camel_uri)
+ ff->uri = g_strdup (uri);
+ else
+ ff->uri = uri != NULL ? em_uri_from_camel (uri) : NULL;
gdk_window_raise(GTK_WIDGET(gtk_widget_get_ancestor(GTK_WIDGET(button), GTK_TYPE_WINDOW))->window);
}
@@ -235,10 +251,15 @@ get_widget(FilterElement *fe)
GtkWidget *button;
char *uri;
- uri = em_uri_to_camel(ff->uri);
+ if (ff->store_camel_uri)
+ uri = ff->uri;
+ else
+ uri = em_uri_to_camel (ff->uri);
button = em_folder_selection_button_new(_("Select Folder"), NULL);
em_folder_selection_button_set_selection(EM_FOLDER_SELECTION_BUTTON(button), uri);
- g_free(uri);
+
+ if (!ff->store_camel_uri)
+ g_free(uri);
gtk_widget_show(button);
g_signal_connect(button, "selected", G_CALLBACK(folder_selected), ff);
@@ -263,8 +284,9 @@ format_sexp(FilterElement *fe, GString *out)
static void
emff_copy_value(FilterElement *de, FilterElement *se)
{
- if (EM_IS_FILTER_FOLDER_ELEMENT(se))
+ if (EM_IS_FILTER_FOLDER_ELEMENT(se)) {
+ ((EMFilterFolderElement *)de)->store_camel_uri = ((EMFilterFolderElement *)se)->store_camel_uri;
em_filter_folder_element_set_value((EMFilterFolderElement *)de, ((EMFilterFolderElement *)se)->uri);
- else
+ } else
parent_class->copy_value(de, se);
}
diff --git a/mail/em-filter-folder-element.h b/mail/em-filter-folder-element.h
index 27c6ea81d4..8f9a2d8b4e 100644
--- a/mail/em-filter-folder-element.h
+++ b/mail/em-filter-folder-element.h
@@ -40,6 +40,7 @@ struct _EMFilterFolderElement {
FilterElement parent_object;
char *uri;
+ gboolean store_camel_uri; /* true if uri should contain camel uri, otherwise contains evolution's uri with an Account ID */
};
struct _EMFilterFolderElementClass {
diff --git a/mail/em-format-html-display.c b/mail/em-format-html-display.c
index 0a7856f39e..7793b2da39 100644
--- a/mail/em-format-html-display.c
+++ b/mail/em-format-html-display.c
@@ -2129,7 +2129,7 @@ type_ok:
}
/* FIXME: How should I free the Bonobo_ServerInfo's ? */
- g_list_foreach (components, CORBA_free, NULL);
+ g_list_foreach (components, (GFunc)CORBA_free, NULL);
g_list_free (components);
return component != NULL;
diff --git a/mail/em-vfolder-context.c b/mail/em-vfolder-context.c
index eebf12e960..88c97b0a0f 100644
--- a/mail/em-vfolder-context.c
+++ b/mail/em-vfolder-context.c
@@ -33,6 +33,8 @@
#include "filter/filter-option.h"
#include "filter/filter-int.h"
+#include "em-filter-folder-element.h"
+
static FilterElement *vfolder_new_element(RuleContext *rc, const char *type);
static RuleContextClass *parent_class = NULL;
@@ -108,6 +110,13 @@ vfolder_new_element(RuleContext *rc, const char *type)
return (FilterElement *) filter_option_new();
} else if (!strcmp(type, "score")) {
return (FilterElement *) filter_int_new_type("score", -3, 3);
+ } else if (!strcmp(type, "folder-curi")) {
+ EMFilterFolderElement *ff = em_filter_folder_element_new ();
+ if (ff)
+ ff->store_camel_uri = TRUE;
+ return (FilterElement *) ff;
+ } else if (!strcmp(type, "folder")) {
+ return (FilterElement *) em_filter_folder_element_new();
} else {
return parent_class->new_element(rc, type);
}
diff --git a/mail/searchtypes.xml b/mail/searchtypes.xml
index ded2e2eabd..83941d875c 100644
--- a/mail/searchtypes.xml
+++ b/mail/searchtypes.xml
@@ -115,6 +115,223 @@
<input type="address" name="recipient"/>
</part>
+ <part name="cc">
+ <title>CC</title>
+ <input type="optionlist" name="recipient-type">
+ <option value="contains">
+ <title>contains</title>
+ <code>
+ (match-all (header-contains "Cc" ${recipient}))
+ </code>
+ </option>
+ <option value="not contains">
+ <title>does not contain</title>
+ <code>
+ (match-all (not (header-contains "Cc" ${recipient})))
+ </code>
+ </option>
+ <option value="is">
+ <title>is</title>
+ <code>
+ (match-all (header-matches "Cc" ${recipient}))
+ </code>
+ </option>
+ <option value="is not">
+ <title>is not</title>
+ <code>
+ (match-all (not (header-matches "Cc" ${recipient})))
+ </code>
+ </option>
+ <option value="starts with">
+ <title>starts with</title>
+ <code>
+ (match-all (header-starts-with "Cc" ${recipient}))
+ </code>
+ </option>
+ <option value="not starts with">
+ <title>does not start with</title>
+ <code>
+ (match-all (not (header-starts-with "Cc" ${recipient})))
+ </code>
+ </option>
+ <option value="ends with">
+ <title>ends with</title>
+ <code>
+ (match-all (header-ends-with "Cc" ${recipient}))
+ </code>
+ </option>
+ <option value="not ends with">
+ <title>does not end with</title>
+ <code>
+ (match-all (not (header-ends-with "Cc" ${recipient})))
+ </code>
+ </option>
+ <option value="matches soundex">
+ <title>sounds like</title>
+ <code>
+ (match-all (header-soundex "Cc" ${recipient}))
+ </code>
+ </option>
+ <option value="not match soundex">
+ <title>does not sound like</title>
+ <code>
+ (match-all (not (header-soundex "Cc" ${recipient})))
+ </code>
+ </option>
+ </input>
+ <input type="address" name="recipient"/>
+ </part>
+
+ <part name="bcc">
+ <title>BCC</title>
+ <input type="optionlist" name="recipient-type">
+ <option value="contains">
+ <title>contains</title>
+ <code>
+ (match-all (header-contains "Bcc" ${recipient}))
+ </code>
+ </option>
+ <option value="not contains">
+ <title>does not contain</title>
+ <code>
+ (match-all (not (header-contains "Bcc" ${recipient})))
+ </code>
+ </option>
+ <option value="is">
+ <title>is</title>
+ <code>
+ (match-all (header-matches "Bcc" ${recipient}))
+ </code>
+ </option>
+ <option value="is not">
+ <title>is not</title>
+ <code>
+ (match-all (not (header-matches "Bcc" ${recipient})))
+ </code>
+ </option>
+ <option value="starts with">
+ <title>starts with</title>
+ <code>
+ (match-all (header-starts-with "Bcc" ${recipient}))
+ </code>
+ </option>
+ <option value="not starts with">
+ <title>does not start with</title>
+ <code>
+ (match-all (not (header-starts-with "Bcc" ${recipient})))
+ </code>
+ </option>
+ <option value="ends with">
+ <title>ends with</title>
+ <code>
+ (match-all (header-ends-with "Bcc" ${recipient}))
+ </code>
+ </option>
+ <option value="not ends with">
+ <title>does not end with</title>
+ <code>
+ (match-all (not (header-ends-with "Bcc" ${recipient})))
+ </code>
+ </option>
+ <option value="matches soundex">
+ <title>sounds like</title>
+ <code>
+ (match-all (header-soundex "Bcc" ${recipient}))
+ </code>
+ </option>
+ <option value="not match soundex">
+ <title>does not sound like</title>
+ <code>
+ (match-all (not (header-soundex "Bcc" ${recipient})))
+ </code>
+ </option>
+ </input>
+ <input type="address" name="recipient"/>
+ </part>
+
+ <part name="senderto">
+ <title>Sender or Recipients</title>
+ <input type="optionlist" name="recipient-type">
+ <option value="contains">
+ <title>contains</title>
+ <code>
+ (match-all (or (header-contains "From" ${recipient})
+ (header-contains "To" ${recipient})
+ (header-contains "Cc" ${recipient})
+ (header-contains "Bcc" ${recipient})))
+ </code>
+ </option>
+ <option value="not contains">
+ <title>does not contain</title>
+ <code>
+ (match-all (not (or
+ (header-contains "From" ${recipient})
+ (header-contains "To" ${recipient})
+ (header-contains "Cc" ${recipient})
+ (header-contains "Bcc" ${recipient}))))
+ </code>
+ </option>
+ <option value="is">
+ <title>is</title>
+ <code>
+ (match-all (or (header-matches "From" ${recipient})
+ (header-matches "To" ${recipient})
+ (header-matches "Cc" ${recipient})
+ (header-matches "Bcc" ${recipient})))
+ </code>
+ </option>
+ <option value="is not">
+ <title>is not</title>
+ <code>
+ (match-all (not (or
+ (header-matches "From" ${recipient})
+ (header-matches "To" ${recipient})
+ (header-matches "Cc" ${recipient})
+ (header-matches "Bcc" ${recipient}))))
+ </code>
+ </option>
+ <option value="starts with">
+ <title>starts with</title>
+ <code>
+ (match-all (or (header-starts-with "From" ${recipient})
+ (header-starts-with "To" ${recipient})
+ (header-starts-with "Cc" ${recipient})
+ (header-starts-with "Bcc" ${recipient})))
+ </code>
+ </option>
+ <option value="not starts with">
+ <title>does not start with</title>
+ <code>
+ (match-all (not (or
+ (header-starts-with "From" ${recipient})
+ (header-starts-with "To" ${recipient})
+ (header-starts-with "Cc" ${recipient})
+ (header-starts-with "Bcc" ${recipient}))))
+ </code>
+ </option>
+ <option value="ends with">
+ <title>ends with</title>
+ <code>
+ (match-all (or (header-ends-with "From" ${recipient})
+ (header-ends-with "To" ${recipient})
+ (header-ends-with "Cc" ${recipient})
+ (header-ends-with "Bcc" ${recipient})))
+ </code>
+ </option>
+ <option value="not ends with">
+ <title>does not end with</title>
+ <code>
+ (match-all (not (or
+ (header-ends-with "From" ${recipient})
+ (header-ends-with "To" ${recipient})
+ (header-ends-with "Cc" ${recipient})
+ (header-ends-with "Bcc" ${recipient}))))
+ </code>
+ </option>
+ </input>
+ <input type="address" name="recipient"/>
+ </part>
+
<part name="subject">
<title>Subject</title>
<input type="optionlist" name="subject-type">
@@ -169,6 +386,87 @@
</input>
<input type="string" name="subject"/>
</part>
+
+ <part name="header">
+ <title>Specific header</title>
+ <input type="string" name="header-field"/>
+ <input type="optionlist" name="header-type">
+ <option value="contains">
+ <title>contains</title>
+ <code>
+ (match-all (header-contains ${header-field} ${word}))
+ </code>
+ </option>
+ <option value="not contains">
+ <title>does not contain</title>
+ <code>
+ (match-all (not (header-contains ${header-field} ${word})))
+ </code>
+ </option>
+ <option value="is">
+ <title>is</title>
+ <code>
+ (match-all (header-matches ${header-field} ${word}))
+ </code>
+ </option>
+ <option value="is not">
+ <title>is not</title>
+ <code>
+ (match-all (not (header-matches ${header-field} ${word})))
+ </code>
+ </option>
+ <option value="starts with">
+ <title>starts with</title>
+ <code>
+ (match-all (header-starts-with ${header-field} ${word}))
+ </code>
+ </option>
+ <option value="not starts with">
+ <title>does not start with</title>
+ <code>
+ (match-all (not (header-starts-with ${header-field} ${word})))
+ </code>
+ </option>
+ <option value="ends with">
+ <title>ends with</title>
+ <code>
+ (match-all (header-ends-with ${header-field} ${word}))
+ </code>
+ </option>
+ <option value="not ends with">
+ <title>does not end with</title>
+ <code>
+ (match-all (not (header-ends-with ${header-field} ${word})))
+ </code>
+ </option>
+ <option value="exists">
+ <title>exists</title>
+ <code>
+ (match-all (header-exists ${header-field}))
+ </code>
+ </option>
+ <option value="not exists">
+ <title>does not exist</title>
+ <code>
+ (match-all (not (header-exists ${header-field})))
+ </code>
+ </option>
+ <option value="matches soundex">
+ <title>sounds like</title>
+ <code>
+ (match-all (header-soundex ${header-field} ${word}))
+ </code>
+ </option>
+ <option value="not match soundex">
+ <title>does not sound like</title>
+ <code>
+ (match-all (not (header-soundex ${header-field} ${word})))
+ </code>
+ </option>
+ </input>
+ <input type="string" name="word"/>
+ </part>
+
<part name="body">
<title>Message Body</title>
<input type="optionlist" name="body-type">
@@ -437,6 +735,25 @@
<input type="string" name="mlist"/>
</part>
+ <part name="regex">
+ <title>Regex Match</title>
+ <input type="optionlist" name="match-type">
+ <option value="header">
+ <title>Message Header</title>
+ <code>
+ (match-all (header-full-regex ${expression}))
+ </code>
+ </option>
+ <option value="body">
+ <title>Message Body</title>
+ <code>
+ (match-all (body-regex ${expression}))
+ </code>
+ </option>
+ </input>
+ <input type="regex" name="expression"/>
+ </part>
+
<part name="all">
<title>Match All</title>
<code>
diff --git a/mail/vfoldertypes.xml b/mail/vfoldertypes.xml
index b87af3280a..11ed7cc0af 100644
--- a/mail/vfoldertypes.xml
+++ b/mail/vfoldertypes.xml
@@ -115,6 +115,140 @@
<input type="address" name="recipient"/>
</part>
+ <part name="cc">
+ <title>CC</title>
+ <input type="optionlist" name="recipient-type">
+ <option value="contains">
+ <title>contains</title>
+ <code>
+ (match-all (header-contains "Cc" ${recipient}))
+ </code>
+ </option>
+ <option value="not contains">
+ <title>does not contain</title>
+ <code>
+ (match-all (not (header-contains "Cc" ${recipient})))
+ </code>
+ </option>
+ <option value="is">
+ <title>is</title>
+ <code>
+ (match-all (header-matches "Cc" ${recipient}))
+ </code>
+ </option>
+ <option value="is not">
+ <title>is not</title>
+ <code>
+ (match-all (not (header-matches "Cc" ${recipient})))
+ </code>
+ </option>
+ <option value="starts with">
+ <title>starts with</title>
+ <code>
+ (match-all (header-starts-with "Cc" ${recipient}))
+ </code>
+ </option>
+ <option value="not starts with">
+ <title>does not start with</title>
+ <code>
+ (match-all (not (header-starts-with "Cc" ${recipient})))
+ </code>
+ </option>
+ <option value="ends with">
+ <title>ends with</title>
+ <code>
+ (match-all (header-ends-with "Cc" ${recipient}))
+ </code>
+ </option>
+ <option value="not ends with">
+ <title>does not end with</title>
+ <code>
+ (match-all (not (header-ends-with "Cc" ${recipient})))
+ </code>
+ </option>
+ <option value="matches soundex">
+ <title>sounds like</title>
+ <code>
+ (match-all (header-soundex "Cc" ${recipient}))
+ </code>
+ </option>
+ <option value="not match soundex">
+ <title>does not sound like</title>
+ <code>
+ (match-all (not (header-soundex "Cc" ${recipient})))
+ </code>
+ </option>
+ </input>
+ <input type="address" name="recipient"/>
+ </part>
+
+ <part name="bcc">
+ <title>BCC</title>
+ <input type="optionlist" name="recipient-type">
+ <option value="contains">
+ <title>contains</title>
+ <code>
+ (match-all (header-contains "Bcc" ${recipient}))
+ </code>
+ </option>
+ <option value="not contains">
+ <title>does not contain</title>
+ <code>
+ (match-all (not (header-contains "Bcc" ${recipient})))
+ </code>
+ </option>
+ <option value="is">
+ <title>is</title>
+ <code>
+ (match-all (header-matches "Bcc" ${recipient}))
+ </code>
+ </option>
+ <option value="is not">
+ <title>is not</title>
+ <code>
+ (match-all (not (header-matches "Bcc" ${recipient})))
+ </code>
+ </option>
+ <option value="starts with">
+ <title>starts with</title>
+ <code>
+ (match-all (header-starts-with "Bcc" ${recipient}))
+ </code>
+ </option>
+ <option value="not starts with">
+ <title>does not start with</title>
+ <code>
+ (match-all (not (header-starts-with "Bcc" ${recipient})))
+ </code>
+ </option>
+ <option value="ends with">
+ <title>ends with</title>
+ <code>
+ (match-all (header-ends-with "Bcc" ${recipient}))
+ </code>
+ </option>
+ <option value="not ends with">
+ <title>does not end with</title>
+ <code>
+ (match-all (not (header-ends-with "Bcc" ${recipient})))
+ </code>
+ </option>
+ <option value="matches soundex">
+ <title>sounds like</title>
+ <code>
+ (match-all (header-soundex "Bcc" ${recipient}))
+ </code>
+ </option>
+ <option value="not match soundex">
+ <title>does not sound like</title>
+ <code>
+ (match-all (not (header-soundex "Bcc" ${recipient})))
+ </code>
+ </option>
+ </input>
+ <input type="address" name="recipient"/>
+ </part>
+
<part name="senderto">
<title>Sender or Recipients</title>
<input type="optionlist" name="recipient-type">
@@ -252,6 +386,87 @@
</input>
<input type="string" name="subject"/>
</part>
+
+ <part name="header">
+ <title>Specific header</title>
+ <input type="string" name="header-field"/>
+ <input type="optionlist" name="header-type">
+ <option value="contains">
+ <title>contains</title>
+ <code>
+ (match-all (header-contains ${header-field} ${word}))
+ </code>
+ </option>
+ <option value="not contains">
+ <title>does not contain</title>
+ <code>
+ (match-all (not (header-contains ${header-field} ${word})))
+ </code>
+ </option>
+ <option value="is">
+ <title>is</title>
+ <code>
+ (match-all (header-matches ${header-field} ${word}))
+ </code>
+ </option>
+ <option value="is not">
+ <title>is not</title>
+ <code>
+ (match-all (not (header-matches ${header-field} ${word})))
+ </code>
+ </option>
+ <option value="starts with">
+ <title>starts with</title>
+ <code>
+ (match-all (header-starts-with ${header-field} ${word}))
+ </code>
+ </option>
+ <option value="not starts with">
+ <title>does not start with</title>
+ <code>
+ (match-all (not (header-starts-with ${header-field} ${word})))
+ </code>
+ </option>
+ <option value="ends with">
+ <title>ends with</title>
+ <code>
+ (match-all (header-ends-with ${header-field} ${word}))
+ </code>
+ </option>
+ <option value="not ends with">
+ <title>does not end with</title>
+ <code>
+ (match-all (not (header-ends-with ${header-field} ${word})))
+ </code>
+ </option>
+ <option value="exists">
+ <title>exists</title>
+ <code>
+ (match-all (header-exists ${header-field}))
+ </code>
+ </option>
+ <option value="not exists">
+ <title>does not exist</title>
+ <code>
+ (match-all (not (header-exists ${header-field})))
+ </code>
+ </option>
+ <option value="matches soundex">
+ <title>sounds like</title>
+ <code>
+ (match-all (header-soundex ${header-field} ${word}))
+ </code>
+ </option>
+ <option value="not match soundex">
+ <title>does not sound like</title>
+ <code>
+ (match-all (not (header-soundex ${header-field} ${word})))
+ </code>
+ </option>
+ </input>
+ <input type="string" name="word"/>
+ </part>
+
<part name="body">
<title>Message Body</title>
<input type="optionlist" name="body-type">
@@ -523,6 +738,44 @@
<input type="string" name="mlist"/>
</part>
+ <part name="regex">
+ <title>Regex Match</title>
+ <input type="optionlist" name="match-type">
+ <option value="header">
+ <title>Message Header</title>
+ <code>
+ (match-all (header-full-regex ${expression}))
+ </code>
+ </option>
+ <option value="body">
+ <title>Message Body</title>
+ <code>
+ (match-all (body-regex ${expression}))
+ </code>
+ </option>
+ </input>
+ <input type="regex" name="expression"/>
+ </part>
+
+ <part name="location">
+ <title>Message Location</title>
+ <input type="optionlist" name="msglocation-type">
+ <option value="is">
+ <title>is</title>
+ <code>
+ (match-all (message-location ${folder}))
+ </code>
+ </option>
+ <option value="is-not">
+ <title>is not</title>
+ <code>
+ (match-all (not (message-location ${folder})))
+ </code>
+ </option>
+ </input>
+ <input type="folder-curi" name="folder"/>
+ </part>
+
<part name="all">
<title>Match All</title>
<code>