Merge pull request #854 from joeirimpan/postback

feat(postback): Add attachment, from email to postback body
This commit is contained in:
Kailash Nadh 2022-06-27 16:19:47 +05:30 committed by GitHub
commit a2d01b20da
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
4 changed files with 250 additions and 59 deletions

2
go.mod
View file

@ -24,7 +24,7 @@ require (
github.com/mattn/go-colorable v0.1.12 // indirect
github.com/mitchellh/mapstructure v1.4.2 // indirect
github.com/niemeyer/pretty v0.0.0-20200227124842-a10e7caefd8e // indirect
github.com/paulbellamy/ratecounter v0.2.0 // indirect
github.com/paulbellamy/ratecounter v0.2.0
github.com/pelletier/go-toml v1.9.4 // indirect
github.com/rhnvrm/simples3 v0.8.2
github.com/spf13/cast v1.4.1 // indirect

2
go.sum
View file

@ -144,8 +144,6 @@ github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZb
github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
github.com/posener/complete v1.1.1/go.mod h1:em0nMJCgc9GFtwrmVmEMR/ZL6WyhyjMBndrE9hABlRI=
github.com/rhnvrm/simples3 v0.6.1/go.mod h1:Y+3vYm2V7Y4VijFoJHHTrja6OgPrJ2cBti8dPGkC3sA=
github.com/rhnvrm/simples3 v0.8.1 h1:jL2yCi9P0pA8hFYkyVWZ4cs5RX3AMgcVsXTOqnCj0/w=
github.com/rhnvrm/simples3 v0.8.1/go.mod h1:Y+3vYm2V7Y4VijFoJHHTrja6OgPrJ2cBti8dPGkC3sA=
github.com/rhnvrm/simples3 v0.8.2 h1:O9dj0DLaU8clz4ctuI82k9VH/X+TbtdfKLlivMmF6Xw=
github.com/rhnvrm/simples3 v0.8.2/go.mod h1:Y+3vYm2V7Y4VijFoJHHTrja6OgPrJ2cBti8dPGkC3sA=
github.com/ryanuber/columnize v2.1.0+incompatible/go.mod h1:sm1tb6uqfes/u+d4ooFouqFdy9/2g9QGwK3SQygK0Ts=

View file

@ -7,6 +7,7 @@ import (
"io"
"io/ioutil"
"net/http"
"net/textproto"
"time"
"github.com/knadh/listmonk/internal/messenger"
@ -16,26 +17,34 @@ import (
// postback is the payload that's posted as JSON to the HTTP Postback server.
//easyjson:json
type postback struct {
Subject string `json:"subject"`
ContentType string `json:"content_type"`
Body string `json:"body"`
Recipients []recipient `json:"recipients"`
Campaign *campaign `json:"campaign"`
Subject string `json:"subject"`
ContentType string `json:"content_type"`
Body string `json:"body"`
Recipients []recipient `json:"recipients"`
Campaign *campaign `json:"campaign"`
Attachments []attachment `json:"attachments"`
}
type campaign struct {
UUID string `db:"uuid" json:"uuid"`
Name string `db:"name" json:"name"`
Headers models.Headers `db:"headers" json:"headers"`
Tags []string `db:"tags" json:"tags"`
FromEmail string `json:"from_email"`
UUID string `json:"uuid"`
Name string `json:"name"`
Headers models.Headers `json:"headers"`
Tags []string `json:"tags"`
}
type recipient struct {
UUID string `db:"uuid" json:"uuid"`
Email string `db:"email" json:"email"`
Name string `db:"name" json:"name"`
Attribs models.SubscriberAttribs `db:"attribs" json:"attribs"`
Status string `db:"status" json:"status"`
UUID string `json:"uuid"`
Email string `json:"email"`
Name string `json:"name"`
Attribs models.SubscriberAttribs `json:"attribs"`
Status string `json:"status"`
}
type attachment struct {
Name string `json:"name"`
Header textproto.MIMEHeader `json:"header"`
Content []byte `json:"content"`
}
// Options represents HTTP Postback server options.
@ -101,10 +110,24 @@ func (p *Postback) Push(m messenger.Message) error {
if m.Campaign != nil {
pb.Campaign = &campaign{
UUID: m.Campaign.UUID,
Name: m.Campaign.Name,
Headers: m.Campaign.Headers,
Tags: m.Campaign.Tags,
FromEmail: m.Campaign.FromEmail,
UUID: m.Campaign.UUID,
Name: m.Campaign.Name,
Headers: m.Campaign.Headers,
Tags: m.Campaign.Tags,
}
}
if len(m.Attachments) > 0 {
files := make([]attachment, 0, len(m.Attachments))
for _, f := range m.Attachments {
a := attachment{
Name: f.Name,
Header: f.Header,
Content: make([]byte, len(f.Content)),
}
copy(a.Content, f.Content)
files = append(files, a)
}
}

View file

@ -8,6 +8,7 @@ import (
easyjson "github.com/mailru/easyjson"
jlexer "github.com/mailru/easyjson/jlexer"
jwriter "github.com/mailru/easyjson/jwriter"
textproto "net/textproto"
)
// suppress unused package warning
@ -76,6 +77,29 @@ func easyjsonDf11841fDecodeGithubComKnadhListmonkInternalMessengerPostback(in *j
}
easyjsonDf11841fDecodeGithubComKnadhListmonkInternalMessengerPostback2(in, out.Campaign)
}
case "attachments":
if in.IsNull() {
in.Skip()
out.Attachments = nil
} else {
in.Delim('[')
if out.Attachments == nil {
if !in.IsDelim(']') {
out.Attachments = make([]attachment, 0, 1)
} else {
out.Attachments = []attachment{}
}
} else {
out.Attachments = (out.Attachments)[:0]
}
for !in.IsDelim(']') {
var v2 attachment
easyjsonDf11841fDecodeGithubComKnadhListmonkInternalMessengerPostback3(in, &v2)
out.Attachments = append(out.Attachments, v2)
in.WantComma()
}
in.Delim(']')
}
default:
in.SkipRecursive()
}
@ -112,11 +136,11 @@ func easyjsonDf11841fEncodeGithubComKnadhListmonkInternalMessengerPostback(out *
out.RawString("null")
} else {
out.RawByte('[')
for v2, v3 := range in.Recipients {
if v2 > 0 {
for v3, v4 := range in.Recipients {
if v3 > 0 {
out.RawByte(',')
}
easyjsonDf11841fEncodeGithubComKnadhListmonkInternalMessengerPostback1(out, v3)
easyjsonDf11841fEncodeGithubComKnadhListmonkInternalMessengerPostback1(out, v4)
}
out.RawByte(']')
}
@ -130,6 +154,22 @@ func easyjsonDf11841fEncodeGithubComKnadhListmonkInternalMessengerPostback(out *
easyjsonDf11841fEncodeGithubComKnadhListmonkInternalMessengerPostback2(out, *in.Campaign)
}
}
{
const prefix string = ",\"attachments\":"
out.RawString(prefix)
if in.Attachments == nil && (out.Flags&jwriter.NilSliceAsEmpty) == 0 {
out.RawString("null")
} else {
out.RawByte('[')
for v5, v6 := range in.Attachments {
if v5 > 0 {
out.RawByte(',')
}
easyjsonDf11841fEncodeGithubComKnadhListmonkInternalMessengerPostback3(out, v6)
}
out.RawByte(']')
}
}
out.RawByte('}')
}
@ -156,6 +196,129 @@ func (v *postback) UnmarshalJSON(data []byte) error {
func (v *postback) UnmarshalEasyJSON(l *jlexer.Lexer) {
easyjsonDf11841fDecodeGithubComKnadhListmonkInternalMessengerPostback(l, v)
}
func easyjsonDf11841fDecodeGithubComKnadhListmonkInternalMessengerPostback3(in *jlexer.Lexer, out *attachment) {
isTopLevel := in.IsStart()
if in.IsNull() {
if isTopLevel {
in.Consumed()
}
in.Skip()
return
}
in.Delim('{')
for !in.IsDelim('}') {
key := in.UnsafeFieldName(false)
in.WantColon()
if in.IsNull() {
in.Skip()
in.WantComma()
continue
}
switch key {
case "name":
out.Name = string(in.String())
case "header":
if in.IsNull() {
in.Skip()
} else {
in.Delim('{')
out.Header = make(textproto.MIMEHeader)
for !in.IsDelim('}') {
key := string(in.String())
in.WantColon()
var v7 []string
if in.IsNull() {
in.Skip()
v7 = nil
} else {
in.Delim('[')
if v7 == nil {
if !in.IsDelim(']') {
v7 = make([]string, 0, 4)
} else {
v7 = []string{}
}
} else {
v7 = (v7)[:0]
}
for !in.IsDelim(']') {
var v8 string
v8 = string(in.String())
v7 = append(v7, v8)
in.WantComma()
}
in.Delim(']')
}
(out.Header)[key] = v7
in.WantComma()
}
in.Delim('}')
}
case "content":
if in.IsNull() {
in.Skip()
out.Content = nil
} else {
out.Content = in.Bytes()
}
default:
in.SkipRecursive()
}
in.WantComma()
}
in.Delim('}')
if isTopLevel {
in.Consumed()
}
}
func easyjsonDf11841fEncodeGithubComKnadhListmonkInternalMessengerPostback3(out *jwriter.Writer, in attachment) {
out.RawByte('{')
first := true
_ = first
{
const prefix string = ",\"name\":"
out.RawString(prefix[1:])
out.String(string(in.Name))
}
{
const prefix string = ",\"header\":"
out.RawString(prefix)
if in.Header == nil && (out.Flags&jwriter.NilMapAsEmpty) == 0 {
out.RawString(`null`)
} else {
out.RawByte('{')
v10First := true
for v10Name, v10Value := range in.Header {
if v10First {
v10First = false
} else {
out.RawByte(',')
}
out.String(string(v10Name))
out.RawByte(':')
if v10Value == nil && (out.Flags&jwriter.NilSliceAsEmpty) == 0 {
out.RawString("null")
} else {
out.RawByte('[')
for v11, v12 := range v10Value {
if v11 > 0 {
out.RawByte(',')
}
out.String(string(v12))
}
out.RawByte(']')
}
}
out.RawByte('}')
}
}
{
const prefix string = ",\"content\":"
out.RawString(prefix)
out.Base64Bytes(in.Content)
}
out.RawByte('}')
}
func easyjsonDf11841fDecodeGithubComKnadhListmonkInternalMessengerPostback2(in *jlexer.Lexer, out *campaign) {
isTopLevel := in.IsStart()
if in.IsNull() {
@ -175,6 +338,8 @@ func easyjsonDf11841fDecodeGithubComKnadhListmonkInternalMessengerPostback2(in *
continue
}
switch key {
case "from_email":
out.FromEmail = string(in.String())
case "uuid":
out.UUID = string(in.String())
case "name":
@ -195,23 +360,23 @@ func easyjsonDf11841fDecodeGithubComKnadhListmonkInternalMessengerPostback2(in *
out.Headers = (out.Headers)[:0]
}
for !in.IsDelim(']') {
var v4 map[string]string
var v15 map[string]string
if in.IsNull() {
in.Skip()
} else {
in.Delim('{')
v4 = make(map[string]string)
v15 = make(map[string]string)
for !in.IsDelim('}') {
key := string(in.String())
in.WantColon()
var v5 string
v5 = string(in.String())
(v4)[key] = v5
var v16 string
v16 = string(in.String())
(v15)[key] = v16
in.WantComma()
}
in.Delim('}')
}
out.Headers = append(out.Headers, v4)
out.Headers = append(out.Headers, v15)
in.WantComma()
}
in.Delim(']')
@ -232,9 +397,9 @@ func easyjsonDf11841fDecodeGithubComKnadhListmonkInternalMessengerPostback2(in *
out.Tags = (out.Tags)[:0]
}
for !in.IsDelim(']') {
var v6 string
v6 = string(in.String())
out.Tags = append(out.Tags, v6)
var v17 string
v17 = string(in.String())
out.Tags = append(out.Tags, v17)
in.WantComma()
}
in.Delim(']')
@ -254,8 +419,13 @@ func easyjsonDf11841fEncodeGithubComKnadhListmonkInternalMessengerPostback2(out
first := true
_ = first
{
const prefix string = ",\"uuid\":"
const prefix string = ",\"from_email\":"
out.RawString(prefix[1:])
out.String(string(in.FromEmail))
}
{
const prefix string = ",\"uuid\":"
out.RawString(prefix)
out.String(string(in.UUID))
}
{
@ -270,24 +440,24 @@ func easyjsonDf11841fEncodeGithubComKnadhListmonkInternalMessengerPostback2(out
out.RawString("null")
} else {
out.RawByte('[')
for v7, v8 := range in.Headers {
if v7 > 0 {
for v18, v19 := range in.Headers {
if v18 > 0 {
out.RawByte(',')
}
if v8 == nil && (out.Flags&jwriter.NilMapAsEmpty) == 0 {
if v19 == nil && (out.Flags&jwriter.NilMapAsEmpty) == 0 {
out.RawString(`null`)
} else {
out.RawByte('{')
v9First := true
for v9Name, v9Value := range v8 {
if v9First {
v9First = false
v20First := true
for v20Name, v20Value := range v19 {
if v20First {
v20First = false
} else {
out.RawByte(',')
}
out.String(string(v9Name))
out.String(string(v20Name))
out.RawByte(':')
out.String(string(v9Value))
out.String(string(v20Value))
}
out.RawByte('}')
}
@ -302,11 +472,11 @@ func easyjsonDf11841fEncodeGithubComKnadhListmonkInternalMessengerPostback2(out
out.RawString("null")
} else {
out.RawByte('[')
for v10, v11 := range in.Tags {
if v10 > 0 {
for v21, v22 := range in.Tags {
if v21 > 0 {
out.RawByte(',')
}
out.String(string(v11))
out.String(string(v22))
}
out.RawByte(']')
}
@ -347,15 +517,15 @@ func easyjsonDf11841fDecodeGithubComKnadhListmonkInternalMessengerPostback1(in *
for !in.IsDelim('}') {
key := string(in.String())
in.WantColon()
var v12 interface{}
if m, ok := v12.(easyjson.Unmarshaler); ok {
var v23 interface{}
if m, ok := v23.(easyjson.Unmarshaler); ok {
m.UnmarshalEasyJSON(in)
} else if m, ok := v12.(json.Unmarshaler); ok {
} else if m, ok := v23.(json.Unmarshaler); ok {
_ = m.UnmarshalJSON(in.Raw())
} else {
v12 = in.Interface()
v23 = in.Interface()
}
(out.Attribs)[key] = v12
(out.Attribs)[key] = v23
in.WantComma()
}
in.Delim('}')
@ -398,21 +568,21 @@ func easyjsonDf11841fEncodeGithubComKnadhListmonkInternalMessengerPostback1(out
out.RawString(`null`)
} else {
out.RawByte('{')
v13First := true
for v13Name, v13Value := range in.Attribs {
if v13First {
v13First = false
v24First := true
for v24Name, v24Value := range in.Attribs {
if v24First {
v24First = false
} else {
out.RawByte(',')
}
out.String(string(v13Name))
out.String(string(v24Name))
out.RawByte(':')
if m, ok := v13Value.(easyjson.Marshaler); ok {
if m, ok := v24Value.(easyjson.Marshaler); ok {
m.MarshalEasyJSON(out)
} else if m, ok := v13Value.(json.Marshaler); ok {
} else if m, ok := v24Value.(json.Marshaler); ok {
out.Raw(m.MarshalJSON())
} else {
out.Raw(json.Marshal(v13Value))
out.Raw(json.Marshal(v24Value))
}
}
out.RawByte('}')