aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--filter/ChangeLog18
-rw-r--r--filter/filter-element.c16
-rw-r--r--filter/filter-element.h5
-rw-r--r--filter/filter-input.c72
-rw-r--r--filter/filter-option.c7
-rw-r--r--filter/filter-part.c19
-rw-r--r--filter/filter-part.h2
-rw-r--r--filter/filter-rule.c11
-rw-r--r--filter/filtertypes.xml4
9 files changed, 139 insertions, 15 deletions
diff --git a/filter/ChangeLog b/filter/ChangeLog
index a43dce3f0d..bfa9886c53 100644
--- a/filter/ChangeLog
+++ b/filter/ChangeLog
@@ -1,5 +1,23 @@
2000-10-30 Jeffrey Stedfast <fejj@helixcode.com>
+ * filter-option.c (option_activate): If a regex option is
+ selected, change the FilterElement data to TRUE else set to FALSE.
+
+ * filter-rule.c (more_parts): Validate the previously entered
+ FilterPart before allowing the user to add a new FilterPart.
+
+ * filter-part.c (filter_part_validate): New convenience function
+ to validate an entire FilterPart expression.
+
+ * filter-input.c (validate): Validate the entry text if it
+ contains a regular expression.
+
+ * filter-element.[c,h]: New virtual function to validate the
+ contents of the FilterElement (useful for regex and sexp).
+ (filter_element_validate): You get the idea...
+
+2000-10-30 Jeffrey Stedfast <fejj@helixcode.com>
+
* filter-input.c:
* filter-option.c:
* filter-part.c: Pure formatting changes, no actual code
diff --git a/filter/filter-element.c b/filter/filter-element.c
index 21df744fe5..ad6e133a6a 100644
--- a/filter/filter-element.c
+++ b/filter/filter-element.c
@@ -31,6 +31,7 @@
#include "filter-folder.h"
#include "filter-url.h"
+static gboolean validate (FilterElement *fe, gpointer data);
static void xml_create(FilterElement *fe, xmlNodePtr node);
static FilterElement *clone(FilterElement *fe);
@@ -83,6 +84,7 @@ filter_element_class_init (FilterElementClass *class)
object_class->finalize = filter_element_finalise;
/* override methods */
+ class->validate = validate;
class->xml_create = xml_create;
class->clone = clone;
@@ -121,6 +123,12 @@ filter_element_new (void)
return o;
}
+gboolean
+filter_element_validate (FilterElement *fe, gpointer data)
+{
+ return ((FilterElementClass *)((GtkObject *)fe)->klass)->validate (fe, data);
+}
+
/**
* filter_element_xml_create:
* @fe: filter element
@@ -261,6 +269,12 @@ filter_element_new_type_name (const char *type)
}
/* default implementations */
+static gboolean
+validate (FilterElement *fe, gpointer data)
+{
+ return TRUE;
+}
+
static void
xml_create (FilterElement *fe, xmlNodePtr node)
{
@@ -280,5 +294,3 @@ clone (FilterElement *fe)
return new;
}
-
-
diff --git a/filter/filter-element.h b/filter/filter-element.h
index 8fe82402ee..ce5290c3cb 100644
--- a/filter/filter-element.h
+++ b/filter/filter-element.h
@@ -36,6 +36,7 @@ struct _FilterElement {
struct _FilterElementPrivate *priv;
char *name;
+ gpointer data;
};
struct _FilterPart;
@@ -44,6 +45,8 @@ struct _FilterElementClass {
GtkObjectClass parent_class;
/* virtual methods */
+ gboolean (*validate)(FilterElement *fe, gpointer data);
+
void (*xml_create)(FilterElement *, xmlNodePtr);
xmlNodePtr (*xml_encode)(FilterElement *);
int (*xml_decode)(FilterElement *, xmlNodePtr);
@@ -63,6 +66,8 @@ FilterElement *filter_element_new (void);
FilterElement *filter_element_new_type_name (const char *type);
/* methods */
+gboolean filter_element_validate (FilterElement *fe, gpointer data);
+
void filter_element_xml_create (FilterElement *fe, xmlNodePtr node);
xmlNodePtr filter_element_xml_encode (FilterElement *fe);
diff --git a/filter/filter-input.c b/filter/filter-input.c
index 2ef4327c33..fcee83a9eb 100644
--- a/filter/filter-input.c
+++ b/filter/filter-input.c
@@ -20,6 +20,7 @@
#include <gtk/gtk.h>
#include <gnome.h>
+#include <regex.h>
#include <gal/widgets/e-unicode.h>
@@ -28,6 +29,7 @@
#define d(x)
+static gboolean validate (FilterElement *fe, gpointer data);
static void xml_create(FilterElement *fe, xmlNodePtr node);
static xmlNodePtr xml_encode(FilterElement *fe);
static int xml_decode(FilterElement *fe, xmlNodePtr node);
@@ -86,6 +88,7 @@ filter_input_class_init (FilterInputClass *class)
object_class->finalize = filter_input_finalise;
/* override methods */
+ filter_element->validate = validate;
filter_element->xml_create = xml_create;
filter_element->xml_encode = xml_encode;
filter_element->xml_decode = xml_decode;
@@ -101,16 +104,16 @@ filter_input_class_init (FilterInputClass *class)
static void
filter_input_init (FilterInput *o)
{
- o->priv = g_malloc0(sizeof(*o->priv));
+ o->priv = g_malloc0 (sizeof (*o->priv));
}
static void
-filter_input_finalise(GtkObject *obj)
+filter_input_finalise (GtkObject *obj)
{
FilterInput *o = (FilterInput *)obj;
-
+
o = o;
-
+
((GtkObjectClass *)(parent_class))->finalize(obj);
}
@@ -131,8 +134,8 @@ filter_input_new (void)
FilterInput *
filter_input_new_type_name (const char *type)
{
- FilterInput *o = filter_input_new();
- o->type = g_strdup(type);
+ FilterInput *o = filter_input_new ();
+ o->type = g_strdup (type);
d(printf("new type %s = %p\n", type, o));
return o;
@@ -142,15 +145,62 @@ void
filter_input_set_value (FilterInput *fi, const char *value)
{
GList *l;
-
+
l = fi->values;
while (l) {
- g_free(l->data);
- l = g_list_next(l);
+ g_free (l->data);
+ l = g_list_next (l);
}
- g_list_free(fi->values);
+ g_list_free (fi->values);
+
+ fi->values = g_list_append (NULL, g_strdup (value));
+}
- fi->values = g_list_append(NULL, g_strdup(value));
+static gboolean
+validate (FilterElement *fe, gpointer data)
+{
+ FilterInput *fi = (FilterInput *)fe;
+ gboolean is_regex = FALSE;
+ gboolean valid = TRUE;
+
+ if (data)
+ is_regex = GPOINTER_TO_INT (data);
+
+ if (is_regex) {
+ regex_t regexpat; /* regex patern */
+ gint regerr;
+ char *text;
+
+ text = fi->values->data;
+
+ regerr = regcomp (&regexpat, text, REG_EXTENDED | REG_NEWLINE | REG_ICASE);
+ if (regerr) {
+ GtkWidget *dialog;
+ gchar *regmsg, *errmsg;
+ size_t reglen;
+
+ /* regerror gets called twice to get the full error string
+ length to do proper posix error reporting */
+ reglen = regerror (regerr, &regexpat, 0, 0);
+ regmsg = g_malloc0 (reglen + 1);
+ regerror (regerr, &regexpat, regmsg, reglen);
+
+ errmsg = g_strdup_printf (_("Error in regular expression '%s':\n%s"),
+ text, regmsg);
+ g_free (regmsg);
+
+ dialog = gnome_ok_dialog (errmsg);
+
+ gnome_dialog_run_and_close (GNOME_DIALOG (dialog));
+
+ g_free (errmsg);
+ valid = FALSE;
+ }
+
+ regfree (&regexpat);
+ }
+
+ return valid;
}
static void
diff --git a/filter/filter-option.c b/filter/filter-option.c
index 10ac977a1d..bdac9288d3 100644
--- a/filter/filter-option.c
+++ b/filter/filter-option.c
@@ -234,8 +234,15 @@ xml_decode (FilterElement *fe, xmlNodePtr node)
static void
option_activate (GtkMenuItem *item, FilterOption *fo)
{
+ FilterElement *fe = (FilterElement *) fo;
+ gboolean is_regex;
+
fo->current = gtk_object_get_data (GTK_OBJECT (item), "option");
d(printf ("option changed to %s\n", fo->current->title));
+
+ /* FIXME: there's probably a better way to do this */
+ is_regex = !(!strstr (fo->current->title, "regex"));
+ fe->data = GINT_TO_POINTER (is_regex);
}
static GtkWidget *
diff --git a/filter/filter-part.c b/filter/filter-part.c
index a467a0c3c0..f32ed517c7 100644
--- a/filter/filter-part.c
+++ b/filter/filter-part.c
@@ -113,6 +113,25 @@ filter_part_new (void)
return o;
}
+gboolean
+filter_part_validate (FilterPart *fp)
+{
+ gboolean correct = TRUE;
+ FilterElement *last = NULL;
+ GList *l;
+
+ l = fp->elements;
+ while (l && correct) {
+ FilterElement *fe = l->data;
+
+ correct = filter_element_validate (fe, last ? last->data : NULL);
+
+ last = fe;
+ l = l->next;
+ }
+
+ return correct;
+}
int
filter_part_xml_create (FilterPart *ff, xmlNodePtr node)
diff --git a/filter/filter-part.h b/filter/filter-part.h
index 2995046b20..bc9424486b 100644
--- a/filter/filter-part.h
+++ b/filter/filter-part.h
@@ -53,6 +53,8 @@ guint filter_part_get_type (void);
FilterPart *filter_part_new (void);
/* methods */
+gboolean filter_part_validate (FilterPart *fp);
+
int filter_part_xml_create (FilterPart *ff, xmlNodePtr node);
xmlNodePtr filter_part_xml_encode (FilterPart *fe);
diff --git a/filter/filter-rule.c b/filter/filter-rule.c
index 51e474aa72..a33373af5e 100644
--- a/filter/filter-rule.c
+++ b/filter/filter-rule.c
@@ -458,6 +458,17 @@ more_parts (GtkWidget *button, struct _rule_data *data)
FilterPart *new;
GtkWidget *w;
+ /* first make sure that the last part is ok */
+ if (data->fr->parts) {
+ FilterPart *part;
+ GList *l;
+
+ l = g_list_last (data->fr->parts);
+ part = l->data;
+ if (!filter_part_validate (part))
+ return;
+ }
+
/* create a new rule entry, use the first type of rule */
new = rule_context_next_part (data->f, NULL);
if (new) {
diff --git a/filter/filtertypes.xml b/filter/filtertypes.xml
index 925593e402..07846d731c 100644
--- a/filter/filtertypes.xml
+++ b/filter/filtertypes.xml
@@ -52,13 +52,13 @@
(match-all (not (header-ends-with "From" ${sender})))
</code>
</option>
- <option value="matches regex" type="regex">
+ <option value="matches regex">
<title>matches regex</title>
<code>
(match-all (header-regex "From" ${sender}))
</code>
</option>
- <option value="not match regex" type="regex">
+ <option value="not match regex">
<title>does not match regex</title>
<code>
(match-all (not (header-regex "From" ${sender})))