This patch looks at certain paramters after an E-Mail message is edited and
makes it possible to adapt the from header based on certain conditions or the
from lines.

Example:

send2-hook '! ~C problems@' 'clr_header reply-to:'
send2-hook '~C problems@' 'set_header reply-to: problems'

send2-hook '! ~C @lhsystems.com' 'set_header from: Thomas Glanzmann 
<[email protected]>'
send2-hook '~C @lhsystems.com | ~C @tomorrow-focus.de' 'set_header from: Thomas 
Glanzmann <[email protected]>'
---
 hook.c   |   79 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 init.h   |    4 ++++
 mutt.h   |    6 +++++
 protos.h |    1 +
 4 files changed, 90 insertions(+)

diff --git a/hook.c b/hook.c
index 34f3106..d724758 100644
--- a/hook.c
+++ b/hook.c
@@ -42,6 +42,82 @@ typedef struct hook
 static HOOK *Hooks = NULL;
 
 static int current_hook_type = 0;
+static ENVELOPE *current_hook_env = NULL;
+
+int mutt_modify_header (BUFFER *buf, BUFFER *s, unsigned long data, BUFFER 
*err)
+{
+  size_t keylen;
+  char *p;
+  ADDRESS **c = NULL;
+
+
+  mutt_extract_token (buf, s, M_TOKEN_SPACE | M_TOKEN_QUOTE);
+  if ((p = strpbrk (buf->data, ": \t")) == NULL || *p != ':')
+  {
+    strfcpy (err->data, _("invalid header field"), err->dsize);
+    return (-1);
+  }
+
+  keylen = p - buf->data + 1;
+
+  if (current_hook_env == NULL) {
+         strfcpy (err->data, _("not called inside a hook"), err->dsize);
+         return (-1);
+  }
+
+  if (ascii_strncasecmp (buf->data, "reply-to:", 9) == 0) {
+       c = &(current_hook_env->reply_to);
+
+  } else if (ascii_strncasecmp (buf->data, "from:", 5) == 0) {
+       c = &(current_hook_env->from);
+
+  } else {
+        strfcpy (err->data, _("can't handle this heaer"), err->dsize);
+       return -1;
+  }
+
+  switch(data) {
+  case MODIFYHEADER_ADD:
+         /* FIXME: check if already there --tg 17:37 05-05-12 */
+         *c = rfc822_parse_adrlist (*c, buf->data + keylen);
+         break;
+
+  case MODIFYHEADER_CLR:
+         rfc822_free_address (c);
+         break;
+
+  case MODIFYHEADER_DEL:
+#if 0
+         {
+                 ADDRESS *t = *c;
+                 while(t) {
+                         if (ascii_strncasecmp (buf->data + keylen, t->mailbox,
+                                         mutt_strlen(buf->data + keylen)) == 
0) {
+                         }
+
+                         rfc822_free_address (c);
+                 }
+         }
+#else
+        strfcpy (err->data, _("not implemented"), err->dsize);
+       return -1;
+#endif
+         break;
+
+  case MODIFYHEADER_SET:
+         rfc822_free_address (c);
+         *c = rfc822_parse_adrlist (*c, buf->data + keylen);
+         break;
+
+  default:
+         strfcpy (err->data, _("can only add, del or set header"), err->dsize);
+         return -1;
+         break;
+  }
+
+  memset (buf, 0, sizeof (BUFFER));
+  return 0;
+}
 
 int mutt_parse_hook (BUFFER *buf, BUFFER *s, unsigned long data, BUFFER *err)
 {
@@ -333,6 +409,7 @@ void mutt_message_hook (CONTEXT *ctx, HEADER *hdr, int type)
   HOOK *hook;
 
   current_hook_type = type;
+  current_hook_env  = hdr->env;
 
   mutt_buffer_init (&err);
   err.dsize = STRING;
@@ -351,6 +428,7 @@ void mutt_message_hook (CONTEXT *ctx, HEADER *hdr, int type)
          mutt_error ("%s", err.data);
          mutt_sleep (1);
          current_hook_type = 0;
+          current_hook_env  = NULL;
          FREE (&err.data);
 
          return;
@@ -360,6 +438,7 @@ void mutt_message_hook (CONTEXT *ctx, HEADER *hdr, int type)
   FREE (&err.data);
 
   current_hook_type = 0;
+  current_hook_env  = NULL;
 }
 
 static int
diff --git a/init.h b/init.h
index b5b2886..e38c10d 100644
--- a/init.h
+++ b/init.h
@@ -3514,6 +3514,7 @@ struct command_t
 };
 
 const struct command_t Commands[] = {
+  { "add_header",       mutt_modify_header,     MODIFYHEADER_ADD },
   { "alternates",      parse_alternates,       0 },
   { "unalternates",    parse_unalternates,     0 },
 #ifdef USE_SOCKET
@@ -3526,10 +3527,12 @@ const struct command_t Commands[] = {
   { "alternative_order",       parse_list,     UL &AlternativeOrderList},
   { "bind",            mutt_parse_bind,        0 },
   { "charset-hook",    mutt_parse_hook,        M_CHARSETHOOK },
+  { "clr_header",       mutt_modify_header,     MODIFYHEADER_CLR },
 #ifdef HAVE_COLOR
   { "color",           mutt_parse_color,       0 },
   { "uncolor",         mutt_parse_uncolor,     0 },
 #endif
+  { "del_header",       mutt_modify_header,     MODIFYHEADER_DEL },
   { "exec",            mutt_parse_exec,        0 },
   { "fcc-hook",                mutt_parse_hook,        M_FCCHOOK },
   { "fcc-save-hook",   mutt_parse_hook,        M_FCCHOOK | M_SAVEHOOK },
@@ -3564,6 +3567,7 @@ const struct command_t Commands[] = {
   { "source",          parse_source,           0 },
   { "spam",            parse_spam_list,        M_SPAM },
   { "nospam",          parse_spam_list,        M_NOSPAM },
+  { "set_header",       mutt_modify_header,     MODIFYHEADER_SET },
   { "subscribe",       parse_subscribe,        0 },
   { "toggle",          parse_set,              M_SET_INV },
   { "unalias",         parse_unalias,          0 },
diff --git a/mutt.h b/mutt.h
index 06e3c8c..d5ffc63 100644
--- a/mutt.h
+++ b/mutt.h
@@ -308,6 +308,12 @@ enum
 #define M_SPAM          1
 #define M_NOSPAM        2
 
+/* flags for mutt_modify_header */
+#define MODIFYHEADER_ADD (1<<0)
+#define MODIFYHEADER_CLR (1<<1)
+#define MODIFYHEADER_DEL (1<<2)
+#define MODIFYHEADER_SET (1<<3)
+
 /* boolean vars */
 enum
 {
diff --git a/protos.h b/protos.h
index cbd6199..fe69fad 100644
--- a/protos.h
+++ b/protos.h
@@ -323,6 +323,7 @@ int mutt_match_rx_list (const char *, RX_LIST *);
 int mutt_match_spam_list (const char *, SPAM_LIST *, char *, int);
 int mutt_messages_in_thread (CONTEXT *, HEADER *, int);
 int mutt_multi_choice (char *prompt, char *letters);
+int mutt_modify_header (BUFFER *buf, BUFFER *s, unsigned long data, BUFFER 
*err);
 int mutt_needs_mailcap (BODY *);
 int mutt_num_postponed (int);
 int mutt_parse_bind (BUFFER *, BUFFER *, unsigned long, BUFFER *);
-- 
1.7.10.4

Reply via email to