mirror of
				https://github.com/TeaOSLab/EdgeAPI.git
				synced 2025-11-04 16:00:24 +08:00 
			
		
		
		
	ACME申请证书时可以设置回调URL
This commit is contained in:
		@@ -39,7 +39,7 @@ func TestRequest_Run_DNS(t *testing.T) {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
	req := NewRequest(&Task{
 | 
						req := NewRequest(&Task{
 | 
				
			||||||
		User:        user,
 | 
							User:        user,
 | 
				
			||||||
		Type:        TaskTypeDNS,
 | 
							AuthType:    AuthTypeDNS,
 | 
				
			||||||
		DNSProvider: dnsProvider,
 | 
							DNSProvider: dnsProvider,
 | 
				
			||||||
		DNSDomain:   "yun4s.cn",
 | 
							DNSDomain:   "yun4s.cn",
 | 
				
			||||||
		Domains:     []string{"yun4s.cn"},
 | 
							Domains:     []string{"yun4s.cn"},
 | 
				
			||||||
@@ -74,9 +74,9 @@ func TestRequest_Run_HTTP(t *testing.T) {
 | 
				
			|||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	req := NewRequest(&Task{
 | 
						req := NewRequest(&Task{
 | 
				
			||||||
		User:    user,
 | 
							User:     user,
 | 
				
			||||||
		Type:    TaskTypeHTTP,
 | 
							AuthType: AuthTypeHTTP,
 | 
				
			||||||
		Domains: []string{"teaos.cn", "www.teaos.cn", "meloy.cn"},
 | 
							Domains:  []string{"teaos.cn", "www.teaos.cn", "meloy.cn"},
 | 
				
			||||||
	})
 | 
						})
 | 
				
			||||||
	certData, keyData, err := req.runHTTP()
 | 
						certData, keyData, err := req.runHTTP()
 | 
				
			||||||
	if err != nil {
 | 
						if err != nil {
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -1,6 +1,7 @@
 | 
				
			|||||||
package acme
 | 
					package acme
 | 
				
			||||||
 | 
					
 | 
				
			||||||
import (
 | 
					import (
 | 
				
			||||||
 | 
						"bytes"
 | 
				
			||||||
	"encoding/json"
 | 
						"encoding/json"
 | 
				
			||||||
	"github.com/TeaOSLab/EdgeAPI/internal/acme"
 | 
						"github.com/TeaOSLab/EdgeAPI/internal/acme"
 | 
				
			||||||
	"github.com/TeaOSLab/EdgeAPI/internal/db/models"
 | 
						"github.com/TeaOSLab/EdgeAPI/internal/db/models"
 | 
				
			||||||
@@ -8,13 +9,17 @@ import (
 | 
				
			|||||||
	dbutils "github.com/TeaOSLab/EdgeAPI/internal/db/utils"
 | 
						dbutils "github.com/TeaOSLab/EdgeAPI/internal/db/utils"
 | 
				
			||||||
	"github.com/TeaOSLab/EdgeAPI/internal/dnsclients"
 | 
						"github.com/TeaOSLab/EdgeAPI/internal/dnsclients"
 | 
				
			||||||
	"github.com/TeaOSLab/EdgeAPI/internal/errors"
 | 
						"github.com/TeaOSLab/EdgeAPI/internal/errors"
 | 
				
			||||||
 | 
						"github.com/TeaOSLab/EdgeAPI/internal/remotelogs"
 | 
				
			||||||
 | 
						"github.com/TeaOSLab/EdgeAPI/internal/utils"
 | 
				
			||||||
	"github.com/TeaOSLab/EdgeCommon/pkg/serverconfigs/sslconfigs"
 | 
						"github.com/TeaOSLab/EdgeCommon/pkg/serverconfigs/sslconfigs"
 | 
				
			||||||
	"github.com/go-acme/lego/v4/registration"
 | 
						"github.com/go-acme/lego/v4/registration"
 | 
				
			||||||
	_ "github.com/go-sql-driver/mysql"
 | 
						_ "github.com/go-sql-driver/mysql"
 | 
				
			||||||
	"github.com/iwind/TeaGo/Tea"
 | 
						"github.com/iwind/TeaGo/Tea"
 | 
				
			||||||
	"github.com/iwind/TeaGo/dbs"
 | 
						"github.com/iwind/TeaGo/dbs"
 | 
				
			||||||
	"github.com/iwind/TeaGo/logs"
 | 
						"github.com/iwind/TeaGo/logs"
 | 
				
			||||||
 | 
						"github.com/iwind/TeaGo/maps"
 | 
				
			||||||
	"github.com/iwind/TeaGo/types"
 | 
						"github.com/iwind/TeaGo/types"
 | 
				
			||||||
 | 
						"net/http"
 | 
				
			||||||
	"time"
 | 
						"time"
 | 
				
			||||||
)
 | 
					)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@@ -44,7 +49,7 @@ func init() {
 | 
				
			|||||||
	})
 | 
						})
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// 启用条目
 | 
					// EnableACMETask 启用条目
 | 
				
			||||||
func (this *ACMETaskDAO) EnableACMETask(tx *dbs.Tx, id int64) error {
 | 
					func (this *ACMETaskDAO) EnableACMETask(tx *dbs.Tx, id int64) error {
 | 
				
			||||||
	_, err := this.Query(tx).
 | 
						_, err := this.Query(tx).
 | 
				
			||||||
		Pk(id).
 | 
							Pk(id).
 | 
				
			||||||
@@ -53,7 +58,7 @@ func (this *ACMETaskDAO) EnableACMETask(tx *dbs.Tx, id int64) error {
 | 
				
			|||||||
	return err
 | 
						return err
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// 禁用条目
 | 
					// DisableACMETask 禁用条目
 | 
				
			||||||
func (this *ACMETaskDAO) DisableACMETask(tx *dbs.Tx, id int64) error {
 | 
					func (this *ACMETaskDAO) DisableACMETask(tx *dbs.Tx, id int64) error {
 | 
				
			||||||
	_, err := this.Query(tx).
 | 
						_, err := this.Query(tx).
 | 
				
			||||||
		Pk(id).
 | 
							Pk(id).
 | 
				
			||||||
@@ -62,7 +67,7 @@ func (this *ACMETaskDAO) DisableACMETask(tx *dbs.Tx, id int64) error {
 | 
				
			|||||||
	return err
 | 
						return err
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// 查找启用中的条目
 | 
					// FindEnabledACMETask 查找启用中的条目
 | 
				
			||||||
func (this *ACMETaskDAO) FindEnabledACMETask(tx *dbs.Tx, id int64) (*ACMETask, error) {
 | 
					func (this *ACMETaskDAO) FindEnabledACMETask(tx *dbs.Tx, id int64) (*ACMETask, error) {
 | 
				
			||||||
	result, err := this.Query(tx).
 | 
						result, err := this.Query(tx).
 | 
				
			||||||
		Pk(id).
 | 
							Pk(id).
 | 
				
			||||||
@@ -74,7 +79,7 @@ func (this *ACMETaskDAO) FindEnabledACMETask(tx *dbs.Tx, id int64) (*ACMETask, e
 | 
				
			|||||||
	return result.(*ACMETask), err
 | 
						return result.(*ACMETask), err
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// 计算某个ACME用户相关的任务数量
 | 
					// CountACMETasksWithACMEUserId 计算某个ACME用户相关的任务数量
 | 
				
			||||||
func (this *ACMETaskDAO) CountACMETasksWithACMEUserId(tx *dbs.Tx, acmeUserId int64) (int64, error) {
 | 
					func (this *ACMETaskDAO) CountACMETasksWithACMEUserId(tx *dbs.Tx, acmeUserId int64) (int64, error) {
 | 
				
			||||||
	return this.Query(tx).
 | 
						return this.Query(tx).
 | 
				
			||||||
		State(ACMETaskStateEnabled).
 | 
							State(ACMETaskStateEnabled).
 | 
				
			||||||
@@ -82,7 +87,7 @@ func (this *ACMETaskDAO) CountACMETasksWithACMEUserId(tx *dbs.Tx, acmeUserId int
 | 
				
			|||||||
		Count()
 | 
							Count()
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// 计算某个DNS服务商相关的任务数量
 | 
					// CountACMETasksWithDNSProviderId 计算某个DNS服务商相关的任务数量
 | 
				
			||||||
func (this *ACMETaskDAO) CountACMETasksWithDNSProviderId(tx *dbs.Tx, dnsProviderId int64) (int64, error) {
 | 
					func (this *ACMETaskDAO) CountACMETasksWithDNSProviderId(tx *dbs.Tx, dnsProviderId int64) (int64, error) {
 | 
				
			||||||
	return this.Query(tx).
 | 
						return this.Query(tx).
 | 
				
			||||||
		State(ACMETaskStateEnabled).
 | 
							State(ACMETaskStateEnabled).
 | 
				
			||||||
@@ -90,7 +95,7 @@ func (this *ACMETaskDAO) CountACMETasksWithDNSProviderId(tx *dbs.Tx, dnsProvider
 | 
				
			|||||||
		Count()
 | 
							Count()
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// 停止某个证书相关任务
 | 
					// DisableAllTasksWithCertId 停止某个证书相关任务
 | 
				
			||||||
func (this *ACMETaskDAO) DisableAllTasksWithCertId(tx *dbs.Tx, certId int64) error {
 | 
					func (this *ACMETaskDAO) DisableAllTasksWithCertId(tx *dbs.Tx, certId int64) error {
 | 
				
			||||||
	_, err := this.Query(tx).
 | 
						_, err := this.Query(tx).
 | 
				
			||||||
		Attr("certId", certId).
 | 
							Attr("certId", certId).
 | 
				
			||||||
@@ -99,7 +104,7 @@ func (this *ACMETaskDAO) DisableAllTasksWithCertId(tx *dbs.Tx, certId int64) err
 | 
				
			|||||||
	return err
 | 
						return err
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// 计算所有任务数量
 | 
					// CountAllEnabledACMETasks 计算所有任务数量
 | 
				
			||||||
func (this *ACMETaskDAO) CountAllEnabledACMETasks(tx *dbs.Tx, adminId int64, userId int64, isAvailable bool, isExpired bool, expiringDays int64, keyword string) (int64, error) {
 | 
					func (this *ACMETaskDAO) CountAllEnabledACMETasks(tx *dbs.Tx, adminId int64, userId int64, isAvailable bool, isExpired bool, expiringDays int64, keyword string) (int64, error) {
 | 
				
			||||||
	query := dbutils.NewQuery(tx, this, adminId, userId)
 | 
						query := dbutils.NewQuery(tx, this, adminId, userId)
 | 
				
			||||||
	if isAvailable || isExpired || expiringDays > 0 {
 | 
						if isAvailable || isExpired || expiringDays > 0 {
 | 
				
			||||||
@@ -130,7 +135,7 @@ func (this *ACMETaskDAO) CountAllEnabledACMETasks(tx *dbs.Tx, adminId int64, use
 | 
				
			|||||||
		Count()
 | 
							Count()
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// 列出单页任务
 | 
					// ListEnabledACMETasks 列出单页任务
 | 
				
			||||||
func (this *ACMETaskDAO) ListEnabledACMETasks(tx *dbs.Tx, adminId int64, userId int64, isAvailable bool, isExpired bool, expiringDays int64, keyword string, offset int64, size int64) (result []*ACMETask, err error) {
 | 
					func (this *ACMETaskDAO) ListEnabledACMETasks(tx *dbs.Tx, adminId int64, userId int64, isAvailable bool, isExpired bool, expiringDays int64, keyword string, offset int64, size int64) (result []*ACMETask, err error) {
 | 
				
			||||||
	query := dbutils.NewQuery(tx, this, adminId, userId)
 | 
						query := dbutils.NewQuery(tx, this, adminId, userId)
 | 
				
			||||||
	if isAvailable || isExpired || expiringDays > 0 {
 | 
						if isAvailable || isExpired || expiringDays > 0 {
 | 
				
			||||||
@@ -161,8 +166,8 @@ func (this *ACMETaskDAO) ListEnabledACMETasks(tx *dbs.Tx, adminId int64, userId
 | 
				
			|||||||
	return
 | 
						return
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// 创建任务
 | 
					// CreateACMETask 创建任务
 | 
				
			||||||
func (this *ACMETaskDAO) CreateACMETask(tx *dbs.Tx, adminId int64, userId int64, authType acme.AuthType, acmeUserId int64, dnsProviderId int64, dnsDomain string, domains []string, autoRenew bool) (int64, error) {
 | 
					func (this *ACMETaskDAO) CreateACMETask(tx *dbs.Tx, adminId int64, userId int64, authType acme.AuthType, acmeUserId int64, dnsProviderId int64, dnsDomain string, domains []string, autoRenew bool, authURL string) (int64, error) {
 | 
				
			||||||
	op := NewACMETaskOperator()
 | 
						op := NewACMETaskOperator()
 | 
				
			||||||
	op.AdminId = adminId
 | 
						op.AdminId = adminId
 | 
				
			||||||
	op.UserId = userId
 | 
						op.UserId = userId
 | 
				
			||||||
@@ -182,6 +187,7 @@ func (this *ACMETaskDAO) CreateACMETask(tx *dbs.Tx, adminId int64, userId int64,
 | 
				
			|||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	op.AutoRenew = autoRenew
 | 
						op.AutoRenew = autoRenew
 | 
				
			||||||
 | 
						op.AuthURL = authURL
 | 
				
			||||||
	op.IsOn = true
 | 
						op.IsOn = true
 | 
				
			||||||
	op.State = ACMETaskStateEnabled
 | 
						op.State = ACMETaskStateEnabled
 | 
				
			||||||
	err := this.Save(tx, op)
 | 
						err := this.Save(tx, op)
 | 
				
			||||||
@@ -191,8 +197,8 @@ func (this *ACMETaskDAO) CreateACMETask(tx *dbs.Tx, adminId int64, userId int64,
 | 
				
			|||||||
	return types.Int64(op.Id), nil
 | 
						return types.Int64(op.Id), nil
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// 修改任务
 | 
					// UpdateACMETask 修改任务
 | 
				
			||||||
func (this *ACMETaskDAO) UpdateACMETask(tx *dbs.Tx, acmeTaskId int64, acmeUserId int64, dnsProviderId int64, dnsDomain string, domains []string, autoRenew bool) error {
 | 
					func (this *ACMETaskDAO) UpdateACMETask(tx *dbs.Tx, acmeTaskId int64, acmeUserId int64, dnsProviderId int64, dnsDomain string, domains []string, autoRenew bool, authURL string) error {
 | 
				
			||||||
	if acmeTaskId <= 0 {
 | 
						if acmeTaskId <= 0 {
 | 
				
			||||||
		return errors.New("invalid acmeTaskId")
 | 
							return errors.New("invalid acmeTaskId")
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
@@ -214,11 +220,12 @@ func (this *ACMETaskDAO) UpdateACMETask(tx *dbs.Tx, acmeTaskId int64, acmeUserId
 | 
				
			|||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	op.AutoRenew = autoRenew
 | 
						op.AutoRenew = autoRenew
 | 
				
			||||||
 | 
						op.AuthURL = authURL
 | 
				
			||||||
	err := this.Save(tx, op)
 | 
						err := this.Save(tx, op)
 | 
				
			||||||
	return err
 | 
						return err
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// 检查权限
 | 
					// CheckACMETask 检查权限
 | 
				
			||||||
func (this *ACMETaskDAO) CheckACMETask(tx *dbs.Tx, adminId int64, userId int64, acmeTaskId int64) (bool, error) {
 | 
					func (this *ACMETaskDAO) CheckACMETask(tx *dbs.Tx, adminId int64, userId int64, acmeTaskId int64) (bool, error) {
 | 
				
			||||||
	return dbutils.NewQuery(tx, this, adminId, userId).
 | 
						return dbutils.NewQuery(tx, this, adminId, userId).
 | 
				
			||||||
		State(ACMETaskStateEnabled).
 | 
							State(ACMETaskStateEnabled).
 | 
				
			||||||
@@ -226,7 +233,7 @@ func (this *ACMETaskDAO) CheckACMETask(tx *dbs.Tx, adminId int64, userId int64,
 | 
				
			|||||||
		Exist()
 | 
							Exist()
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// 设置任务关联的证书
 | 
					// UpdateACMETaskCert 设置任务关联的证书
 | 
				
			||||||
func (this *ACMETaskDAO) UpdateACMETaskCert(tx *dbs.Tx, taskId int64, certId int64) error {
 | 
					func (this *ACMETaskDAO) UpdateACMETaskCert(tx *dbs.Tx, taskId int64, certId int64) error {
 | 
				
			||||||
	if taskId <= 0 {
 | 
						if taskId <= 0 {
 | 
				
			||||||
		return errors.New("invalid taskId")
 | 
							return errors.New("invalid taskId")
 | 
				
			||||||
@@ -239,7 +246,7 @@ func (this *ACMETaskDAO) UpdateACMETaskCert(tx *dbs.Tx, taskId int64, certId int
 | 
				
			|||||||
	return err
 | 
						return err
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// 执行任务并记录日志
 | 
					// RunTask 执行任务并记录日志
 | 
				
			||||||
func (this *ACMETaskDAO) RunTask(tx *dbs.Tx, taskId int64) (isOk bool, errMsg string, resultCertId int64) {
 | 
					func (this *ACMETaskDAO) RunTask(tx *dbs.Tx, taskId int64) (isOk bool, errMsg string, resultCertId int64) {
 | 
				
			||||||
	isOk, errMsg, resultCertId = this.runTaskWithoutLog(tx, taskId)
 | 
						isOk, errMsg, resultCertId = this.runTaskWithoutLog(tx, taskId)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@@ -350,7 +357,33 @@ func (this *ACMETaskDAO) runTaskWithoutLog(tx *dbs.Tx, taskId int64) (isOk bool,
 | 
				
			|||||||
	acmeRequest.OnAuth(func(domain, token, keyAuth string) {
 | 
						acmeRequest.OnAuth(func(domain, token, keyAuth string) {
 | 
				
			||||||
		err := SharedACMEAuthenticationDAO.CreateAuth(tx, taskId, domain, token, keyAuth)
 | 
							err := SharedACMEAuthenticationDAO.CreateAuth(tx, taskId, domain, token, keyAuth)
 | 
				
			||||||
		if err != nil {
 | 
							if err != nil {
 | 
				
			||||||
			logs.Println("[ACME]write authentication to database error: " + err.Error())
 | 
								remotelogs.Error("ACME", "write authentication to database error: "+err.Error())
 | 
				
			||||||
 | 
							} else {
 | 
				
			||||||
 | 
								// 调用校验URL
 | 
				
			||||||
 | 
								if len(task.AuthURL) > 0 {
 | 
				
			||||||
 | 
									authJSON, err := json.Marshal(maps.Map{
 | 
				
			||||||
 | 
										"domain": domain,
 | 
				
			||||||
 | 
										"token":  token,
 | 
				
			||||||
 | 
										"key":    keyAuth,
 | 
				
			||||||
 | 
									})
 | 
				
			||||||
 | 
									if err != nil {
 | 
				
			||||||
 | 
										remotelogs.Error("ACME", "encode auth data failed: '"+task.AuthURL+"'")
 | 
				
			||||||
 | 
									} else {
 | 
				
			||||||
 | 
										client := utils.SharedHttpClient(5 * time.Second)
 | 
				
			||||||
 | 
										req, err := http.NewRequest(http.MethodPost, task.AuthURL, bytes.NewReader(authJSON))
 | 
				
			||||||
 | 
										req.Header.Set("Content-Type", "application/json")
 | 
				
			||||||
 | 
										if err != nil {
 | 
				
			||||||
 | 
											remotelogs.Error("ACME", "parse auth url failed '"+task.AuthURL+"': "+err.Error())
 | 
				
			||||||
 | 
										} else {
 | 
				
			||||||
 | 
											resp, err := client.Do(req)
 | 
				
			||||||
 | 
											if err != nil {
 | 
				
			||||||
 | 
												remotelogs.Error("ACME", "call auth url failed '"+task.AuthURL+"': "+err.Error())
 | 
				
			||||||
 | 
											} else {
 | 
				
			||||||
 | 
												_ = resp.Body.Close()
 | 
				
			||||||
 | 
											}
 | 
				
			||||||
 | 
										}
 | 
				
			||||||
 | 
									}
 | 
				
			||||||
 | 
								}
 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
	})
 | 
						})
 | 
				
			||||||
	certData, keyData, err := acmeRequest.Run()
 | 
						certData, keyData, err := acmeRequest.Run()
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -1,6 +1,6 @@
 | 
				
			|||||||
package acme
 | 
					package acme
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// ACME任务
 | 
					// ACMETask ACME任务
 | 
				
			||||||
type ACMETask struct {
 | 
					type ACMETask struct {
 | 
				
			||||||
	Id            uint64 `field:"id"`            // ID
 | 
						Id            uint64 `field:"id"`            // ID
 | 
				
			||||||
	AdminId       uint32 `field:"adminId"`       // 管理员ID
 | 
						AdminId       uint32 `field:"adminId"`       // 管理员ID
 | 
				
			||||||
@@ -15,6 +15,7 @@ type ACMETask struct {
 | 
				
			|||||||
	CertId        uint64 `field:"certId"`        // 生成的证书ID
 | 
						CertId        uint64 `field:"certId"`        // 生成的证书ID
 | 
				
			||||||
	AutoRenew     uint8  `field:"autoRenew"`     // 是否自动更新
 | 
						AutoRenew     uint8  `field:"autoRenew"`     // 是否自动更新
 | 
				
			||||||
	AuthType      string `field:"authType"`      // 认证类型
 | 
						AuthType      string `field:"authType"`      // 认证类型
 | 
				
			||||||
 | 
						AuthURL       string `field:"authURL"`       // 认证URL
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
type ACMETaskOperator struct {
 | 
					type ACMETaskOperator struct {
 | 
				
			||||||
@@ -31,6 +32,7 @@ type ACMETaskOperator struct {
 | 
				
			|||||||
	CertId        interface{} // 生成的证书ID
 | 
						CertId        interface{} // 生成的证书ID
 | 
				
			||||||
	AutoRenew     interface{} // 是否自动更新
 | 
						AutoRenew     interface{} // 是否自动更新
 | 
				
			||||||
	AuthType      interface{} // 认证类型
 | 
						AuthType      interface{} // 认证类型
 | 
				
			||||||
 | 
						AuthURL       interface{} // 认证URL
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
func NewACMETaskOperator() *ACMETaskOperator {
 | 
					func NewACMETaskOperator() *ACMETaskOperator {
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -10,12 +10,12 @@ import (
 | 
				
			|||||||
	"github.com/TeaOSLab/EdgeCommon/pkg/rpc/pb"
 | 
						"github.com/TeaOSLab/EdgeCommon/pkg/rpc/pb"
 | 
				
			||||||
)
 | 
					)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// ACME任务相关服务
 | 
					// ACMETaskService ACME任务相关服务
 | 
				
			||||||
type ACMETaskService struct {
 | 
					type ACMETaskService struct {
 | 
				
			||||||
	BaseService
 | 
						BaseService
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// 计算某个ACME用户相关的任务数量
 | 
					// CountAllEnabledACMETasksWithACMEUserId 计算某个ACME用户相关的任务数量
 | 
				
			||||||
func (this *ACMETaskService) CountAllEnabledACMETasksWithACMEUserId(ctx context.Context, req *pb.CountAllEnabledACMETasksWithACMEUserIdRequest) (*pb.RPCCountResponse, error) {
 | 
					func (this *ACMETaskService) CountAllEnabledACMETasksWithACMEUserId(ctx context.Context, req *pb.CountAllEnabledACMETasksWithACMEUserIdRequest) (*pb.RPCCountResponse, error) {
 | 
				
			||||||
	_, _, err := this.ValidateAdminAndUser(ctx, 0, 0)
 | 
						_, _, err := this.ValidateAdminAndUser(ctx, 0, 0)
 | 
				
			||||||
	if err != nil {
 | 
						if err != nil {
 | 
				
			||||||
@@ -33,7 +33,7 @@ func (this *ACMETaskService) CountAllEnabledACMETasksWithACMEUserId(ctx context.
 | 
				
			|||||||
	return this.SuccessCount(count)
 | 
						return this.SuccessCount(count)
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// 计算跟某个DNS服务商相关的任务数量
 | 
					// CountEnabledACMETasksWithDNSProviderId 计算跟某个DNS服务商相关的任务数量
 | 
				
			||||||
func (this *ACMETaskService) CountEnabledACMETasksWithDNSProviderId(ctx context.Context, req *pb.CountEnabledACMETasksWithDNSProviderIdRequest) (*pb.RPCCountResponse, error) {
 | 
					func (this *ACMETaskService) CountEnabledACMETasksWithDNSProviderId(ctx context.Context, req *pb.CountEnabledACMETasksWithDNSProviderIdRequest) (*pb.RPCCountResponse, error) {
 | 
				
			||||||
	_, _, err := this.ValidateAdminAndUser(ctx, 0, 0)
 | 
						_, _, err := this.ValidateAdminAndUser(ctx, 0, 0)
 | 
				
			||||||
	if err != nil {
 | 
						if err != nil {
 | 
				
			||||||
@@ -51,7 +51,7 @@ func (this *ACMETaskService) CountEnabledACMETasksWithDNSProviderId(ctx context.
 | 
				
			|||||||
	return this.SuccessCount(count)
 | 
						return this.SuccessCount(count)
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// 计算所有任务数量
 | 
					// CountAllEnabledACMETasks 计算所有任务数量
 | 
				
			||||||
func (this *ACMETaskService) CountAllEnabledACMETasks(ctx context.Context, req *pb.CountAllEnabledACMETasksRequest) (*pb.RPCCountResponse, error) {
 | 
					func (this *ACMETaskService) CountAllEnabledACMETasks(ctx context.Context, req *pb.CountAllEnabledACMETasksRequest) (*pb.RPCCountResponse, error) {
 | 
				
			||||||
	_, _, err := this.ValidateAdminAndUser(ctx, 0, req.UserId)
 | 
						_, _, err := this.ValidateAdminAndUser(ctx, 0, req.UserId)
 | 
				
			||||||
	if err != nil {
 | 
						if err != nil {
 | 
				
			||||||
@@ -67,7 +67,7 @@ func (this *ACMETaskService) CountAllEnabledACMETasks(ctx context.Context, req *
 | 
				
			|||||||
	return this.SuccessCount(count)
 | 
						return this.SuccessCount(count)
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// 列出单页任务
 | 
					// ListEnabledACMETasks 列出单页任务
 | 
				
			||||||
func (this *ACMETaskService) ListEnabledACMETasks(ctx context.Context, req *pb.ListEnabledACMETasksRequest) (*pb.ListEnabledACMETasksResponse, error) {
 | 
					func (this *ACMETaskService) ListEnabledACMETasks(ctx context.Context, req *pb.ListEnabledACMETasksRequest) (*pb.ListEnabledACMETasksResponse, error) {
 | 
				
			||||||
	_, _, err := this.ValidateAdminAndUser(ctx, 0, req.UserId)
 | 
						_, _, err := this.ValidateAdminAndUser(ctx, 0, req.UserId)
 | 
				
			||||||
	if err != nil {
 | 
						if err != nil {
 | 
				
			||||||
@@ -162,13 +162,14 @@ func (this *ACMETaskService) ListEnabledACMETasks(ctx context.Context, req *pb.L
 | 
				
			|||||||
			SslCert:           pbCert,
 | 
								SslCert:           pbCert,
 | 
				
			||||||
			LatestACMETaskLog: pbTaskLog,
 | 
								LatestACMETaskLog: pbTaskLog,
 | 
				
			||||||
			AuthType:          task.AuthType,
 | 
								AuthType:          task.AuthType,
 | 
				
			||||||
 | 
								AuthURL:           task.AuthURL,
 | 
				
			||||||
		})
 | 
							})
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	return &pb.ListEnabledACMETasksResponse{AcmeTasks: result}, nil
 | 
						return &pb.ListEnabledACMETasksResponse{AcmeTasks: result}, nil
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// 创建任务
 | 
					// CreateACMETask 创建任务
 | 
				
			||||||
func (this *ACMETaskService) CreateACMETask(ctx context.Context, req *pb.CreateACMETaskRequest) (*pb.CreateACMETaskResponse, error) {
 | 
					func (this *ACMETaskService) CreateACMETask(ctx context.Context, req *pb.CreateACMETaskRequest) (*pb.CreateACMETaskResponse, error) {
 | 
				
			||||||
	adminId, userId, err := this.ValidateAdminAndUser(ctx, 0, 0)
 | 
						adminId, userId, err := this.ValidateAdminAndUser(ctx, 0, 0)
 | 
				
			||||||
	if err != nil {
 | 
						if err != nil {
 | 
				
			||||||
@@ -180,14 +181,14 @@ func (this *ACMETaskService) CreateACMETask(ctx context.Context, req *pb.CreateA
 | 
				
			|||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	tx := this.NullTx()
 | 
						tx := this.NullTx()
 | 
				
			||||||
	taskId, err := acmemodels.SharedACMETaskDAO.CreateACMETask(tx, adminId, userId, req.AuthType, req.AcmeUserId, req.DnsProviderId, req.DnsDomain, req.Domains, req.AutoRenew)
 | 
						taskId, err := acmemodels.SharedACMETaskDAO.CreateACMETask(tx, adminId, userId, req.AuthType, req.AcmeUserId, req.DnsProviderId, req.DnsDomain, req.Domains, req.AutoRenew, req.AuthURL)
 | 
				
			||||||
	if err != nil {
 | 
						if err != nil {
 | 
				
			||||||
		return nil, err
 | 
							return nil, err
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	return &pb.CreateACMETaskResponse{AcmeTaskId: taskId}, nil
 | 
						return &pb.CreateACMETaskResponse{AcmeTaskId: taskId}, nil
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// 修改任务
 | 
					// UpdateACMETask 修改任务
 | 
				
			||||||
func (this *ACMETaskService) UpdateACMETask(ctx context.Context, req *pb.UpdateACMETaskRequest) (*pb.RPCSuccess, error) {
 | 
					func (this *ACMETaskService) UpdateACMETask(ctx context.Context, req *pb.UpdateACMETaskRequest) (*pb.RPCSuccess, error) {
 | 
				
			||||||
	adminId, userId, err := this.ValidateAdminAndUser(ctx, 0, 0)
 | 
						adminId, userId, err := this.ValidateAdminAndUser(ctx, 0, 0)
 | 
				
			||||||
	if err != nil {
 | 
						if err != nil {
 | 
				
			||||||
@@ -204,14 +205,14 @@ func (this *ACMETaskService) UpdateACMETask(ctx context.Context, req *pb.UpdateA
 | 
				
			|||||||
		return nil, this.PermissionError()
 | 
							return nil, this.PermissionError()
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	err = acmemodels.SharedACMETaskDAO.UpdateACMETask(tx, req.AcmeTaskId, req.AcmeUserId, req.DnsProviderId, req.DnsDomain, req.Domains, req.AutoRenew)
 | 
						err = acmemodels.SharedACMETaskDAO.UpdateACMETask(tx, req.AcmeTaskId, req.AcmeUserId, req.DnsProviderId, req.DnsDomain, req.Domains, req.AutoRenew, req.AuthURL)
 | 
				
			||||||
	if err != nil {
 | 
						if err != nil {
 | 
				
			||||||
		return nil, err
 | 
							return nil, err
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	return this.Success()
 | 
						return this.Success()
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// 删除任务
 | 
					// DeleteACMETask 删除任务
 | 
				
			||||||
func (this *ACMETaskService) DeleteACMETask(ctx context.Context, req *pb.DeleteACMETaskRequest) (*pb.RPCSuccess, error) {
 | 
					func (this *ACMETaskService) DeleteACMETask(ctx context.Context, req *pb.DeleteACMETaskRequest) (*pb.RPCSuccess, error) {
 | 
				
			||||||
	adminId, userId, err := this.ValidateAdminAndUser(ctx, 0, 0)
 | 
						adminId, userId, err := this.ValidateAdminAndUser(ctx, 0, 0)
 | 
				
			||||||
	if err != nil {
 | 
						if err != nil {
 | 
				
			||||||
@@ -235,7 +236,7 @@ func (this *ACMETaskService) DeleteACMETask(ctx context.Context, req *pb.DeleteA
 | 
				
			|||||||
	return this.Success()
 | 
						return this.Success()
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// 运行某个任务
 | 
					// RunACMETask 运行某个任务
 | 
				
			||||||
func (this *ACMETaskService) RunACMETask(ctx context.Context, req *pb.RunACMETaskRequest) (*pb.RunACMETaskResponse, error) {
 | 
					func (this *ACMETaskService) RunACMETask(ctx context.Context, req *pb.RunACMETaskRequest) (*pb.RunACMETaskResponse, error) {
 | 
				
			||||||
	adminId, userId, err := this.ValidateAdminAndUser(ctx, 0, 0)
 | 
						adminId, userId, err := this.ValidateAdminAndUser(ctx, 0, 0)
 | 
				
			||||||
	if err != nil {
 | 
						if err != nil {
 | 
				
			||||||
@@ -261,7 +262,7 @@ func (this *ACMETaskService) RunACMETask(ctx context.Context, req *pb.RunACMETas
 | 
				
			|||||||
	}, nil
 | 
						}, nil
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// 查找单个任务信息
 | 
					// FindEnabledACMETask 查找单个任务信息
 | 
				
			||||||
func (this *ACMETaskService) FindEnabledACMETask(ctx context.Context, req *pb.FindEnabledACMETaskRequest) (*pb.FindEnabledACMETaskResponse, error) {
 | 
					func (this *ACMETaskService) FindEnabledACMETask(ctx context.Context, req *pb.FindEnabledACMETaskRequest) (*pb.FindEnabledACMETaskResponse, error) {
 | 
				
			||||||
	adminId, userId, err := this.ValidateAdminAndUser(ctx, 0, 0)
 | 
						adminId, userId, err := this.ValidateAdminAndUser(ctx, 0, 0)
 | 
				
			||||||
	if err != nil {
 | 
						if err != nil {
 | 
				
			||||||
@@ -328,5 +329,6 @@ func (this *ACMETaskService) FindEnabledACMETask(ctx context.Context, req *pb.Fi
 | 
				
			|||||||
		DnsProvider: pbProvider,
 | 
							DnsProvider: pbProvider,
 | 
				
			||||||
		AcmeUser:    pbACMEUser,
 | 
							AcmeUser:    pbACMEUser,
 | 
				
			||||||
		AuthType:    task.AuthType,
 | 
							AuthType:    task.AuthType,
 | 
				
			||||||
 | 
							AuthURL:     task.AuthURL,
 | 
				
			||||||
	}}, nil
 | 
						}}, nil
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 
 | 
				
			|||||||
							
								
								
									
										53
									
								
								internal/utils/http.go
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										53
									
								
								internal/utils/http.go
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,53 @@
 | 
				
			|||||||
 | 
					package utils
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					import (
 | 
				
			||||||
 | 
						"crypto/tls"
 | 
				
			||||||
 | 
						"io/ioutil"
 | 
				
			||||||
 | 
						"net/http"
 | 
				
			||||||
 | 
						"net/http/httputil"
 | 
				
			||||||
 | 
						"sync"
 | 
				
			||||||
 | 
						"time"
 | 
				
			||||||
 | 
					)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// HTTP请求客户端管理
 | 
				
			||||||
 | 
					var timeoutClientMap = map[time.Duration]*http.Client{} // timeout => Client
 | 
				
			||||||
 | 
					var timeoutClientLocker = sync.Mutex{}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// DumpResponse 导出响应
 | 
				
			||||||
 | 
					func DumpResponse(resp *http.Response) (header []byte, body []byte, err error) {
 | 
				
			||||||
 | 
						header, err = httputil.DumpResponse(resp, false)
 | 
				
			||||||
 | 
						body, err = ioutil.ReadAll(resp.Body)
 | 
				
			||||||
 | 
						return
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// NewHTTPClient 获取一个新的Client
 | 
				
			||||||
 | 
					func NewHTTPClient(timeout time.Duration) *http.Client {
 | 
				
			||||||
 | 
						return &http.Client{
 | 
				
			||||||
 | 
							Timeout: timeout,
 | 
				
			||||||
 | 
							Transport: &http.Transport{
 | 
				
			||||||
 | 
								MaxIdleConns:          4096,
 | 
				
			||||||
 | 
								MaxIdleConnsPerHost:   32,
 | 
				
			||||||
 | 
								MaxConnsPerHost:       32,
 | 
				
			||||||
 | 
								IdleConnTimeout:       2 * time.Minute,
 | 
				
			||||||
 | 
								ExpectContinueTimeout: 1 * time.Second,
 | 
				
			||||||
 | 
								TLSHandshakeTimeout:   0,
 | 
				
			||||||
 | 
								TLSClientConfig: &tls.Config{
 | 
				
			||||||
 | 
									InsecureSkipVerify: true,
 | 
				
			||||||
 | 
								},
 | 
				
			||||||
 | 
							},
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// SharedHttpClient 获取一个公用的Client
 | 
				
			||||||
 | 
					func SharedHttpClient(timeout time.Duration) *http.Client {
 | 
				
			||||||
 | 
						timeoutClientLocker.Lock()
 | 
				
			||||||
 | 
						defer timeoutClientLocker.Unlock()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						client, ok := timeoutClientMap[timeout]
 | 
				
			||||||
 | 
						if ok {
 | 
				
			||||||
 | 
							return client
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						client = NewHTTPClient(timeout)
 | 
				
			||||||
 | 
						timeoutClientMap[timeout] = client
 | 
				
			||||||
 | 
						return client
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
		Reference in New Issue
	
	Block a user