mirror of
https://github.com/matrix-org/dendrite.git
synced 2025-12-29 01:33:10 -06:00
Define Mailer interface and provide SmtpMailer implementation
This commit is contained in:
parent
503f43abe0
commit
4d1f248a9b
|
|
@ -22,6 +22,16 @@ import (
|
||||||
"github.com/matrix-org/gomatrixserverlib"
|
"github.com/matrix-org/gomatrixserverlib"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
const (
|
||||||
|
// Verification is used in
|
||||||
|
// - https://matrix.org/docs/spec/client_server/r0.6.1#post-matrix-client-r0-account-3pid-email-requesttoken
|
||||||
|
// - https://matrix.org/docs/spec/client_server/r0.6.1#post-matrix-client-r0-register-email-requesttoken
|
||||||
|
Verification ThreepidSessionType = iota
|
||||||
|
// Password is used in
|
||||||
|
// - https://matrix.org/docs/spec/client_server/r0.6.1#post-matrix-client-r0-account-password-email-requesttoken
|
||||||
|
Password
|
||||||
|
)
|
||||||
|
|
||||||
// UserInternalAPI is the internal API for information about users and devices.
|
// UserInternalAPI is the internal API for information about users and devices.
|
||||||
type UserInternalAPI interface {
|
type UserInternalAPI interface {
|
||||||
InputAccountData(ctx context.Context, req *InputAccountDataRequest, res *InputAccountDataResponse) error
|
InputAccountData(ctx context.Context, req *InputAccountDataRequest, res *InputAccountDataResponse) error
|
||||||
|
|
@ -365,3 +375,5 @@ type IsSessionValidatedResponse struct {
|
||||||
Validated bool
|
Validated bool
|
||||||
ValidatedAt int
|
ValidatedAt int
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type ThreepidSessionType int
|
||||||
|
|
|
||||||
102
userapi/mail/mail.go
Normal file
102
userapi/mail/mail.go
Normal file
|
|
@ -0,0 +1,102 @@
|
||||||
|
package mail
|
||||||
|
|
||||||
|
import (
|
||||||
|
"bytes"
|
||||||
|
"fmt"
|
||||||
|
"io/ioutil"
|
||||||
|
"net/smtp"
|
||||||
|
"text/template"
|
||||||
|
"time"
|
||||||
|
|
||||||
|
"github.com/matrix-org/dendrite/internal"
|
||||||
|
"github.com/matrix-org/dendrite/setup/config"
|
||||||
|
"github.com/matrix-org/dendrite/userapi/api"
|
||||||
|
)
|
||||||
|
|
||||||
|
const (
|
||||||
|
messageIdByteLength = 48
|
||||||
|
)
|
||||||
|
|
||||||
|
type Mailer interface {
|
||||||
|
// Send is used in
|
||||||
|
// - https://matrix.org/docs/spec/client_server/r0.6.1#post-matrix-client-r0-account-3pid-email-requesttoken
|
||||||
|
// - https://matrix.org/docs/spec/client_server/r0.6.1#post-matrix-client-r0-register-email-requesttoken
|
||||||
|
// - https://matrix.org/docs/spec/client_server/r0.6.1#post-matrix-client-r0-account-password-email-requesttoken
|
||||||
|
Send(*Mail, api.ThreepidSessionType) error
|
||||||
|
}
|
||||||
|
type SmtpMailer struct {
|
||||||
|
conf config.EmailConf
|
||||||
|
templates map[api.ThreepidSessionType]*template.Template
|
||||||
|
}
|
||||||
|
|
||||||
|
type Mail struct {
|
||||||
|
To string
|
||||||
|
Link string
|
||||||
|
Token string
|
||||||
|
Extra []string
|
||||||
|
}
|
||||||
|
|
||||||
|
type Substitutions struct {
|
||||||
|
*Mail
|
||||||
|
Date string
|
||||||
|
MessageId string
|
||||||
|
}
|
||||||
|
|
||||||
|
func (m *SmtpMailer) Send(mail *Mail, t api.ThreepidSessionType) error {
|
||||||
|
return m.send(mail, m.templates[t])
|
||||||
|
}
|
||||||
|
|
||||||
|
func (m *SmtpMailer) send(mail *Mail, t *template.Template) error {
|
||||||
|
messageId, err := internal.GenerateBlob(messageIdByteLength)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
s := Substitutions{
|
||||||
|
Mail: mail,
|
||||||
|
Date: time.Now().Format(time.RFC1123Z),
|
||||||
|
MessageId: messageId,
|
||||||
|
}
|
||||||
|
b := bytes.Buffer{}
|
||||||
|
err = t.Execute(&b, s)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
return smtp.SendMail(
|
||||||
|
m.conf.Smtp.Host,
|
||||||
|
smtp.PlainAuth(
|
||||||
|
"",
|
||||||
|
m.conf.Smtp.User,
|
||||||
|
m.conf.Smtp.Password,
|
||||||
|
m.conf.Smtp.Host,
|
||||||
|
),
|
||||||
|
m.conf.From,
|
||||||
|
[]string{
|
||||||
|
mail.To,
|
||||||
|
},
|
||||||
|
b.Bytes(),
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
func NewMailer(c *config.UserAPI) (Mailer, error) {
|
||||||
|
templateRaw, err := ioutil.ReadFile(fmt.Sprintf("%s/verification.eml", c.Email.TemplatesPath))
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
verificationT, err := template.New("verification").Parse(string(templateRaw))
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
templateRaw, err = ioutil.ReadFile(fmt.Sprintf("%s/password.eml", c.Email.TemplatesPath))
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
passwordT, err := template.New("password").Parse(string(templateRaw))
|
||||||
|
return &SmtpMailer{
|
||||||
|
conf: c.Email,
|
||||||
|
templates: map[api.ThreepidSessionType]*template.Template{
|
||||||
|
api.Password: passwordT,
|
||||||
|
api.Verification: verificationT,
|
||||||
|
},
|
||||||
|
}, err
|
||||||
|
|
||||||
|
}
|
||||||
38
userapi/mail/mail_test.go
Normal file
38
userapi/mail/mail_test.go
Normal file
|
|
@ -0,0 +1,38 @@
|
||||||
|
package mail
|
||||||
|
|
||||||
|
import (
|
||||||
|
"testing"
|
||||||
|
|
||||||
|
"github.com/matrix-org/dendrite/setup/config"
|
||||||
|
"github.com/matrix-org/dendrite/userapi/api"
|
||||||
|
"github.com/matryer/is"
|
||||||
|
)
|
||||||
|
|
||||||
|
func TestSendVerification(t *testing.T) {
|
||||||
|
is := is.New(t)
|
||||||
|
dut := mustNewMailer(is)
|
||||||
|
err := dut.Send(
|
||||||
|
&Mail{
|
||||||
|
To: "kevil11378@186site.com",
|
||||||
|
Link: "my",
|
||||||
|
Token: "foo",
|
||||||
|
Extra: []string{
|
||||||
|
"bar",
|
||||||
|
},
|
||||||
|
}, api.Verification)
|
||||||
|
is.NoErr(err)
|
||||||
|
}
|
||||||
|
|
||||||
|
func mustNewMailer(is *is.I) Mailer {
|
||||||
|
mailer, err := NewMailer(&config.UserAPI{
|
||||||
|
Email: config.EmailConf{
|
||||||
|
TemplatesPath: "../../res/default",
|
||||||
|
From: "test@matrix.com",
|
||||||
|
Smtp: config.Smtp{
|
||||||
|
Host: "localhost:25",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
})
|
||||||
|
is.NoErr(err)
|
||||||
|
return mailer
|
||||||
|
}
|
||||||
Loading…
Reference in a new issue