micro-account/pkg/infrsatructure/external/mail/webmail_account.go
2025-02-20 16:18:23 +08:00

332 lines
6.7 KiB
Go
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

package mail
import (
"crypto/tls"
"errors"
"fmt"
"github.com/PuerkitoBio/goquery"
"io"
"log"
"net/http"
"net/http/cookiejar"
"net/url"
"strings"
"time"
)
const (
//LoginSuccessUrl = "https://mail.fontree.cn/iredadmin/dashboard?checknew" //登录后的重定向地址
CreateUrl = "http://106.12.56.142/admin/box/new?new=true"
LoginUrl = "http://106.12.56.142/admin/login"
)
type iredCookie struct {
Cookie string
Name string
ExpireAt *time.Time
}
type IRedMail struct {
IsProd bool `json:"isProd"`
Username string `json:"username"`
Password string `json:"password"`
Domain string
*iredCookie
}
type CreateAccountInfo struct {
Username string
Password string
Cn string
}
var ReadMail *IRedMail
func LoadEnv(userName, psw, domain string, isProd bool) {
ReadMail = &IRedMail{
IsProd: isProd,
Username: userName,
Password: psw,
Domain: domain,
}
}
//CreateMailAccount 创建电子邮箱账号
func (m *IRedMail) CreateMailAccount(new CreateAccountInfo) error {
if m.IsProd != true {
fmt.Println("过滤创建邮箱帐号")
return nil
}
//0 登陆
cookies, err := m.login()
if err != nil {
return err
}
/*
//1 先去解析csrf_token
csrfToken, err := m.getCsrfTokenBeforeAdd()
if err != nil {
return err
}
fmt.Println(csrfToken, err)
*/
//1 先去解析csrf_token
err = m.createAccount(cookies, new)
if err != nil {
return err
}
return nil
}
// login 登陆超管
func (m *IRedMail) login() ([]*http.Cookie, error) {
cookies, csrfToken, err := m.getCsrfTokenAndCookieBeforeLogin()
if err != nil {
return nil, err
}
fmt.Println(cookies, csrfToken)
loginUrl := LoginUrl
values := url.Values{}
values.Set("email", m.Username)
values.Set("password", m.Password)
values.Set("_csrf_token", csrfToken)
// 忽略HTTPS证书验证
tr := &http.Transport{
TLSClientConfig: &tls.Config{InsecureSkipVerify: true},
}
tempCookieJar, _ := cookiejar.New(nil)
u, err := url.Parse("http://106.12.56.142")
if err != nil {
log.Fatal(err)
return nil, err
}
tempCookieJar.SetCookies(u, cookies)
// 创建一个自定义Transport的HTTP客户端
//client := &http.Client{Transport: tr, Jar:cookies }
client := &http.Client{Transport: tr, Jar: tempCookieJar}
// 发起POST请求
res, err := client.PostForm(loginUrl, values)
if err != nil {
log.Fatal(err)
return nil, err
}
// 发送请求
defer res.Body.Close()
//fmt.Println(res.)
str, err := io.ReadAll(res.Body)
if err != nil {
return nil, err
}
fmt.Println("成功")
fmt.Println(string(str))
/*
if res.Request.URL.String() != LoginSuccessUrl {
msg := res.Request.URL.Query().Get("msg")
return errors.New("超管登录失败提示:" + msg)
}
*/
/*
for _, cookie := range res.Cookies() {
temp := &iredCookie{
Cookie: cookie.Value,
Name: cookie.Name,
}
m.iredCookie = temp
}
*/
return res.Cookies(), nil
}
// getCsrfTokenAndCookieBeforeLogin 登陆前获取token
func (m *IRedMail) getCsrfTokenAndCookieBeforeLogin() ([]*http.Cookie, string, error) {
var csrfToken string
var isExist bool
cookieJar, _ := cookiejar.New(nil)
tr := &http.Transport{
TLSClientConfig: &tls.Config{InsecureSkipVerify: true},
}
// 创建一个HTTP客户端并设置cookie jar
client := &http.Client{
Jar: cookieJar,
Transport: tr,
}
// 创建登录请求
loginURL := LoginUrl
req, err := http.NewRequest("GET", loginURL, nil)
if err != nil {
fmt.Println("创建请求失败:", err)
return nil, "", err
}
// 发送登录请求
res, err := client.Do(req)
if err != nil {
fmt.Println("请求错误", loginURL, err)
return nil, "", err
}
defer res.Body.Close()
if err != nil {
return nil, "", err
}
str, err := io.ReadAll(res.Body)
if err != nil {
return nil, "", err
}
// 解析HTML
doc, err := goquery.NewDocumentFromReader(strings.NewReader(string(str)))
if err != nil {
return nil, "", err
}
doc.Find("input[name='_csrf_token']").Each(func(i int, s *goquery.Selection) {
csrfToken, isExist = s.Attr("value")
fmt.Println("查找1---", csrfToken, isExist) // 输出: testUser
})
if isExist == false {
return nil, "", errors.New("没有查找到csrf_token")
}
return res.Cookies(), csrfToken, nil
}
// getCsrfTokenBeforeAdd 登陆前获取token
func (m *IRedMail) getCsrfTokenBeforeAdd() (string, error) {
var csrfToken string
var isExist bool
cookieJar, _ := cookiejar.New(nil)
tr := &http.Transport{
TLSClientConfig: &tls.Config{InsecureSkipVerify: true},
}
// 创建一个HTTP客户端并设置cookie jar
client := &http.Client{
Jar: cookieJar,
Transport: tr,
}
// 创建登录请求
loginURL := CreateUrl + m.Domain
req, err := http.NewRequest("GET", loginURL, nil)
if err != nil {
fmt.Println("创建请求失败:", err)
return "", err
}
// 向请求中添加cookie
cookie := &http.Cookie{
Name: m.iredCookie.Name,
Value: m.iredCookie.Cookie,
}
req.AddCookie(cookie)
// 发送登录请求
res, err := client.Do(req)
if err != nil {
fmt.Println("请求错误", loginURL, err)
return "", err
}
defer res.Body.Close()
if err != nil {
return "", err
}
str, err := io.ReadAll(res.Body)
if err != nil {
return "", err
}
// 解析HTML
doc, err := goquery.NewDocumentFromReader(strings.NewReader(string(str)))
if err != nil {
return "", err
}
doc.Find("input[name='csrf_token']").Each(func(i int, s *goquery.Selection) {
csrfToken, isExist = s.Attr("value")
fmt.Println("查找1---", csrfToken, isExist) // 输出: testUser
})
if isExist == false {
return "", errors.New("没有查找到csrf_token")
}
return csrfToken, nil
}
// createAccount 创建用户mail
func (m *IRedMail) createAccount(cookies []*http.Cookie, info CreateAccountInfo) error {
cookieJar, _ := cookiejar.New(nil)
values := url.Values{}
values.Set("name", info.Cn)
values.Set("user", info.Username)
values.Set("domain", m.Domain)
values.Set("passwordPlaintext", info.Password)
tr := &http.Transport{
TLSClientConfig: &tls.Config{InsecureSkipVerify: true},
}
u, err := url.Parse("http://106.12.56.142")
if err != nil {
log.Fatal(err)
return err
}
cookieJar.SetCookies(u, cookies)
// 创建一个HTTP客户端并设置cookie jar
client := &http.Client{
Jar: cookieJar,
Transport: tr,
//CheckRedirect:
}
// 创建登录请求
loginURL := CreateUrl
req, err := http.NewRequest("POST", loginURL, strings.NewReader(values.Encode()))
if err != nil {
fmt.Println("创建请求失败:", err)
return err
}
req.Header.Set("content-type", "application/x-www-form-urlencoded")
// 发送登录请求
res, err := client.Do(req)
if err != nil {
fmt.Println("请求错误", loginURL, err)
return err
}
defer res.Body.Close()
fmt.Println("状态码", res.StatusCode)
fmt.Println("状态码", res.Status)
return nil
}