// invokeMessageCallback extracts the relevant data from the passed FETCH response // and invokes the user-provided callback. func (w *IMAPSource) invokeMessageCallback(msgInfo *imap.MessageInfo) error { logger.Debugf("handling mail uid=%d", msgInfo.Attrs["UID"]) flags := imap.AsFlagSet(msgInfo.Attrs["FLAGS"]) idate := imap.AsDateTime(msgInfo.Attrs["INTERNALDATE"]) mailBytes := imap.AsBytes(msgInfo.Attrs["RFC822"]) mailLiteral := imap.NewLiteral(mailBytes) logger.Debugf("invoking message transformer") err := w.callbackFunc(flags, &idate, mailLiteral) if err == nil { logger.Debugf("message transformation successful") } else { logger.Warningf("message transformation failed: %s", err) } return err }
// newEmailMessage will parse an imap.FieldMap into an map[string]interface{}. This // will expect the message to container the internaldate and the body with // all headers included. func newEmailMessage(msgFields imap.FieldMap) (map[string]interface{}, error) { var email map[string]interface{} // parse the header rawHeader := imap.AsBytes(msgFields["RFC822.HEADER"]) msg, err := mail.ReadMessage(bytes.NewReader(rawHeader)) if err != nil { return email, err } email = map[string]interface{}{ "internal_date": imap.AsDateTime(msgFields["INTERNALDATE"]), "body": imap.AsString(msgFields["BODY[]"]), "from": msg.Header.Get("From"), "to": msg.Header.Get("To"), "subject": msg.Header.Get("Subject"), } return email, nil }
// newEmailMessage will parse an imap.FieldMap into an Email. This // will expect the message to container the internaldate and the body with // all headers included. func newEmail(msgFields imap.FieldMap) (Email, error) { var email Email // parse the header var message bytes.Buffer message.Write(imap.AsBytes(msgFields["RFC822.HEADER"])) message.Write([]byte("\n\n")) rawBody := imap.AsBytes(msgFields["BODY[]"]) message.Write(rawBody) msg, err := mail.ReadMessage(&message) if err != nil { return email, fmt.Errorf("unable to read header: %s", err) } from, err := mail.ParseAddress(msg.Header.Get("From")) if err != nil { return email, fmt.Errorf("unable to parse from address: %s", err) } to, err := mail.ParseAddressList(msg.Header.Get("To")) if err != nil { return email, fmt.Errorf("unable to parse to address: %s", err) } email = Email{ Message: msg, InternalDate: imap.AsDateTime(msgFields["INTERNALDATE"]), Precedence: msg.Header.Get("Precedence"), From: from, To: to, Subject: parseSubject(msg.Header.Get("Subject")), } // chunk the body up into simple chunks email.HTML, email.Text, email.IsMultiPart, err = parseBody(msg.Header, rawBody) return email, err }