diff --git a/go.mod b/go.mod index 76016d6d3..9e66c07fb 100644 --- a/go.mod +++ b/go.mod @@ -52,7 +52,6 @@ require ( github.com/huaweicloud/huaweicloud-sdk-go-v3 v0.1.199 github.com/jdcloud-api/jdcloud-sdk-go v1.66.0 github.com/jlaffaye/ftp v0.2.0 - github.com/kong/go-kong v0.76.1 github.com/luthermonson/go-proxmox v0.7.1 github.com/microcosm-cc/bluemonday v1.0.27 github.com/minio/minio-go/v7 v7.2.0 @@ -132,15 +131,12 @@ require ( github.com/gorilla/websocket v1.5.4-0.20250319132907-e064f32e3674 // indirect github.com/hashicorp/go-cleanhttp v0.5.2 // indirect github.com/hashicorp/go-retryablehttp v0.7.8 // indirect - github.com/imdario/mergo v0.3.16 // indirect github.com/jinzhu/copier v0.4.0 // indirect - github.com/kong/semver/v4 v4.0.1 // indirect github.com/kylelemons/godebug v1.1.0 // indirect github.com/leodido/go-urn v1.4.0 // indirect github.com/linode/linodego v1.69.1 // indirect github.com/magefile/mage v1.17.2 // indirect github.com/mitchellh/go-homedir v1.1.0 // indirect - github.com/mitchellh/mapstructure v1.5.0 // indirect github.com/munnerz/goautoneg v0.0.0-20191010083416-a7dc8b61c822 // indirect github.com/namedotcom/go/v4 v4.0.2 // indirect github.com/nrdcg/bunny-go v0.1.0 // indirect @@ -157,9 +153,6 @@ require ( github.com/sirupsen/logrus v1.9.4 // indirect github.com/stretchr/objx v0.5.3 // indirect github.com/stretchr/testify v1.11.1 // indirect - github.com/tidwall/gjson v1.18.0 // indirect - github.com/tidwall/match v1.2.0 // indirect - github.com/tidwall/pretty v1.2.1 // indirect github.com/vultr/govultr/v3 v3.31.2 // indirect github.com/x448/float16 v0.8.4 // indirect go.mongodb.org/mongo-driver v1.17.9 // indirect diff --git a/go.sum b/go.sum index c1920bbf5..611d768d0 100644 --- a/go.sum +++ b/go.sum @@ -615,8 +615,6 @@ github.com/huaweicloud/huaweicloud-sdk-go-v3 v0.1.199 h1:mPzaN5CadyxTg1mHCZd+IUQ github.com/huaweicloud/huaweicloud-sdk-go-v3 v0.1.199/go.mod h1:M+yna96Fx9o5GbIUnF3OvVvQGjgfVSyeJbV9Yb1z/wI= github.com/hudl/fargo v1.4.0/go.mod h1:9Ai6uvFy5fQNq6VPKtg+Ceq1+eTY4nKUlR2JElEOcDo= github.com/ianlancetaylor/demangle v0.0.0-20181102032728-5e5cf60278f6/go.mod h1:aSSvb/t6k1mPoxDqO4vJh6VOCGPwU4O0C2/Eqndh1Sc= -github.com/imdario/mergo v0.3.16 h1:wwQJbIsHYGMUyLSPrEq1CT16AhnhNJQ51+4fdHUnCl4= -github.com/imdario/mergo v0.3.16/go.mod h1:WBLT9ZmE3lPoWsEzCh9LPo3TiwVN+ZKEjmz+hD27ysY= github.com/inconshreveable/mousetrap v1.1.0 h1:wN+x4NVGpMsO7ErUn/mUI3vEoE6Jt13X2s0bqwp9tc8= github.com/inconshreveable/mousetrap v1.1.0/go.mod h1:vpF70FUmC8bwa3OWnCshd2FqLfsEA9PFc4w1p2J65bw= github.com/influxdata/influxdb1-client v0.0.0-20200827194710-b269163b24ab/go.mod h1:qj24IKcXYK6Iy9ceXlo3Tc+vtHo9lIhSX5JddghvEPo= @@ -674,10 +672,6 @@ github.com/klauspost/cpuid/v2 v2.3.0 h1:S4CRMLnYUhGeDFDqkGriYKdfoFlDnMtqTiI/sFzh github.com/klauspost/cpuid/v2 v2.3.0/go.mod h1:hqwkgyIinND0mEev00jJYCxPNVRVXFQeu1XKlok6oO0= github.com/klauspost/crc32 v1.3.0 h1:sSmTt3gUt81RP655XGZPElI0PelVTZ6YwCRnPSupoFM= github.com/klauspost/crc32 v1.3.0/go.mod h1:D7kQaZhnkX/Y0tstFGf8VUzv2UofNGqCjnC3zdHB0Hw= -github.com/kong/go-kong v0.76.1 h1:lImAHvog7ehm4XL2rs8ZyCx98k56ihNazLG55bvHgVM= -github.com/kong/go-kong v0.76.1/go.mod h1:Wx5aTcMjyUnIF94M5NYFWb/EnuEkqB5STrWvybFSYYQ= -github.com/kong/semver/v4 v4.0.1 h1:DIcNR8W3gfx0KabFBADPalxxsp+q/5COwIFkkhrFQ2Y= -github.com/kong/semver/v4 v4.0.1/go.mod h1:LImQ0oT15pJvSns/hs2laLca2zcYoHu5EsSNY0J6/QA= github.com/konsorten/go-windows-terminal-sequences v1.0.1/go.mod h1:T0+1ngSBFLxvqU3pZ+m/2kptfBszLMUkC4ZK/EgS/cQ= github.com/konsorten/go-windows-terminal-sequences v1.0.3/go.mod h1:T0+1ngSBFLxvqU3pZ+m/2kptfBszLMUkC4ZK/EgS/cQ= github.com/kr/fs v0.1.0 h1:Jskdu9ieNAYnjxsi0LbQp1ulIKZV1LAFgK1tWhpZgl8= @@ -742,8 +736,6 @@ github.com/mitchellh/go-testing-interface v1.0.0/go.mod h1:kRemZodwjscx+RGhAo8eI github.com/mitchellh/mapstructure v0.0.0-20160808181253-ca63d7c062ee/go.mod h1:FVVH3fgwuzCH5S8UJGiWEs2h04kUh9fWfEaFds41c1Y= github.com/mitchellh/mapstructure v1.1.2/go.mod h1:FVVH3fgwuzCH5S8UJGiWEs2h04kUh9fWfEaFds41c1Y= github.com/mitchellh/mapstructure v1.4.2/go.mod h1:bFUtVrKA4DC2yAKiSyO/QUcy7e+RRV2QTWOzhPopBRo= -github.com/mitchellh/mapstructure v1.5.0 h1:jeMsZIYE/09sWLaz43PL7Gy6RuMjD2eJVyuac5Z2hdY= -github.com/mitchellh/mapstructure v1.5.0/go.mod h1:bFUtVrKA4DC2yAKiSyO/QUcy7e+RRV2QTWOzhPopBRo= github.com/modern-go/concurrent v0.0.0-20180228061459-e0a39a4cb421/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q= github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd h1:TRLaZ9cD/w8PVh93nsPXa1VrQ6jlwL5oN8l14QlcNfg= github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q= @@ -955,14 +947,6 @@ github.com/tencentcloud/tencentcloud-sdk-go/tencentcloud/vod v1.3.112 h1:vxOJOer github.com/tencentcloud/tencentcloud-sdk-go/tencentcloud/vod v1.3.112/go.mod h1:zCS+AwYqW2r0RBeCWHh9dmydCmP6LSew6y9Uyxsedy0= github.com/tencentcloud/tencentcloud-sdk-go/tencentcloud/waf v1.3.111 h1:CKRs1TWBVinSLGZ2J0OVtfzoqoWMizrJ6IdYo6QEfow= github.com/tencentcloud/tencentcloud-sdk-go/tencentcloud/waf v1.3.111/go.mod h1:AfaoGamQm8lafjz+jkZn+T9VE1+tZ3ul9V9v6PORMVE= -github.com/tidwall/gjson v1.18.0 h1:FIDeeyB800efLX89e5a8Y0BNH+LOngJyGrIWxG2FKQY= -github.com/tidwall/gjson v1.18.0/go.mod h1:/wbyibRr2FHMks5tjHJ5F8dMZh3AcwJEMf5vlfC0lxk= -github.com/tidwall/match v1.1.1/go.mod h1:eRSPERbgtNPcGhD8UCthc6PmLEQXEWd3PRB5JTxsfmM= -github.com/tidwall/match v1.2.0 h1:0pt8FlkOwjN2fPt4bIl4BoNxb98gGHN2ObFEDkrfZnM= -github.com/tidwall/match v1.2.0/go.mod h1:eRSPERbgtNPcGhD8UCthc6PmLEQXEWd3PRB5JTxsfmM= -github.com/tidwall/pretty v1.2.0/go.mod h1:ITEVvHYasfjBbM0u2Pg8T2nJnzm8xPwvNhhsoaGGjNU= -github.com/tidwall/pretty v1.2.1 h1:qjsOFOWWQl+N3RsoF5/ssm1pHmJJwhjlSbZ51I6wMl4= -github.com/tidwall/pretty v1.2.1/go.mod h1:ITEVvHYasfjBbM0u2Pg8T2nJnzm8xPwvNhhsoaGGjNU= github.com/tinylib/msgp v1.6.4 h1:mOwYbyYDLPj35mkA2BjjYejgJk9BuHxDdvRnb6v2ZcQ= github.com/tinylib/msgp v1.6.4/go.mod h1:RSp0LW9oSxFut3KzESt5Voq4GVWyS+PSulT77roAqEA= github.com/tjfoc/gmsm v1.3.2/go.mod h1:HaUcFuY0auTiaHB9MHFGCPx5IaLhTUd2atbCFBQXn9w= diff --git a/pkg/core/deployer/providers/apisix/apisix.go b/pkg/core/deployer/providers/apisix/apisix.go index 0540f6c44..78a8d4f5a 100644 --- a/pkg/core/deployer/providers/apisix/apisix.go +++ b/pkg/core/deployer/providers/apisix/apisix.go @@ -93,25 +93,25 @@ func (d *Deployer) deployToCertificate(ctx context.Context, certPEM, privkeyPEM // 更新 SSL 证书 // REF: https://apisix.apache.org/zh/docs/apisix/admin-api/#ssl - sslUpdateReq := &apisixsdk.SslUpdateRequest{ + updateSSLReq := &apisixsdk.UpdateSSLRequest{ ID: lo.ToPtr(d.config.CertificateId), Certificate: lo.ToPtr(certPEM), PrivateKey: lo.ToPtr(privkeyPEM), - SNIs: lo.ToPtr(certX509.DNSNames), + SNIs: lo.Map(certX509.DNSNames, func(s string, _ int) *string { return lo.ToPtr(s) }), Type: lo.ToPtr("server"), Status: lo.ToPtr(int32(1)), } - sslUpdateResp, err := d.sdkClient.SslUpdateWithContext(ctx, d.config.CertificateId, sslUpdateReq) - d.logger.Debug("sdk request 'SslUpdate'", slog.Any("request", sslUpdateReq), slog.Any("response", sslUpdateResp)) + updateSSLResp, err := d.sdkClient.UpdateSSLWithContext(ctx, d.config.CertificateId, updateSSLReq) + d.logger.Debug("sdk request 'UpdateSSL'", slog.Any("request", updateSSLReq), slog.Any("response", updateSSLResp)) if err != nil { - return fmt.Errorf("failed to execute sdk request 'SslUpdate': %w", err) + return fmt.Errorf("failed to execute sdk request 'UpdateSSL': %w", err) } return nil } func createSDKClient(serverUrl, apiKey string, skipTlsVerify bool) (*apisixsdk.Client, error) { - client, err := apisixsdk.NewClient(serverUrl, + client, err := apisixsdk.NewClient(serverUrl, apisixsdk.WithApiKey(apiKey), ) if err != nil { diff --git a/pkg/core/deployer/providers/baishan-cdn/baishan_cdn.go b/pkg/core/deployer/providers/baishan-cdn/baishan_cdn.go index 127dc6999..7ec3eb149 100644 --- a/pkg/core/deployer/providers/baishan-cdn/baishan_cdn.go +++ b/pkg/core/deployer/providers/baishan-cdn/baishan_cdn.go @@ -112,7 +112,7 @@ func (d *Deployer) deployToDomain(ctx context.Context, certPEM, privkeyPEM strin // REF: https://portal.baishancloud.com/track/document/api/1/1065 getDomainConfigReq := &baishansdk.GetDomainConfigRequest{ Domains: lo.ToPtr(d.config.Domain), - Config: lo.ToPtr([]string{"https"}), + Config: []*string{lo.ToPtr("https")}, } getDomainConfigResp, err := d.sdkClient.GetDomainConfigWithContext(ctx, getDomainConfigReq) d.logger.Debug("sdk request 'cdn.GetDomainConfig'", slog.Any("request", getDomainConfigReq), slog.Any("response", getDomainConfigResp)) diff --git a/pkg/core/deployer/providers/baotawaf/baotawaf.go b/pkg/core/deployer/providers/baotawaf/baotawaf.go index 9bc988801..542e9ada0 100644 --- a/pkg/core/deployer/providers/baotawaf/baotawaf.go +++ b/pkg/core/deployer/providers/baotawaf/baotawaf.go @@ -151,7 +151,7 @@ func (d *Deployer) updateSiteCertificate(ctx context.Context, siteName string, s SiteId: lo.ToPtr(siteData.SiteId), Type: lo.ToPtr("openCert"), Server: &btwafsdk.SiteServerInfoMod{ - ListenSSLPorts: lo.ToPtr([]string{fmt.Sprintf("%d", d.config.SitePort)}), + ListenSSLPorts: []*string{lo.ToPtr(fmt.Sprintf("%d", d.config.SitePort))}, SSL: &btwafsdk.SiteServerSSLInfo{ IsSSL: lo.ToPtr(int32(1)), FullChain: lo.ToPtr(certPEM), diff --git a/pkg/core/deployer/providers/kong/kong.go b/pkg/core/deployer/providers/kong/kong.go index 0fb9ceda6..a10a7e960 100644 --- a/pkg/core/deployer/providers/kong/kong.go +++ b/pkg/core/deployer/providers/kong/kong.go @@ -5,13 +5,12 @@ import ( "crypto/tls" "fmt" "log/slog" - "net/http" - "github.com/kong/go-kong/kong" + "github.com/samber/lo" "github.com/certimate-go/certimate/pkg/core" + kongsdk "github.com/certimate-go/certimate/pkg/sdk3rd/kong" xcert "github.com/certimate-go/certimate/pkg/utils/cert" - xhttp "github.com/certimate-go/certimate/pkg/utils/http" ) type ( @@ -39,7 +38,7 @@ type DeployerConfig struct { type Deployer struct { config *DeployerConfig logger *slog.Logger - sdkClient *kong.Client + sdkClient *kongsdk.Client } var _ Provider = (*Deployer)(nil) @@ -98,48 +97,33 @@ func (d *Deployer) deployToCertificate(ctx context.Context, certPEM, privkeyPEM // 更新证书 // REF: https://developer.konghq.com/api/gateway/admin-ee/3.10/#/operations/upsert-certificate // REF: https://developer.konghq.com/api/gateway/admin-ee/3.10/#/operations/upsert-certificate-in-workspace - updateCertificateReq := &kong.Certificate{ - ID: kong.String(d.config.CertificateId), - Cert: kong.String(certPEM), - Key: kong.String(privkeyPEM), - SNIs: kong.StringSlice(certX509.DNSNames...), + upsertCertificateReq := &kongsdk.UpsertCertificateRequest{ + Id: lo.ToPtr(d.config.CertificateId), + Cert: lo.ToPtr(certPEM), + Key: lo.ToPtr(privkeyPEM), + SNIs: lo.Map(certX509.DNSNames, func(s string, _ int) *string { return lo.ToPtr(s) }), } - updateCertificateResp, err := d.sdkClient.Certificates.Update(ctx, updateCertificateReq) - d.logger.Debug("sdk request 'UpdateCertificate'", slog.String("sslId", d.config.CertificateId), slog.Any("request", updateCertificateReq), slog.Any("response", updateCertificateResp)) + upsertCertificateResp, err := d.sdkClient.UpsertCertificateWithContext(ctx, d.config.CertificateId, upsertCertificateReq) + d.logger.Debug("sdk request 'UpsertCertificate'", slog.String("certificateId", d.config.CertificateId), slog.Any("request", upsertCertificateReq), slog.Any("response", upsertCertificateResp)) if err != nil { - return fmt.Errorf("failed to execute sdk request 'UpdateCertificate': %w", err) + return fmt.Errorf("failed to execute sdk request 'UpsertCertificate': %w", err) } return nil } -func createSDKClient(serverUrl, workspace, apiToken string, skipTlsVerify bool) (*kong.Client, error) { - httpClient := &http.Client{ - Transport: xhttp.NewDefaultTransport(), - Timeout: http.DefaultClient.Timeout, - } - if skipTlsVerify { - transport := xhttp.NewDefaultTransport() - transport.DisableKeepAlives = true - transport.TLSClientConfig = &tls.Config{InsecureSkipVerify: true} - httpClient.Transport = transport - } else { - httpClient.Transport = http.DefaultTransport - } - - httpHeaders := http.Header{} - if apiToken != "" { - httpHeaders.Set("Kong-Admin-Token", apiToken) - } - - client, err := kong.NewClient(kong.String(serverUrl), kong.HTTPClientWithHeaders(httpClient, httpHeaders)) +func createSDKClient(serverUrl, workspace, apiToken string, skipTlsVerify bool) (*kongsdk.Client, error) { + client, err := kongsdk.NewClient(serverUrl, + kongsdk.WithWorkspace(workspace), + kongsdk.WithApiToken(apiToken), + ) if err != nil { return nil, err } - if workspace != "" { - client.SetWorkspace(workspace) + if skipTlsVerify { + client.SetTLSConfig(&tls.Config{InsecureSkipVerify: true}) } - return client, nil + return client, err } diff --git a/pkg/sdk3rd/apisix/api_ssl_update.go b/pkg/sdk3rd/apisix/api_ssl_update.go deleted file mode 100644 index a581eed49..000000000 --- a/pkg/sdk3rd/apisix/api_ssl_update.go +++ /dev/null @@ -1,33 +0,0 @@ -package apisix - -import ( - "context" - "fmt" - "net/http" - "net/url" -) - -type SslUpdateRequest = SslCertificate - -type SslUpdateResponse = SslCertificate - -func (c *Client) SslUpdate(sslId string, req *SslUpdateRequest) (*SslUpdateResponse, error) { - return c.SslUpdateWithContext(context.Background(), sslId, req) -} - -func (c *Client) SslUpdateWithContext(ctx context.Context, sslId string, req *SslUpdateRequest) (*SslUpdateResponse, error) { - httpreq, err := c.newRequest(http.MethodPut, fmt.Sprintf("/ssls/%s", url.PathEscape(sslId))) - if err != nil { - return nil, err - } else { - httpreq.SetBody(req) - httpreq.SetContext(ctx) - } - - result := &SslUpdateResponse{} - if _, err := c.doRequestWithResult(httpreq, result); err != nil { - return result, err - } - - return result, nil -} diff --git a/pkg/sdk3rd/apisix/api_update_ssl.go b/pkg/sdk3rd/apisix/api_update_ssl.go new file mode 100644 index 000000000..1c802d7b5 --- /dev/null +++ b/pkg/sdk3rd/apisix/api_update_ssl.go @@ -0,0 +1,37 @@ +package apisix + +import ( + "context" + "fmt" + "net/http" + "net/url" +) + +type UpdateSSLRequest Certificate + +type UpdateSSLResponse Certificate + +func (c *Client) UpdateSSL(sslId string, req *UpdateSSLRequest) (*UpdateSSLResponse, error) { + return c.UpdateSSLWithContext(context.Background(), sslId, req) +} + +func (c *Client) UpdateSSLWithContext(ctx context.Context, sslId string, req *UpdateSSLRequest) (*UpdateSSLResponse, error) { + if sslId == "" { + return nil, fmt.Errorf("sdkerr: unset sslId") + } + + httpreq, err := c.newRequest(http.MethodPut, fmt.Sprintf("/ssls/%s", url.PathEscape(sslId))) + if err != nil { + return nil, err + } else { + httpreq.SetBody(req) + httpreq.SetContext(ctx) + } + + result := &UpdateSSLResponse{} + if _, err := c.doRequestWithResult(httpreq, result); err != nil { + return result, err + } + + return result, nil +} diff --git a/pkg/sdk3rd/apisix/types.go b/pkg/sdk3rd/apisix/types.go index ddc798ba0..28ba6633d 100644 --- a/pkg/sdk3rd/apisix/types.go +++ b/pkg/sdk3rd/apisix/types.go @@ -1,13 +1,13 @@ package apisix -type SslCertificate struct { - ID *string `json:"id,omitempty"` - Status *int32 `json:"status,omitempty"` - Certificate *string `json:"cert,omitempty"` - PrivateKey *string `json:"key,omitempty"` - SNIs *[]string `json:"snis,omitempty"` - Type *string `json:"type,omitempty"` - ValidityStart *int64 `json:"validity_start,omitempty"` - ValidityEnd *int64 `json:"validity_end,omitempty"` - Labels *map[string]string `json:"labels,omitempty"` +type Certificate struct { + ID *string `json:"id,omitempty"` + Status *int32 `json:"status,omitempty"` + Certificate *string `json:"cert,omitempty"` + PrivateKey *string `json:"key,omitempty"` + SNIs []*string `json:"snis,omitempty"` + Type *string `json:"type,omitempty"` + ValidityStart *int64 `json:"validity_start,omitempty"` + ValidityEnd *int64 `json:"validity_end,omitempty"` + Labels map[string]string `json:"labels,omitempty"` } diff --git a/pkg/sdk3rd/baishan/api_get_domain_config.go b/pkg/sdk3rd/baishan/api_get_domain_config.go index c5ccf98c2..4592af7cf 100644 --- a/pkg/sdk3rd/baishan/api_get_domain_config.go +++ b/pkg/sdk3rd/baishan/api_get_domain_config.go @@ -7,7 +7,7 @@ import ( type GetDomainConfigRequest struct { Domains *string `json:"domains,omitempty" url:"domains,omitempty"` - Config *[]string `json:"config,omitempty" url:"config,omitempty"` + Config []*string `json:"config,omitempty" url:"config,omitempty"` } type GetDomainConfigResponse struct { @@ -32,8 +32,10 @@ func (c *Client) GetDomainConfigWithContext(ctx context.Context, req *GetDomainC httpreq.SetQueryParam("domains", *req.Domains) } if req.Config != nil { - for _, config := range *req.Config { - httpreq.QueryParam.Add("config[]", config) + for _, config := range req.Config { + if config != nil { + httpreq.QueryParam.Add("config[]", *config) + } } } diff --git a/pkg/sdk3rd/btwaf/types.go b/pkg/sdk3rd/btwaf/types.go index a3393a80f..42dae0e47 100644 --- a/pkg/sdk3rd/btwaf/types.go +++ b/pkg/sdk3rd/btwaf/types.go @@ -34,7 +34,7 @@ type SiteRecord struct { // } type SiteServerInfoMod struct { - ListenSSLPorts *[]string `json:"listen_ssl_port,omitempty"` + ListenSSLPorts []*string `json:"listen_ssl_port,omitempty"` SSL *SiteServerSSLInfo `json:"ssl,omitempty"` } diff --git a/pkg/sdk3rd/kong/api_upsert_certificates.go b/pkg/sdk3rd/kong/api_upsert_certificates.go new file mode 100644 index 000000000..479d06c29 --- /dev/null +++ b/pkg/sdk3rd/kong/api_upsert_certificates.go @@ -0,0 +1,39 @@ +package kong + +import ( + "context" + "fmt" + "net/http" + "net/url" +) + +type UpsertCertificateRequest Certificate + +type UpsertCertificateResponse Certificate + +func (c *Client) UpsertCertificate(certificateId string, req *UpsertCertificateRequest) (*UpsertCertificateResponse, error) { + return c.UpsertCertificateWithContext(context.Background(), certificateId, req) +} + +func (c *Client) UpsertCertificateWithContext(ctx context.Context, certificateId string, req *UpsertCertificateRequest) (*UpsertCertificateResponse, error) { + if certificateId == "" { + return nil, fmt.Errorf("sdkerr: unset certificateId") + } + + httpreq, err := c.newRequest(http.MethodPut, fmt.Sprintf("/certificates/%s", url.PathEscape(certificateId))) + if err != nil { + return nil, err + } else { + req.Id = &certificateId + + httpreq.SetBody(req) + httpreq.SetContext(ctx) + } + + result := &UpsertCertificateResponse{} + if _, err := c.doRequestWithResult(httpreq, result); err != nil { + return result, err + } + + return result, nil +} diff --git a/pkg/sdk3rd/kong/client.go b/pkg/sdk3rd/kong/client.go new file mode 100644 index 000000000..5329061b9 --- /dev/null +++ b/pkg/sdk3rd/kong/client.go @@ -0,0 +1,113 @@ +package kong + +import ( + "crypto/tls" + "encoding/json" + "fmt" + "net/url" + "strings" + "time" + + "github.com/go-resty/resty/v2" + + "github.com/certimate-go/certimate/internal/app" +) + +type Client struct { + rc *resty.Client +} + +func NewClient(serverUrl string, optFns ...OptionsFunc) (*Client, error) { + opts := &Options{} + for _, fn := range optFns { + fn(opts) + } + + if serverUrl == "" { + return nil, fmt.Errorf("sdkerr: unset serverUrl") + } + if _, err := url.Parse(serverUrl); err != nil { + return nil, fmt.Errorf("sdkerr: invalid serverUrl: %w", err) + } + if opts.ApiToken == "" { + return nil, fmt.Errorf("sdkerr: unset apiToken") + } + + baseUrl := strings.TrimSuffix(serverUrl, "/") + if opts.Workspace != "" { + baseUrl += fmt.Sprintf("/%s", url.PathEscape(opts.Workspace)) + } + + restyClient := resty.New(). + SetBaseURL(baseUrl). + SetHeader("Accept", "application/json"). + SetHeader("Content-Type", "application/json"). + SetHeader("User-Agent", app.AppUserAgent). + SetHeader("Kong-Admin-Token", opts.ApiToken) + + return &Client{rc: restyClient}, nil +} + +func (c *Client) SetTimeout(timeout time.Duration) *Client { + c.rc.SetTimeout(timeout) + return c +} + +func (c *Client) SetTLSConfig(config *tls.Config) *Client { + c.rc.SetTLSClientConfig(config) + return c +} + +func (c *Client) newRequest(method string, path string) (*resty.Request, error) { + if method == "" { + return nil, fmt.Errorf("sdkerr: unset method") + } + if path == "" { + return nil, fmt.Errorf("sdkerr: unset path") + } + + req := c.rc.R() + req.Method = method + req.URL = path + return req, nil +} + +func (c *Client) doRequest(req *resty.Request) (*resty.Response, error) { + if req == nil { + return nil, fmt.Errorf("sdkerr: nil request") + } + + // WARN: + // PLEASE DO NOT USE `req.SetResult` or `req.SetError` HERE! USE `doRequestWithResult` INSTEAD. + + resp, err := req.Send() + if err != nil { + return resp, fmt.Errorf("sdkerr: failed to send request: %w", err) + } else if resp.IsError() { + return resp, fmt.Errorf("sdkerr: unexpected status code: %d (resp: %s)", resp.StatusCode(), resp.String()) + } + + return resp, nil +} + +func (c *Client) doRequestWithResult(req *resty.Request, res interface{}) (*resty.Response, error) { + if req == nil { + return nil, fmt.Errorf("sdkerr: nil request") + } + + resp, err := c.doRequest(req) + if err != nil { + if resp != nil { + json.Unmarshal(resp.Body(), &res) + } + return resp, err + } + + if len(resp.Body()) != 0 { + if err := json.Unmarshal(resp.Body(), &res); err != nil { + return resp, fmt.Errorf("sdkerr: failed to unmarshal response: %w (resp: %s)", err, resp.String()) + } + } + + return resp, nil +} diff --git a/pkg/sdk3rd/kong/options.go b/pkg/sdk3rd/kong/options.go new file mode 100644 index 000000000..33be7298b --- /dev/null +++ b/pkg/sdk3rd/kong/options.go @@ -0,0 +1,20 @@ +package kong + +type Options struct { + ApiToken string + Workspace string +} + +type OptionsFunc func(*Options) + +func WithApiToken(apiToken string) OptionsFunc { + return func(o *Options) { + o.ApiToken = apiToken + } +} + +func WithWorkspace(workspace string) OptionsFunc { + return func(o *Options) { + o.Workspace = workspace + } +} diff --git a/pkg/sdk3rd/kong/types.go b/pkg/sdk3rd/kong/types.go new file mode 100644 index 000000000..2deac1448 --- /dev/null +++ b/pkg/sdk3rd/kong/types.go @@ -0,0 +1,13 @@ +package kong + +type Certificate struct { + Id *string `json:"id,omitempty"` + Cert *string `json:"cert,omitempty"` + CertAlt *string `json:"cert_alt,omitempty"` + Key *string `json:"key,omitempty"` + KeyAlt *string `json:"key_alt,omitempty"` + SNIs []*string `json:"snis,omitempty"` + Tags []*string `json:"tags,omitempty"` + CreatedAt *string `json:"created_at,omitempty"` + UpdatedAt *string `json:"updated_at,omitempty"` +} diff --git a/pkg/sdk3rd/wangsu/cdnpro/types.go b/pkg/sdk3rd/wangsu/cdnpro/types.go index b68b6e698..dc095819a 100644 --- a/pkg/sdk3rd/wangsu/cdnpro/types.go +++ b/pkg/sdk3rd/wangsu/cdnpro/types.go @@ -44,7 +44,7 @@ type CertificateVersionIdentificationInfo struct { Department *string `json:"department,omitempty"` CommonName *string `json:"commonName,omitempty"` Email *string `json:"email,omitempty"` - SubjectAlternativeNames *[]string `json:"subjectAlternativeNames,omitempty"` + SubjectAlternativeNames []*string `json:"subjectAlternativeNames,omitempty"` } type HostnamePropertyInfo struct {