215 lines
5.4 KiB
Go
215 lines
5.4 KiB
Go
package mailx
|
|
|
|
import (
|
|
"bytes"
|
|
"encoding/base64"
|
|
"fmt"
|
|
"net/smtp"
|
|
"os"
|
|
"path"
|
|
"strings"
|
|
"time"
|
|
)
|
|
|
|
// 邮件发送的封装
|
|
// 1. 支持文本
|
|
// 2. 支持文件
|
|
|
|
func simple_test() {
|
|
// mail_driver := "smtp"
|
|
// mail_host := "smtpdm-ap-southeast-1.aliyun.com"
|
|
// mail_port := ""
|
|
// mail_username := ""
|
|
// mail_password := ""
|
|
// mail_From_address := ""
|
|
// mail_from_name := ""
|
|
// mail_reply_to := ""
|
|
|
|
// user := "tech@email.blueoceantech.co"
|
|
// password := "SupporT2017"
|
|
// host := "smtpdm-ap-southeast-1.aliyun.com"
|
|
// port := "80" // 80或smtp
|
|
// auth := smtp.PlainAuth("", user, password, host)
|
|
// toEmial := []string{
|
|
// "995116474@qq.com",
|
|
// "yun@blueoceanpay.com",
|
|
// }
|
|
// // split := strings.Split()
|
|
// emailHeader := "Header"
|
|
// subject := "邮件的主题"
|
|
// contentType := "Content-Type: text/html; charset=UTF-8"
|
|
// // contentType := "Content-Type: text/plain; charset=UTF-8"
|
|
// body := `<html><body> <h1>黄新云</h1> <span>666</span></body></html>`
|
|
// msg := []byte(contentType + "\r\nTo: " + strings.Join(toEmial, ",") + "\r\nFrom: " + emailHeader + "<" + user + ">\r\nSubject: " + subject + "\r\nBcc: yun@blueoceanpay.com \r\nReply-To: yun@blueoceanpay.com" + "\r\n\r\n" + body)
|
|
// err := smtp.SendMail(host+":"+port, auth, user, toEmial, msg)
|
|
// fmt.Println(err)
|
|
|
|
}
|
|
|
|
// type Mail interface {
|
|
// Auth()
|
|
// Send(message Message) error
|
|
// }
|
|
|
|
type Mailx struct {
|
|
user string
|
|
password string
|
|
host string
|
|
port string
|
|
auth smtp.Auth
|
|
}
|
|
|
|
type Attachment struct {
|
|
Name string
|
|
ContentType string
|
|
WithFile bool
|
|
}
|
|
|
|
type Message struct {
|
|
// Form string
|
|
To []string
|
|
Cc []string
|
|
Bcc []string
|
|
Subject string
|
|
Body string
|
|
// ContentType string
|
|
ReplyTo string
|
|
Attachment []Attachment
|
|
}
|
|
|
|
func NewMailx(user, password, host, port string) *Mailx {
|
|
m := &Mailx{
|
|
user: user,
|
|
password: password,
|
|
host: host,
|
|
port: port,
|
|
}
|
|
m.auth = smtp.PlainAuth("", user, password, host)
|
|
return m
|
|
}
|
|
|
|
func (m *Mailx) Send(message Message) error {
|
|
// .Auth()
|
|
buffer := bytes.NewBuffer(nil)
|
|
boundary := "YunBoundaryYun"
|
|
|
|
Header := make(map[string]string)
|
|
// Header["From"] = "BOP<" + message.Form + ">"
|
|
Header["From"] = m.user
|
|
|
|
if len(message.To) > 0 {
|
|
str := ""
|
|
for _, val := range message.To {
|
|
name := ""
|
|
s := strings.Split(val, "@")
|
|
if len(s) > 0 {
|
|
name = s[0]
|
|
}
|
|
str = str + "," + name + "<" + val + ">"
|
|
}
|
|
Header["To"] = strings.Trim(str, ",")
|
|
// Header["To"] = strings.Join(message.To, ",")
|
|
}
|
|
if len(message.Cc) > 0 {
|
|
str := ""
|
|
for _, val := range message.Cc {
|
|
name := ""
|
|
s := strings.Split(val, "@")
|
|
if len(s) > 0 {
|
|
name = s[0]
|
|
}
|
|
str = str + "," + name + "<" + val + ">"
|
|
}
|
|
Header["Cc"] = strings.Trim(str, ",")
|
|
// Header["Cc"] = strings.Join(message.Cc, ",")
|
|
}
|
|
if len(message.Bcc) > 0 {
|
|
str := ""
|
|
for _, val := range message.Bcc {
|
|
name := ""
|
|
s := strings.Split(val, "@")
|
|
if len(s) > 0 {
|
|
name = s[0]
|
|
}
|
|
str = str + "," + name + "<" + val + ">"
|
|
}
|
|
Header["Bcc"] = strings.Trim(str, ",")
|
|
// Header["Bcc"] = strings.Join(message.Bcc, ",")
|
|
}
|
|
|
|
Header["Subject"] = message.Subject
|
|
Header["Content-Type"] = "multipart/mixed; charset=UTF-8; boundary=" + boundary
|
|
Header["Date"] = time.Now().String()
|
|
Header["Reply-To"] = message.ReplyTo
|
|
|
|
Header["X-Priority"] = "3"
|
|
m.writeHeader(buffer, Header)
|
|
|
|
body := "--" + boundary + "\r\n"
|
|
// body += "Content-Type: text/plain; charset=UTF-8 \r\n"
|
|
body += "Content-Type: text/html;charset=utf-8\r\n"
|
|
body += "Content-Transfer-Encoding:quoted-printable\r\n\r\n"
|
|
// body += "<html><body><h1>huang</h1><h2>xin</h2></body></html>\r\n"
|
|
body += "<html><body>" + message.Body + "</body></html>\r\n"
|
|
// body += "--" + boundary + "--\r\n\r\n"
|
|
buffer.WriteString(body)
|
|
|
|
for _, value := range message.Attachment {
|
|
newBuf := bytes.NewBuffer(nil)
|
|
err := m.writeFile(newBuf, value.Name)
|
|
if err != nil {
|
|
fmt.Println("file err:", err)
|
|
continue
|
|
}
|
|
|
|
f_name := path.Base(value.Name)
|
|
attachment := "--" + boundary + "\r\n"
|
|
attachment += "Content-Transfer-Encoding:base64\r\n"
|
|
attachment += "Content-Disposition:attachment;filename=" + f_name + "\r\n"
|
|
attachment += "Content-Type: application/octet-stream;charset=utf-8;name=" + f_name + "\r\n"
|
|
// attachment += "Contment-Type:" + message.attachment.contentType + ";name=\"" + message.attachment.name + "\"\r\n"
|
|
buffer.WriteString(attachment)
|
|
|
|
buffer.WriteString(newBuf.String())
|
|
}
|
|
|
|
buffer.WriteString("\r\n--" + boundary + "--\r\n")
|
|
b := buffer.Bytes()
|
|
err := smtp.SendMail(m.host+":"+m.port, m.auth, m.user, message.To, b)
|
|
fmt.Println("发送结束:", err)
|
|
fmt.Println(string(b))
|
|
return err
|
|
}
|
|
|
|
// 格式化header
|
|
func (m *Mailx) writeHeader(buffer *bytes.Buffer, Header map[string]string) string {
|
|
header := ""
|
|
// header := "Content-Type: multipart/mixed;charset=UTF-8;boundary=\"YunBoundaryYun\" \r\n"
|
|
for key, value := range Header {
|
|
if value != "" {
|
|
header += key + ": " + value + "\r\n"
|
|
}
|
|
}
|
|
header += "\r\n"
|
|
buffer.WriteString(header)
|
|
return header
|
|
}
|
|
|
|
// 格式化文件
|
|
func (m *Mailx) writeFile(buffer *bytes.Buffer, fileName string) error {
|
|
file, err := os.ReadFile(fileName)
|
|
if err != nil {
|
|
return err
|
|
}
|
|
payload := make([]byte, base64.StdEncoding.EncodedLen(len(file)))
|
|
base64.StdEncoding.Encode(payload, file)
|
|
buffer.WriteString("\r\n")
|
|
for index, line := 0, len(payload); index < line; index++ {
|
|
buffer.WriteByte(payload[index])
|
|
if (index+1)%76 == 0 {
|
|
buffer.WriteString("\r\n")
|
|
}
|
|
}
|
|
return nil
|
|
}
|