main.go (view raw)
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 |
package main import ( "bufio" "bytes" "encoding/json" "errors" "fmt" "io" "io/ioutil" "log" "net/http" "os" "strings" "github.com/emersion/go-message/mail" "github.com/microcosm-cc/bluemonday" ) type Mail struct { From string Date string Body string ContentType string } func makeReq(j []byte) { req, err := http.NewRequest("POST", "http://localhost:8001/webhook", bytes.NewBuffer(j)) req.Header.Set("Content-Type", "application/json") client := http.Client{} res, err := client.Do(req) if err != nil { log.Fatal(err) } defer res.Body.Close() } func cleanHTML(body string) string { bm := bluemonday.StrictPolicy() bm.AddSpaceWhenStrippingTag(true) clean := bm.Sanitize(body) return clean } func jsonMail(p *mail.Part, mr *mail.Reader) ([]byte, error) { b, _ := ioutil.ReadAll(p.Body) body := string(b) ct := p.Header.Get("Content-Type") from := mr.Header.Get("From") date := mr.Header.Get("Date") // Prefer plaintext part over html if strings.Contains(ct, "text/plain") { m := Mail{from, date, body, "text/plain"} j, err := json.Marshal(m) if err != nil { log.Fatal(err) } return j, nil // If there's no plaintext, fallback on html // Clean up HTML junk using bluemonday } else if strings.Contains(ct, "text/html") { cleanBody := cleanHTML(body) m := Mail{from, date, cleanBody, "text/html"} j, err := json.Marshal(m) if err != nil { log.Fatal(err) } return j, nil } else { return nil, errors.New("no plaintext or html parts") } } func main() { r := bufio.NewReader(os.Stdin) mr, err := mail.CreateReader(r) if err != nil { log.Fatal(err) } for { p, err := mr.NextPart() if err == io.EOF { break } else if err != nil { log.Fatal(err) } switch h := p.Header.(type) { case *mail.InlineHeader: jm, err := jsonMail(p, mr) fmt.Println(string(jm)) if err != nil { log.Fatal(err) } makeReq(jm) case *mail.AttachmentHeader: filename, _ := h.Filename() log.Printf("Got attachment: %v\n", filename) } } } |