mirror of
https://github.com/usual2970/certimate.git
synced 2025-07-09 12:39:57 +00:00
Compare commits
1 Commits
d1a05e214a
...
5e536c3b91
Author | SHA1 | Date | |
---|---|---|---|
![]() |
5e536c3b91 |
@ -130,7 +130,7 @@ make local.run
|
|||||||
| [百度智能云](https://cloud.baidu.com/) | 可部署到百度智能云 CDN 等服务 |
|
| [百度智能云](https://cloud.baidu.com/) | 可部署到百度智能云 CDN 等服务 |
|
||||||
| [华为云](https://www.huaweicloud.com/) | 可部署到华为云 CDN、ELB、WAF 等服务 |
|
| [华为云](https://www.huaweicloud.com/) | 可部署到华为云 CDN、ELB、WAF 等服务 |
|
||||||
| [火山引擎](https://www.volcengine.com/) | 可部署到火山引擎 TOS、CDN、DCDN、CLB、ImageX、Live 等服务 |
|
| [火山引擎](https://www.volcengine.com/) | 可部署到火山引擎 TOS、CDN、DCDN、CLB、ImageX、Live 等服务 |
|
||||||
| [京东云](https://www.jdcloud.com/) | 可部署到京东云 CDN、ALB、视频直播等服务 |
|
| [京东云](https://www.jdcloud.com/) | 可部署到京东云 CDN、视频直播等服务 |
|
||||||
| [七牛云](https://www.qiniu.com/) | 可部署到七牛云 CDN、直播云等服务 |
|
| [七牛云](https://www.qiniu.com/) | 可部署到七牛云 CDN、直播云等服务 |
|
||||||
| [白山云](https://www.baishan.com/) | 可部署到白山云 CDN |
|
| [白山云](https://www.baishan.com/) | 可部署到白山云 CDN |
|
||||||
| [多吉云](https://www.dogecloud.com/) | 可部署到多吉云 CDN |
|
| [多吉云](https://www.dogecloud.com/) | 可部署到多吉云 CDN |
|
||||||
|
@ -129,7 +129,7 @@ The following hosting providers are supported:
|
|||||||
| [Baidu AI Cloud](https://intl.cloud.baidu.com/) | Supports deployment to Baidu AI CLoud CDN |
|
| [Baidu AI Cloud](https://intl.cloud.baidu.com/) | Supports deployment to Baidu AI CLoud CDN |
|
||||||
| [Huawei Cloud](https://www.huaweicloud.com/) | Supports deployment to Huawei Cloud CDN, ELB, WAF |
|
| [Huawei Cloud](https://www.huaweicloud.com/) | Supports deployment to Huawei Cloud CDN, ELB, WAF |
|
||||||
| [Volcengine](https://www.volcengine.com/) | Supports deployment to Volcengine TOS, CDN, DCDN, CLB, ImageX, Live |
|
| [Volcengine](https://www.volcengine.com/) | Supports deployment to Volcengine TOS, CDN, DCDN, CLB, ImageX, Live |
|
||||||
| [JD Cloud](https://www.jdcloud.com/) | Supports deployment to JD Cloud CDN, ALB, Live Video |
|
| [JD Cloud](https://www.jdcloud.com/) | Supports deployment to JD Cloud CDN, Live Video |
|
||||||
| [Qiniu Cloud](https://www.qiniu.com/) | Supports deployment to Qiniu Cloud CDN, Pili |
|
| [Qiniu Cloud](https://www.qiniu.com/) | Supports deployment to Qiniu Cloud CDN, Pili |
|
||||||
| [Baishan Cloud](https://intl.baishancloud.com/) | Supports deployment to Baishan Cloud CDN |
|
| [Baishan Cloud](https://intl.baishancloud.com/) | Supports deployment to Baishan Cloud CDN |
|
||||||
| [Doge Cloud](https://www.dogecloud.com/) | Supports deployment to Doge Cloud CDN |
|
| [Doge Cloud](https://www.dogecloud.com/) | Supports deployment to Doge Cloud CDN |
|
||||||
|
@ -30,7 +30,6 @@ import (
|
|||||||
pHuaweiCloudCDN "github.com/usual2970/certimate/internal/pkg/core/deployer/providers/huaweicloud-cdn"
|
pHuaweiCloudCDN "github.com/usual2970/certimate/internal/pkg/core/deployer/providers/huaweicloud-cdn"
|
||||||
pHuaweiCloudELB "github.com/usual2970/certimate/internal/pkg/core/deployer/providers/huaweicloud-elb"
|
pHuaweiCloudELB "github.com/usual2970/certimate/internal/pkg/core/deployer/providers/huaweicloud-elb"
|
||||||
pHuaweiCloudWAF "github.com/usual2970/certimate/internal/pkg/core/deployer/providers/huaweicloud-waf"
|
pHuaweiCloudWAF "github.com/usual2970/certimate/internal/pkg/core/deployer/providers/huaweicloud-waf"
|
||||||
pJDCloudALB "github.com/usual2970/certimate/internal/pkg/core/deployer/providers/jdcloud-alb"
|
|
||||||
pJDCloudCDN "github.com/usual2970/certimate/internal/pkg/core/deployer/providers/jdcloud-cdn"
|
pJDCloudCDN "github.com/usual2970/certimate/internal/pkg/core/deployer/providers/jdcloud-cdn"
|
||||||
pJDCloudLive "github.com/usual2970/certimate/internal/pkg/core/deployer/providers/jdcloud-live"
|
pJDCloudLive "github.com/usual2970/certimate/internal/pkg/core/deployer/providers/jdcloud-live"
|
||||||
pK8sSecret "github.com/usual2970/certimate/internal/pkg/core/deployer/providers/k8s-secret"
|
pK8sSecret "github.com/usual2970/certimate/internal/pkg/core/deployer/providers/k8s-secret"
|
||||||
@ -418,7 +417,7 @@ func createDeployer(options *deployerOptions) (deployer.Deployer, error) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
case domain.DeployProviderTypeJDCloudALB, domain.DeployProviderTypeJDCloudCDN, domain.DeployProviderTypeJDCloudLive:
|
case domain.DeployProviderTypeJDCloudCDN, domain.DeployProviderTypeJDCloudLive:
|
||||||
{
|
{
|
||||||
access := domain.AccessConfigForJDCloud{}
|
access := domain.AccessConfigForJDCloud{}
|
||||||
if err := maps.Populate(options.ProviderAccessConfig, &access); err != nil {
|
if err := maps.Populate(options.ProviderAccessConfig, &access); err != nil {
|
||||||
@ -426,17 +425,6 @@ func createDeployer(options *deployerOptions) (deployer.Deployer, error) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
switch options.Provider {
|
switch options.Provider {
|
||||||
case domain.DeployProviderTypeJDCloudALB:
|
|
||||||
deployer, err := pJDCloudALB.NewDeployer(&pJDCloudALB.DeployerConfig{
|
|
||||||
AccessKeyId: access.AccessKeyId,
|
|
||||||
AccessKeySecret: access.AccessKeySecret,
|
|
||||||
RegionId: maps.GetValueAsString(options.ProviderDeployConfig, "regionId"),
|
|
||||||
ResourceType: pJDCloudALB.ResourceType(maps.GetValueAsString(options.ProviderDeployConfig, "resourceType")),
|
|
||||||
LoadbalancerId: maps.GetValueAsString(options.ProviderDeployConfig, "loadbalancerId"),
|
|
||||||
ListenerId: maps.GetValueAsString(options.ProviderDeployConfig, "listenerId"),
|
|
||||||
})
|
|
||||||
return deployer, err
|
|
||||||
|
|
||||||
case domain.DeployProviderTypeJDCloudCDN:
|
case domain.DeployProviderTypeJDCloudCDN:
|
||||||
deployer, err := pJDCloudCDN.NewDeployer(&pJDCloudCDN.DeployerConfig{
|
deployer, err := pJDCloudCDN.NewDeployer(&pJDCloudCDN.DeployerConfig{
|
||||||
AccessKeyId: access.AccessKeyId,
|
AccessKeyId: access.AccessKeyId,
|
||||||
|
@ -127,7 +127,6 @@ const (
|
|||||||
DeployProviderTypeHuaweiCloudCDN = DeployProviderType("huaweicloud-cdn")
|
DeployProviderTypeHuaweiCloudCDN = DeployProviderType("huaweicloud-cdn")
|
||||||
DeployProviderTypeHuaweiCloudELB = DeployProviderType("huaweicloud-elb")
|
DeployProviderTypeHuaweiCloudELB = DeployProviderType("huaweicloud-elb")
|
||||||
DeployProviderTypeHuaweiCloudWAF = DeployProviderType("huaweicloud-waf")
|
DeployProviderTypeHuaweiCloudWAF = DeployProviderType("huaweicloud-waf")
|
||||||
DeployProviderTypeJDCloudALB = DeployProviderType("jdcloud-alb")
|
|
||||||
DeployProviderTypeJDCloudCDN = DeployProviderType("jdcloud-cdn")
|
DeployProviderTypeJDCloudCDN = DeployProviderType("jdcloud-cdn")
|
||||||
DeployProviderTypeJDCloudLive = DeployProviderType("jdcloud-live")
|
DeployProviderTypeJDCloudLive = DeployProviderType("jdcloud-live")
|
||||||
DeployProviderTypeKubernetesSecret = DeployProviderType("k8s-secret")
|
DeployProviderTypeKubernetesSecret = DeployProviderType("k8s-secret")
|
||||||
|
@ -254,7 +254,7 @@ func (d *DeployerProvider) updateListenerCertificate(ctx context.Context, cloudL
|
|||||||
|
|
||||||
d.logger.Logt("已更新 ALB 监听配置", updateListenerAttributeResp)
|
d.logger.Logt("已更新 ALB 监听配置", updateListenerAttributeResp)
|
||||||
} else {
|
} else {
|
||||||
// 指定 SNI,需部署到扩展域名
|
// 指定 SNI,需部署到扩展域名(支持泛域名)
|
||||||
|
|
||||||
// 查询监听证书列表
|
// 查询监听证书列表
|
||||||
// REF: https://help.aliyun.com/zh/slb/application-load-balancer/developer-reference/api-alb-2020-06-16-listlistenercertificates
|
// REF: https://help.aliyun.com/zh/slb/application-load-balancer/developer-reference/api-alb-2020-06-16-listlistenercertificates
|
||||||
|
@ -211,6 +211,8 @@ func (d *DeployerProvider) updateListenerCertificate(ctx context.Context, cloudL
|
|||||||
|
|
||||||
// 修改监听配置
|
// 修改监听配置
|
||||||
// REF: https://help.aliyun.com/zh/slb/classic-load-balancer/developer-reference/api-slb-2014-05-15-setloadbalancerhttpslistenerattribute
|
// REF: https://help.aliyun.com/zh/slb/classic-load-balancer/developer-reference/api-slb-2014-05-15-setloadbalancerhttpslistenerattribute
|
||||||
|
//
|
||||||
|
// 注意修改监听配置要放在修改扩展域名之后
|
||||||
setLoadBalancerHTTPSListenerAttributeReq := &aliyunSlb.SetLoadBalancerHTTPSListenerAttributeRequest{
|
setLoadBalancerHTTPSListenerAttributeReq := &aliyunSlb.SetLoadBalancerHTTPSListenerAttributeRequest{
|
||||||
RegionId: tea.String(d.config.Region),
|
RegionId: tea.String(d.config.Region),
|
||||||
LoadBalancerId: tea.String(cloudLoadbalancerId),
|
LoadBalancerId: tea.String(cloudLoadbalancerId),
|
||||||
@ -224,7 +226,7 @@ func (d *DeployerProvider) updateListenerCertificate(ctx context.Context, cloudL
|
|||||||
|
|
||||||
d.logger.Logt("已更新 CLB HTTPS 监听配置", setLoadBalancerHTTPSListenerAttributeResp)
|
d.logger.Logt("已更新 CLB HTTPS 监听配置", setLoadBalancerHTTPSListenerAttributeResp)
|
||||||
} else {
|
} else {
|
||||||
// 指定 SNI,需部署到扩展域名
|
// 指定 SNI,需部署到扩展域名(支持泛域名)
|
||||||
|
|
||||||
// 查询扩展域名
|
// 查询扩展域名
|
||||||
// REF: https://help.aliyun.com/zh/slb/classic-load-balancer/developer-reference/api-slb-2014-05-15-describedomainextensions
|
// REF: https://help.aliyun.com/zh/slb/classic-load-balancer/developer-reference/api-slb-2014-05-15-describedomainextensions
|
||||||
|
@ -1,10 +0,0 @@
|
|||||||
package jdcloudalb
|
|
||||||
|
|
||||||
type ResourceType string
|
|
||||||
|
|
||||||
const (
|
|
||||||
// 资源类型:部署到指定负载均衡器。
|
|
||||||
RESOURCE_TYPE_LOADBALANCER = ResourceType("loadbalancer")
|
|
||||||
// 资源类型:部署到指定监听器。
|
|
||||||
RESOURCE_TYPE_LISTENER = ResourceType("listener")
|
|
||||||
)
|
|
@ -1,251 +0,0 @@
|
|||||||
package jdcloudalb
|
|
||||||
|
|
||||||
import (
|
|
||||||
"context"
|
|
||||||
"errors"
|
|
||||||
"fmt"
|
|
||||||
"strings"
|
|
||||||
|
|
||||||
jdCore "github.com/jdcloud-api/jdcloud-sdk-go/core"
|
|
||||||
jdCommon "github.com/jdcloud-api/jdcloud-sdk-go/services/common/models"
|
|
||||||
jdLbApi "github.com/jdcloud-api/jdcloud-sdk-go/services/lb/apis"
|
|
||||||
jdLbClient "github.com/jdcloud-api/jdcloud-sdk-go/services/lb/client"
|
|
||||||
jdLbModel "github.com/jdcloud-api/jdcloud-sdk-go/services/lb/models"
|
|
||||||
xerrors "github.com/pkg/errors"
|
|
||||||
|
|
||||||
"github.com/usual2970/certimate/internal/pkg/core/deployer"
|
|
||||||
"github.com/usual2970/certimate/internal/pkg/core/logger"
|
|
||||||
"github.com/usual2970/certimate/internal/pkg/core/uploader"
|
|
||||||
uploadersp "github.com/usual2970/certimate/internal/pkg/core/uploader/providers/jdcloud-ssl"
|
|
||||||
"github.com/usual2970/certimate/internal/pkg/utils/slices"
|
|
||||||
)
|
|
||||||
|
|
||||||
type DeployerConfig struct {
|
|
||||||
// 京东云 AccessKeyId。
|
|
||||||
AccessKeyId string `json:"accessKeyId"`
|
|
||||||
// 京东云 AccessKeySecret。
|
|
||||||
AccessKeySecret string `json:"accessKeySecret"`
|
|
||||||
// 京东云地域 ID。
|
|
||||||
RegionId string `json:"regionId"`
|
|
||||||
// 部署资源类型。
|
|
||||||
ResourceType ResourceType `json:"resourceType"`
|
|
||||||
// 负载均衡器 ID。
|
|
||||||
// 部署资源类型为 [RESOURCE_TYPE_LOADBALANCER] 时必填。
|
|
||||||
LoadbalancerId string `json:"loadbalancerId,omitempty"`
|
|
||||||
// 监听器 ID。
|
|
||||||
// 部署资源类型为 [RESOURCE_TYPE_LISTENER] 时必填。
|
|
||||||
ListenerId string `json:"listenerId,omitempty"`
|
|
||||||
// SNI 域名(支持泛域名)。
|
|
||||||
// 部署资源类型为 [RESOURCE_TYPE_LOADBALANCER]、[RESOURCE_TYPE_LISTENER] 时选填。
|
|
||||||
Domain string `json:"domain,omitempty"`
|
|
||||||
}
|
|
||||||
|
|
||||||
type DeployerProvider struct {
|
|
||||||
config *DeployerConfig
|
|
||||||
logger logger.Logger
|
|
||||||
sdkClient *jdLbClient.LbClient
|
|
||||||
sslUploader uploader.Uploader
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ deployer.Deployer = (*DeployerProvider)(nil)
|
|
||||||
|
|
||||||
func NewDeployer(config *DeployerConfig) (*DeployerProvider, error) {
|
|
||||||
if config == nil {
|
|
||||||
panic("config is nil")
|
|
||||||
}
|
|
||||||
|
|
||||||
client, err := createSdkClient(config.AccessKeyId, config.AccessKeySecret)
|
|
||||||
if err != nil {
|
|
||||||
return nil, xerrors.Wrap(err, "failed to create sdk client")
|
|
||||||
}
|
|
||||||
|
|
||||||
uploader, err := uploadersp.NewUploader(&uploadersp.UploaderConfig{
|
|
||||||
AccessKeyId: config.AccessKeyId,
|
|
||||||
AccessKeySecret: config.AccessKeySecret,
|
|
||||||
})
|
|
||||||
if err != nil {
|
|
||||||
return nil, xerrors.Wrap(err, "failed to create ssl uploader")
|
|
||||||
}
|
|
||||||
|
|
||||||
return &DeployerProvider{
|
|
||||||
config: config,
|
|
||||||
logger: logger.NewNilLogger(),
|
|
||||||
sdkClient: client,
|
|
||||||
sslUploader: uploader,
|
|
||||||
}, nil
|
|
||||||
}
|
|
||||||
|
|
||||||
func (d *DeployerProvider) WithLogger(logger logger.Logger) *DeployerProvider {
|
|
||||||
d.logger = logger
|
|
||||||
return d
|
|
||||||
}
|
|
||||||
|
|
||||||
func (d *DeployerProvider) Deploy(ctx context.Context, certPem string, privkeyPem string) (*deployer.DeployResult, error) {
|
|
||||||
// 上传证书到 SSL
|
|
||||||
upres, err := d.sslUploader.Upload(ctx, certPem, privkeyPem)
|
|
||||||
if err != nil {
|
|
||||||
return nil, xerrors.Wrap(err, "failed to upload certificate file")
|
|
||||||
} else {
|
|
||||||
d.logger.Logt("certificate file uploaded", upres)
|
|
||||||
}
|
|
||||||
|
|
||||||
// 根据部署资源类型决定部署方式
|
|
||||||
switch d.config.ResourceType {
|
|
||||||
case RESOURCE_TYPE_LOADBALANCER:
|
|
||||||
if err := d.deployToLoadbalancer(ctx, upres.CertId); err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
|
|
||||||
case RESOURCE_TYPE_LISTENER:
|
|
||||||
if err := d.deployToListener(ctx, upres.CertId); err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
|
|
||||||
default:
|
|
||||||
return nil, fmt.Errorf("unsupported resource type: %s", d.config.ResourceType)
|
|
||||||
}
|
|
||||||
|
|
||||||
return &deployer.DeployResult{}, nil
|
|
||||||
}
|
|
||||||
|
|
||||||
func (d *DeployerProvider) deployToLoadbalancer(ctx context.Context, cloudCertId string) error {
|
|
||||||
if d.config.LoadbalancerId == "" {
|
|
||||||
return errors.New("config `loadbalancerId` is required")
|
|
||||||
}
|
|
||||||
|
|
||||||
// 查询负载均衡器详情
|
|
||||||
// REF: https://docs.jdcloud.com/cn/load-balancer/api/describeloadbalancer
|
|
||||||
describeLoadBalancerReq := jdLbApi.NewDescribeLoadBalancerRequest(d.config.RegionId, d.config.LoadbalancerId)
|
|
||||||
describeLoadBalancerResp, err := d.sdkClient.DescribeLoadBalancer(describeLoadBalancerReq)
|
|
||||||
if err != nil {
|
|
||||||
return xerrors.Wrap(err, "failed to execute sdk request 'lb.DescribeLoadBalancer'")
|
|
||||||
} else {
|
|
||||||
d.logger.Logt("已查询到负载均衡器详情", describeLoadBalancerResp)
|
|
||||||
}
|
|
||||||
|
|
||||||
// 查询监听器列表
|
|
||||||
// REF: https://docs.jdcloud.com/cn/load-balancer/api/describelisteners
|
|
||||||
listenerIds := make([]string, 0)
|
|
||||||
describeListenersPageNumber := 1
|
|
||||||
describeListenersPageSize := 100
|
|
||||||
for {
|
|
||||||
describeListenersReq := jdLbApi.NewDescribeListenersRequest(d.config.RegionId)
|
|
||||||
describeListenersReq.SetFilters([]jdCommon.Filter{{Name: "loadBalancerId", Values: []string{d.config.LoadbalancerId}}})
|
|
||||||
describeListenersReq.SetPageSize(describeListenersPageNumber)
|
|
||||||
describeListenersReq.SetPageSize(describeListenersPageSize)
|
|
||||||
describeListenersResp, err := d.sdkClient.DescribeListeners(describeListenersReq)
|
|
||||||
if err != nil {
|
|
||||||
return xerrors.Wrap(err, "failed to execute sdk request 'lb.DescribeListeners'")
|
|
||||||
}
|
|
||||||
|
|
||||||
for _, listener := range describeListenersResp.Result.Listeners {
|
|
||||||
if strings.EqualFold(listener.Protocol, "https") || strings.EqualFold(listener.Protocol, "tls") {
|
|
||||||
listenerIds = append(listenerIds, listener.ListenerId)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if len(describeListenersResp.Result.Listeners) < int(describeListenersPageSize) {
|
|
||||||
break
|
|
||||||
} else {
|
|
||||||
describeListenersPageNumber++
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// 遍历更新监听器证书
|
|
||||||
if len(listenerIds) == 0 {
|
|
||||||
return errors.New("listener not found")
|
|
||||||
} else {
|
|
||||||
d.logger.Logt("已查询到负载均衡器下的全部 HTTPS/TLS 监听器", listenerIds)
|
|
||||||
|
|
||||||
var errs []error
|
|
||||||
|
|
||||||
for _, listenerId := range listenerIds {
|
|
||||||
if err := d.updateListenerCertificate(ctx, listenerId, cloudCertId); err != nil {
|
|
||||||
errs = append(errs, err)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if len(errs) > 0 {
|
|
||||||
return errors.Join(errs...)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
func (d *DeployerProvider) deployToListener(ctx context.Context, cloudCertId string) error {
|
|
||||||
if d.config.ListenerId == "" {
|
|
||||||
return errors.New("config `listenerId` is required")
|
|
||||||
}
|
|
||||||
|
|
||||||
// 更新监听器证书
|
|
||||||
if err := d.updateListenerCertificate(ctx, d.config.ListenerId, cloudCertId); err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
func (d *DeployerProvider) updateListenerCertificate(ctx context.Context, cloudListenerId string, cloudCertId string) error {
|
|
||||||
// 查询监听器详情
|
|
||||||
// REF: https://docs.jdcloud.com/cn/load-balancer/api/describelistener
|
|
||||||
describeListenerReq := jdLbApi.NewDescribeListenerRequest(d.config.RegionId, cloudListenerId)
|
|
||||||
describeListenerResp, err := d.sdkClient.DescribeListener(describeListenerReq)
|
|
||||||
if err != nil {
|
|
||||||
return xerrors.Wrap(err, "failed to execute sdk request 'lb.DescribeListener'")
|
|
||||||
} else {
|
|
||||||
d.logger.Logt("已查询到监听器详情", describeListenerResp)
|
|
||||||
}
|
|
||||||
|
|
||||||
if d.config.Domain == "" {
|
|
||||||
// 未指定 SNI,只需部署到监听器
|
|
||||||
|
|
||||||
// 修改监听器信息
|
|
||||||
// REF: https://docs.jdcloud.com/cn/load-balancer/api/updatelistener
|
|
||||||
updateListenerReq := jdLbApi.NewUpdateListenerRequest(d.config.RegionId, cloudListenerId)
|
|
||||||
updateListenerReq.SetCertificateSpecs([]jdLbModel.CertificateSpec{{CertificateId: cloudCertId}})
|
|
||||||
updateListenerResp, err := d.sdkClient.UpdateListener(updateListenerReq)
|
|
||||||
if err != nil {
|
|
||||||
return xerrors.Wrap(err, "failed to execute sdk request 'lb.UpdateListener'")
|
|
||||||
} else {
|
|
||||||
d.logger.Logt("已修改监听器信息", updateListenerResp)
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
// 指定 SNI,需部署到扩展证书
|
|
||||||
|
|
||||||
extCertSpecs := slices.Filter(describeListenerResp.Result.Listener.ExtensionCertificateSpecs, func(extCertSpec jdLbModel.ExtensionCertificateSpec) bool {
|
|
||||||
return extCertSpec.Domain == d.config.Domain
|
|
||||||
})
|
|
||||||
if len(extCertSpecs) == 0 {
|
|
||||||
return errors.New("extension certificate spec not found")
|
|
||||||
}
|
|
||||||
|
|
||||||
// 批量修改扩展证书
|
|
||||||
// REF: https://docs.jdcloud.com/cn/load-balancer/api/updatelistenercertificates
|
|
||||||
updateListenerCertificatesReq := jdLbApi.NewUpdateListenerCertificatesRequest(
|
|
||||||
d.config.RegionId,
|
|
||||||
cloudListenerId,
|
|
||||||
slices.Map(extCertSpecs, func(extCertSpec jdLbModel.ExtensionCertificateSpec) jdLbModel.ExtCertificateUpdateSpec {
|
|
||||||
return jdLbModel.ExtCertificateUpdateSpec{
|
|
||||||
CertificateBindId: extCertSpec.CertificateBindId,
|
|
||||||
CertificateId: &cloudCertId,
|
|
||||||
Domain: &extCertSpec.Domain,
|
|
||||||
}
|
|
||||||
}),
|
|
||||||
)
|
|
||||||
updateListenerCertificatesResp, err := d.sdkClient.UpdateListenerCertificates(updateListenerCertificatesReq)
|
|
||||||
if err != nil {
|
|
||||||
return xerrors.Wrap(err, "failed to execute sdk request 'lb.UpdateListenerCertificates'")
|
|
||||||
} else {
|
|
||||||
d.logger.Logt("已批量修改扩展证书", updateListenerCertificatesResp)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
func createSdkClient(accessKeyId, accessKeySecret string) (*jdLbClient.LbClient, error) {
|
|
||||||
clientCredentials := jdCore.NewCredentials(accessKeyId, accessKeySecret)
|
|
||||||
client := jdLbClient.NewLbClient(clientCredentials)
|
|
||||||
return client, nil
|
|
||||||
}
|
|
@ -1,118 +0,0 @@
|
|||||||
package jdcloudalb_test
|
|
||||||
|
|
||||||
import (
|
|
||||||
"context"
|
|
||||||
"flag"
|
|
||||||
"fmt"
|
|
||||||
"os"
|
|
||||||
"strings"
|
|
||||||
"testing"
|
|
||||||
|
|
||||||
provider "github.com/usual2970/certimate/internal/pkg/core/deployer/providers/jdcloud-alb"
|
|
||||||
)
|
|
||||||
|
|
||||||
var (
|
|
||||||
fInputCertPath string
|
|
||||||
fInputKeyPath string
|
|
||||||
fAccessKeyId string
|
|
||||||
fAccessKeySecret string
|
|
||||||
fRegionId string
|
|
||||||
fLoadbalancerId string
|
|
||||||
fListenerId string
|
|
||||||
)
|
|
||||||
|
|
||||||
func init() {
|
|
||||||
argsPrefix := "CERTIMATE_DEPLOYER_JDCLOUDALB_"
|
|
||||||
|
|
||||||
flag.StringVar(&fInputCertPath, argsPrefix+"INPUTCERTPATH", "", "")
|
|
||||||
flag.StringVar(&fInputKeyPath, argsPrefix+"INPUTKEYPATH", "", "")
|
|
||||||
flag.StringVar(&fAccessKeyId, argsPrefix+"ACCESSKEYID", "", "")
|
|
||||||
flag.StringVar(&fAccessKeySecret, argsPrefix+"ACCESSKEYSECRET", "", "")
|
|
||||||
flag.StringVar(&fRegionId, argsPrefix+"REGIONID", "", "")
|
|
||||||
flag.StringVar(&fLoadbalancerId, argsPrefix+"LOADBALANCERID", "", "")
|
|
||||||
flag.StringVar(&fListenerId, argsPrefix+"LISTENERID", "", "")
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
Shell command to run this test:
|
|
||||||
|
|
||||||
go test -v ./jdcloud_alb_test.go -args \
|
|
||||||
--CERTIMATE_DEPLOYER_JDCLOUDALB_INPUTCERTPATH="/path/to/your-input-cert.pem" \
|
|
||||||
--CERTIMATE_DEPLOYER_JDCLOUDALB_INPUTKEYPATH="/path/to/your-input-key.pem" \
|
|
||||||
--CERTIMATE_DEPLOYER_JDCLOUDALB_ACCESSKEYID="your-access-key-id" \
|
|
||||||
--CERTIMATE_DEPLOYER_JDCLOUDALB_ACCESSKEYSECRET="your-secret-access-key" \
|
|
||||||
--CERTIMATE_DEPLOYER_JDCLOUDALB_REGION_ID="cn-north-1" \
|
|
||||||
--CERTIMATE_DEPLOYER_JDCLOUDALB_LOADBALANCERID="your-alb-loadbalancer-id" \
|
|
||||||
--CERTIMATE_DEPLOYER_JDCLOUDALB_LISTENERID="your-alb-listener-id"
|
|
||||||
*/
|
|
||||||
func TestDeploy(t *testing.T) {
|
|
||||||
flag.Parse()
|
|
||||||
|
|
||||||
t.Run("Deploy_ToLoadbalancer", func(t *testing.T) {
|
|
||||||
t.Log(strings.Join([]string{
|
|
||||||
"args:",
|
|
||||||
fmt.Sprintf("INPUTCERTPATH: %v", fInputCertPath),
|
|
||||||
fmt.Sprintf("INPUTKEYPATH: %v", fInputKeyPath),
|
|
||||||
fmt.Sprintf("ACCESSKEYID: %v", fAccessKeyId),
|
|
||||||
fmt.Sprintf("ACCESSKEYSECRET: %v", fAccessKeySecret),
|
|
||||||
fmt.Sprintf("REGIONID: %v", fRegionId),
|
|
||||||
fmt.Sprintf("LOADBALANCERID: %v", fLoadbalancerId),
|
|
||||||
}, "\n"))
|
|
||||||
|
|
||||||
deployer, err := provider.NewDeployer(&provider.DeployerConfig{
|
|
||||||
AccessKeyId: fAccessKeyId,
|
|
||||||
AccessKeySecret: fAccessKeySecret,
|
|
||||||
RegionId: fRegionId,
|
|
||||||
ResourceType: provider.RESOURCE_TYPE_LOADBALANCER,
|
|
||||||
LoadbalancerId: fLoadbalancerId,
|
|
||||||
})
|
|
||||||
if err != nil {
|
|
||||||
t.Errorf("err: %+v", err)
|
|
||||||
return
|
|
||||||
}
|
|
||||||
|
|
||||||
fInputCertData, _ := os.ReadFile(fInputCertPath)
|
|
||||||
fInputKeyData, _ := os.ReadFile(fInputKeyPath)
|
|
||||||
res, err := deployer.Deploy(context.Background(), string(fInputCertData), string(fInputKeyData))
|
|
||||||
if err != nil {
|
|
||||||
t.Errorf("err: %+v", err)
|
|
||||||
return
|
|
||||||
}
|
|
||||||
|
|
||||||
t.Logf("ok: %v", res)
|
|
||||||
})
|
|
||||||
|
|
||||||
t.Run("Deploy_ToListener", func(t *testing.T) {
|
|
||||||
t.Log(strings.Join([]string{
|
|
||||||
"args:",
|
|
||||||
fmt.Sprintf("INPUTCERTPATH: %v", fInputCertPath),
|
|
||||||
fmt.Sprintf("INPUTKEYPATH: %v", fInputKeyPath),
|
|
||||||
fmt.Sprintf("ACCESSKEYID: %v", fAccessKeyId),
|
|
||||||
fmt.Sprintf("ACCESSKEYSECRET: %v", fAccessKeySecret),
|
|
||||||
fmt.Sprintf("REGIONID: %v", fRegionId),
|
|
||||||
fmt.Sprintf("LISTENERID: %v", fListenerId),
|
|
||||||
}, "\n"))
|
|
||||||
|
|
||||||
deployer, err := provider.NewDeployer(&provider.DeployerConfig{
|
|
||||||
AccessKeyId: fAccessKeyId,
|
|
||||||
AccessKeySecret: fAccessKeySecret,
|
|
||||||
RegionId: fRegionId,
|
|
||||||
ResourceType: provider.RESOURCE_TYPE_LISTENER,
|
|
||||||
ListenerId: fListenerId,
|
|
||||||
})
|
|
||||||
if err != nil {
|
|
||||||
t.Errorf("err: %+v", err)
|
|
||||||
return
|
|
||||||
}
|
|
||||||
|
|
||||||
fInputCertData, _ := os.ReadFile(fInputCertPath)
|
|
||||||
fInputKeyData, _ := os.ReadFile(fInputKeyPath)
|
|
||||||
res, err := deployer.Deploy(context.Background(), string(fInputCertData), string(fInputKeyData))
|
|
||||||
if err != nil {
|
|
||||||
t.Errorf("err: %+v", err)
|
|
||||||
return
|
|
||||||
}
|
|
||||||
|
|
||||||
t.Logf("ok: %v", res)
|
|
||||||
})
|
|
||||||
}
|
|
@ -10,8 +10,6 @@ import (
|
|||||||
|
|
||||||
"github.com/usual2970/certimate/internal/pkg/core/deployer"
|
"github.com/usual2970/certimate/internal/pkg/core/deployer"
|
||||||
"github.com/usual2970/certimate/internal/pkg/core/logger"
|
"github.com/usual2970/certimate/internal/pkg/core/logger"
|
||||||
"github.com/usual2970/certimate/internal/pkg/core/uploader"
|
|
||||||
uploadersp "github.com/usual2970/certimate/internal/pkg/core/uploader/providers/jdcloud-ssl"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
type DeployerConfig struct {
|
type DeployerConfig struct {
|
||||||
@ -24,10 +22,9 @@ type DeployerConfig struct {
|
|||||||
}
|
}
|
||||||
|
|
||||||
type DeployerProvider struct {
|
type DeployerProvider struct {
|
||||||
config *DeployerConfig
|
config *DeployerConfig
|
||||||
logger logger.Logger
|
logger logger.Logger
|
||||||
sdkClient *jdCdnClient.CdnClient
|
sdkClient *jdCdnClient.CdnClient
|
||||||
sslUploader uploader.Uploader
|
|
||||||
}
|
}
|
||||||
|
|
||||||
var _ deployer.Deployer = (*DeployerProvider)(nil)
|
var _ deployer.Deployer = (*DeployerProvider)(nil)
|
||||||
@ -42,19 +39,10 @@ func NewDeployer(config *DeployerConfig) (*DeployerProvider, error) {
|
|||||||
return nil, xerrors.Wrap(err, "failed to create sdk client")
|
return nil, xerrors.Wrap(err, "failed to create sdk client")
|
||||||
}
|
}
|
||||||
|
|
||||||
uploader, err := uploadersp.NewUploader(&uploadersp.UploaderConfig{
|
|
||||||
AccessKeyId: config.AccessKeyId,
|
|
||||||
AccessKeySecret: config.AccessKeySecret,
|
|
||||||
})
|
|
||||||
if err != nil {
|
|
||||||
return nil, xerrors.Wrap(err, "failed to create ssl uploader")
|
|
||||||
}
|
|
||||||
|
|
||||||
return &DeployerProvider{
|
return &DeployerProvider{
|
||||||
config: config,
|
config: config,
|
||||||
logger: logger.NewNilLogger(),
|
logger: logger.NewNilLogger(),
|
||||||
sdkClient: client,
|
sdkClient: client,
|
||||||
sslUploader: uploader,
|
|
||||||
}, nil
|
}, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -74,22 +62,14 @@ func (d *DeployerProvider) Deploy(ctx context.Context, certPem string, privkeyPe
|
|||||||
d.logger.Logt("已查询到域名配置信息", queryDomainConfigResp)
|
d.logger.Logt("已查询到域名配置信息", queryDomainConfigResp)
|
||||||
}
|
}
|
||||||
|
|
||||||
// 上传证书到 SSL
|
|
||||||
upres, err := d.sslUploader.Upload(ctx, certPem, privkeyPem)
|
|
||||||
if err != nil {
|
|
||||||
return nil, xerrors.Wrap(err, "failed to upload certificate file")
|
|
||||||
} else {
|
|
||||||
d.logger.Logt("certificate file uploaded", upres)
|
|
||||||
}
|
|
||||||
|
|
||||||
// 设置通讯协议
|
// 设置通讯协议
|
||||||
// REF: https://docs.jdcloud.com/cn/cdn/api/sethttptype
|
// REF: https://docs.jdcloud.com/cn/cdn/api/sethttptype
|
||||||
setHttpTypeReq := jdCdnApi.NewSetHttpTypeRequest(d.config.Domain)
|
setHttpTypeReq := jdCdnApi.NewSetHttpTypeRequest(d.config.Domain)
|
||||||
setHttpTypeReq.SetHttpType("https")
|
setHttpTypeReq.SetHttpType("https")
|
||||||
|
setHttpTypeReq.SetCertFrom("default")
|
||||||
setHttpTypeReq.SetCertificate(certPem)
|
setHttpTypeReq.SetCertificate(certPem)
|
||||||
setHttpTypeReq.SetRsaKey(privkeyPem)
|
setHttpTypeReq.SetRsaKey(privkeyPem)
|
||||||
setHttpTypeReq.SetCertFrom("ssl")
|
setHttpTypeReq.SetSyncToSsl(false)
|
||||||
setHttpTypeReq.SetSslCertId(upres.CertId)
|
|
||||||
setHttpTypeReq.SetJumpType(queryDomainConfigResp.Result.HttpsJumpType)
|
setHttpTypeReq.SetJumpType(queryDomainConfigResp.Result.HttpsJumpType)
|
||||||
setHttpTypeResp, err := d.sdkClient.SetHttpType(setHttpTypeReq)
|
setHttpTypeResp, err := d.sdkClient.SetHttpType(setHttpTypeReq)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
@ -20,7 +20,7 @@ var (
|
|||||||
)
|
)
|
||||||
|
|
||||||
func init() {
|
func init() {
|
||||||
argsPrefix := "CERTIMATE_DEPLOYER_JDCLOUDCDN_"
|
argsPrefix := "CERTIMATE_DEPLOYER_BAIDUCLOUDCDN_"
|
||||||
|
|
||||||
flag.StringVar(&fInputCertPath, argsPrefix+"INPUTCERTPATH", "", "")
|
flag.StringVar(&fInputCertPath, argsPrefix+"INPUTCERTPATH", "", "")
|
||||||
flag.StringVar(&fInputKeyPath, argsPrefix+"INPUTKEYPATH", "", "")
|
flag.StringVar(&fInputKeyPath, argsPrefix+"INPUTKEYPATH", "", "")
|
||||||
|
@ -20,7 +20,7 @@ var (
|
|||||||
)
|
)
|
||||||
|
|
||||||
func init() {
|
func init() {
|
||||||
argsPrefix := "CERTIMATE_DEPLOYER_JDCLOUDLIVE_"
|
argsPrefix := "CERTIMATE_DEPLOYER_BAIDUCLOUDCDN_"
|
||||||
|
|
||||||
flag.StringVar(&fInputCertPath, argsPrefix+"INPUTCERTPATH", "", "")
|
flag.StringVar(&fInputCertPath, argsPrefix+"INPUTCERTPATH", "", "")
|
||||||
flag.StringVar(&fInputKeyPath, argsPrefix+"INPUTKEYPATH", "", "")
|
flag.StringVar(&fInputKeyPath, argsPrefix+"INPUTKEYPATH", "", "")
|
||||||
|
@ -138,7 +138,7 @@ func (d *DeployerProvider) deployViaSslService(ctx context.Context, cloudCertId
|
|||||||
// 未指定 SNI,只需部署到监听器
|
// 未指定 SNI,只需部署到监听器
|
||||||
deployCertificateInstanceReq.InstanceIdList = common.StringPtrs([]string{fmt.Sprintf("%s|%s", d.config.LoadbalancerId, d.config.ListenerId)})
|
deployCertificateInstanceReq.InstanceIdList = common.StringPtrs([]string{fmt.Sprintf("%s|%s", d.config.LoadbalancerId, d.config.ListenerId)})
|
||||||
} else {
|
} else {
|
||||||
// 指定 SNI,需部署到域名
|
// 指定 SNI,需部署到域名(支持泛域名)
|
||||||
deployCertificateInstanceReq.InstanceIdList = common.StringPtrs([]string{fmt.Sprintf("%s|%s|%s", d.config.LoadbalancerId, d.config.ListenerId, d.config.Domain)})
|
deployCertificateInstanceReq.InstanceIdList = common.StringPtrs([]string{fmt.Sprintf("%s|%s|%s", d.config.LoadbalancerId, d.config.ListenerId, d.config.Domain)})
|
||||||
}
|
}
|
||||||
deployCertificateInstanceResp, err := d.sdkClients.ssl.DeployCertificateInstance(deployCertificateInstanceReq)
|
deployCertificateInstanceResp, err := d.sdkClients.ssl.DeployCertificateInstance(deployCertificateInstanceReq)
|
||||||
|
@ -1,138 +0,0 @@
|
|||||||
package jdcloudssl
|
|
||||||
|
|
||||||
import (
|
|
||||||
"context"
|
|
||||||
"crypto/sha256"
|
|
||||||
"encoding/hex"
|
|
||||||
"fmt"
|
|
||||||
"strings"
|
|
||||||
"time"
|
|
||||||
|
|
||||||
jdCore "github.com/jdcloud-api/jdcloud-sdk-go/core"
|
|
||||||
jdSslApi "github.com/jdcloud-api/jdcloud-sdk-go/services/ssl/apis"
|
|
||||||
jdSslClient "github.com/jdcloud-api/jdcloud-sdk-go/services/ssl/client"
|
|
||||||
xerrors "github.com/pkg/errors"
|
|
||||||
"golang.org/x/exp/slices"
|
|
||||||
|
|
||||||
"github.com/usual2970/certimate/internal/pkg/core/uploader"
|
|
||||||
"github.com/usual2970/certimate/internal/pkg/utils/certs"
|
|
||||||
)
|
|
||||||
|
|
||||||
type UploaderConfig struct {
|
|
||||||
// 京东云 AccessKeyId。
|
|
||||||
AccessKeyId string `json:"accessKeyId"`
|
|
||||||
// 京东云 AccessKeySecret。
|
|
||||||
AccessKeySecret string `json:"accessKeySecret"`
|
|
||||||
}
|
|
||||||
|
|
||||||
type UploaderProvider struct {
|
|
||||||
config *UploaderConfig
|
|
||||||
sdkClient *jdSslClient.SslClient
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ uploader.Uploader = (*UploaderProvider)(nil)
|
|
||||||
|
|
||||||
func NewUploader(config *UploaderConfig) (*UploaderProvider, error) {
|
|
||||||
if config == nil {
|
|
||||||
panic("config is nil")
|
|
||||||
}
|
|
||||||
|
|
||||||
client, err := createSdkClient(config.AccessKeyId, config.AccessKeySecret)
|
|
||||||
if err != nil {
|
|
||||||
return nil, xerrors.Wrap(err, "failed to create sdk client")
|
|
||||||
}
|
|
||||||
|
|
||||||
return &UploaderProvider{
|
|
||||||
config: config,
|
|
||||||
sdkClient: client,
|
|
||||||
}, nil
|
|
||||||
}
|
|
||||||
|
|
||||||
func (u *UploaderProvider) Upload(ctx context.Context, certPem string, privkeyPem string) (res *uploader.UploadResult, err error) {
|
|
||||||
// 解析证书内容
|
|
||||||
certX509, err := certs.ParseCertificateFromPEM(certPem)
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
|
|
||||||
// 格式化私钥内容,以便后续计算私钥摘要
|
|
||||||
privkeyPem = strings.TrimSpace(privkeyPem)
|
|
||||||
privkeyPem = strings.ReplaceAll(privkeyPem, "\r", "")
|
|
||||||
privkeyPem = strings.ReplaceAll(privkeyPem, "\n", "\r\n")
|
|
||||||
privkeyPem = privkeyPem + "\r\n"
|
|
||||||
|
|
||||||
// 遍历查看证书列表,避免重复上传
|
|
||||||
// REF: https://docs.jdcloud.com/cn/ssl-certificate/api/describecerts
|
|
||||||
describeCertsPageNumber := 1
|
|
||||||
describeCertsPageSize := 100
|
|
||||||
for {
|
|
||||||
describeCertsReq := jdSslApi.NewDescribeCertsRequest()
|
|
||||||
describeCertsReq.DomainName = &certX509.Subject.CommonName
|
|
||||||
describeCertsReq.PageNumber = &describeCertsPageNumber
|
|
||||||
describeCertsReq.PageSize = &describeCertsPageSize
|
|
||||||
describeCertsResp, err := u.sdkClient.DescribeCerts(describeCertsReq)
|
|
||||||
if err != nil {
|
|
||||||
return nil, xerrors.Wrap(err, "failed to execute sdk request 'ssl.DescribeCerts'")
|
|
||||||
}
|
|
||||||
|
|
||||||
for _, certDetail := range describeCertsResp.Result.CertListDetails {
|
|
||||||
// 先尝试匹配 CN
|
|
||||||
if !strings.EqualFold(certX509.Subject.CommonName, certDetail.CommonName) {
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
|
|
||||||
// 再尝试匹配 SAN
|
|
||||||
if !slices.Equal(certX509.DNSNames, certDetail.DnsNames) {
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
|
|
||||||
// 再尝试匹配证书有效期
|
|
||||||
oldCertNotBefore, _ := time.Parse(time.RFC3339, certDetail.StartTime)
|
|
||||||
oldCertNotAfter, _ := time.Parse(time.RFC3339, certDetail.EndTime)
|
|
||||||
if !certX509.NotBefore.Equal(oldCertNotBefore) || !certX509.NotAfter.Equal(oldCertNotAfter) {
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
|
|
||||||
// 最后尝试匹配私钥摘要
|
|
||||||
newKeyDigest := sha256.Sum256([]byte(privkeyPem))
|
|
||||||
newKeyDigestHex := hex.EncodeToString(newKeyDigest[:])
|
|
||||||
if !strings.EqualFold(newKeyDigestHex, certDetail.Digest) {
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
|
|
||||||
// 如果以上都匹配,则视为已存在相同证书,直接返回已有的证书信息
|
|
||||||
return &uploader.UploadResult{
|
|
||||||
CertId: certDetail.CertId,
|
|
||||||
CertName: certDetail.CertName,
|
|
||||||
}, nil
|
|
||||||
}
|
|
||||||
|
|
||||||
if len(describeCertsResp.Result.CertListDetails) < int(describeCertsPageSize) {
|
|
||||||
break
|
|
||||||
} else {
|
|
||||||
describeCertsPageNumber++
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// 生成新证书名(需符合京东云命名规则)
|
|
||||||
certName := fmt.Sprintf("certimate-%d", time.Now().UnixMilli())
|
|
||||||
|
|
||||||
// 上传证书
|
|
||||||
// REF: https://docs.jdcloud.com/cn/ssl-certificate/api/uploadcert
|
|
||||||
uploadCertReq := jdSslApi.NewUploadCertRequest(certName, privkeyPem, certPem)
|
|
||||||
uploadCertResp, err := u.sdkClient.UploadCert(uploadCertReq)
|
|
||||||
if err != nil {
|
|
||||||
return nil, xerrors.Wrap(err, "failed to execute sdk request 'ssl.UploadCertificate'")
|
|
||||||
}
|
|
||||||
|
|
||||||
return &uploader.UploadResult{
|
|
||||||
CertId: uploadCertResp.Result.CertId,
|
|
||||||
CertName: certName,
|
|
||||||
}, nil
|
|
||||||
}
|
|
||||||
|
|
||||||
func createSdkClient(accessKeyId, accessKeySecret string) (*jdSslClient.SslClient, error) {
|
|
||||||
clientCredentials := jdCore.NewCredentials(accessKeyId, accessKeySecret)
|
|
||||||
client := jdSslClient.NewSslClient(clientCredentials)
|
|
||||||
return client, nil
|
|
||||||
}
|
|
@ -1,72 +0,0 @@
|
|||||||
package jdcloudssl_test
|
|
||||||
|
|
||||||
import (
|
|
||||||
"context"
|
|
||||||
"encoding/json"
|
|
||||||
"flag"
|
|
||||||
"fmt"
|
|
||||||
"os"
|
|
||||||
"strings"
|
|
||||||
"testing"
|
|
||||||
|
|
||||||
provider "github.com/usual2970/certimate/internal/pkg/core/uploader/providers/jdcloud-ssl"
|
|
||||||
)
|
|
||||||
|
|
||||||
var (
|
|
||||||
fInputCertPath string
|
|
||||||
fInputKeyPath string
|
|
||||||
fAccessKeyId string
|
|
||||||
fAccessKeySecret string
|
|
||||||
)
|
|
||||||
|
|
||||||
func init() {
|
|
||||||
argsPrefix := "CERTIMATE_UPLOADER_JDCLOUDSSL_"
|
|
||||||
|
|
||||||
flag.StringVar(&fInputCertPath, argsPrefix+"INPUTCERTPATH", "", "")
|
|
||||||
flag.StringVar(&fInputKeyPath, argsPrefix+"INPUTKEYPATH", "", "")
|
|
||||||
flag.StringVar(&fAccessKeyId, argsPrefix+"ACCESSKEYID", "", "")
|
|
||||||
flag.StringVar(&fAccessKeySecret, argsPrefix+"ACCESSKEYSECRET", "", "")
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
Shell command to run this test:
|
|
||||||
|
|
||||||
go test -v ./jdcloud_ssl_test.go -args \
|
|
||||||
--CERTIMATE_UPLOADER_JDCLOUDSSL_INPUTCERTPATH="/path/to/your-input-cert.pem" \
|
|
||||||
--CERTIMATE_UPLOADER_JDCLOUDSSL_INPUTKEYPATH="/path/to/your-input-key.pem" \
|
|
||||||
--CERTIMATE_UPLOADER_JDCLOUDSSL_ACCESSKEYID="your-access-key-id" \
|
|
||||||
--CERTIMATE_UPLOADER_JDCLOUDSSL_ACCESSKEYSECRET="your-access-key-secret"
|
|
||||||
*/
|
|
||||||
func TestDeploy(t *testing.T) {
|
|
||||||
flag.Parse()
|
|
||||||
|
|
||||||
t.Run("Deploy", func(t *testing.T) {
|
|
||||||
t.Log(strings.Join([]string{
|
|
||||||
"args:",
|
|
||||||
fmt.Sprintf("INPUTCERTPATH: %v", fInputCertPath),
|
|
||||||
fmt.Sprintf("INPUTKEYPATH: %v", fInputKeyPath),
|
|
||||||
fmt.Sprintf("ACCESSKEYID: %v", fAccessKeyId),
|
|
||||||
fmt.Sprintf("ACCESSKEYSECRET: %v", fAccessKeySecret),
|
|
||||||
}, "\n"))
|
|
||||||
|
|
||||||
uploader, err := provider.NewUploader(&provider.UploaderConfig{
|
|
||||||
AccessKeyId: fAccessKeyId,
|
|
||||||
AccessKeySecret: fAccessKeySecret,
|
|
||||||
})
|
|
||||||
if err != nil {
|
|
||||||
t.Errorf("err: %+v", err)
|
|
||||||
return
|
|
||||||
}
|
|
||||||
|
|
||||||
fInputCertData, _ := os.ReadFile(fInputCertPath)
|
|
||||||
fInputKeyData, _ := os.ReadFile(fInputKeyPath)
|
|
||||||
res, err := uploader.Upload(context.Background(), string(fInputCertData), string(fInputKeyData))
|
|
||||||
if err != nil {
|
|
||||||
t.Errorf("err: %+v", err)
|
|
||||||
return
|
|
||||||
}
|
|
||||||
|
|
||||||
sres, _ := json.Marshal(res)
|
|
||||||
t.Logf("ok: %s", string(sres))
|
|
||||||
})
|
|
||||||
}
|
|
@ -38,7 +38,6 @@ import DeployNodeConfigFormGcoreCDNConfig from "./DeployNodeConfigFormGcoreCDNCo
|
|||||||
import DeployNodeConfigFormHuaweiCloudCDNConfig from "./DeployNodeConfigFormHuaweiCloudCDNConfig";
|
import DeployNodeConfigFormHuaweiCloudCDNConfig from "./DeployNodeConfigFormHuaweiCloudCDNConfig";
|
||||||
import DeployNodeConfigFormHuaweiCloudELBConfig from "./DeployNodeConfigFormHuaweiCloudELBConfig";
|
import DeployNodeConfigFormHuaweiCloudELBConfig from "./DeployNodeConfigFormHuaweiCloudELBConfig";
|
||||||
import DeployNodeConfigFormHuaweiCloudWAFConfig from "./DeployNodeConfigFormHuaweiCloudWAFConfig";
|
import DeployNodeConfigFormHuaweiCloudWAFConfig from "./DeployNodeConfigFormHuaweiCloudWAFConfig";
|
||||||
import DeployNodeConfigFormJDCloudALBConfig from "./DeployNodeConfigFormJDCloudALBConfig";
|
|
||||||
import DeployNodeConfigFormJDCloudCDNConfig from "./DeployNodeConfigFormJDCloudCDNConfig";
|
import DeployNodeConfigFormJDCloudCDNConfig from "./DeployNodeConfigFormJDCloudCDNConfig";
|
||||||
import DeployNodeConfigFormJDCloudLiveConfig from "./DeployNodeConfigFormJDCloudLiveConfig";
|
import DeployNodeConfigFormJDCloudLiveConfig from "./DeployNodeConfigFormJDCloudLiveConfig";
|
||||||
import DeployNodeConfigFormKubernetesSecretConfig from "./DeployNodeConfigFormKubernetesSecretConfig";
|
import DeployNodeConfigFormKubernetesSecretConfig from "./DeployNodeConfigFormKubernetesSecretConfig";
|
||||||
@ -181,8 +180,6 @@ const DeployNodeConfigForm = forwardRef<DeployNodeConfigFormInstance, DeployNode
|
|||||||
return <DeployNodeConfigFormHuaweiCloudELBConfig {...nestedFormProps} />;
|
return <DeployNodeConfigFormHuaweiCloudELBConfig {...nestedFormProps} />;
|
||||||
case DEPLOY_PROVIDERS.HUAWEICLOUD_WAF:
|
case DEPLOY_PROVIDERS.HUAWEICLOUD_WAF:
|
||||||
return <DeployNodeConfigFormHuaweiCloudWAFConfig {...nestedFormProps} />;
|
return <DeployNodeConfigFormHuaweiCloudWAFConfig {...nestedFormProps} />;
|
||||||
case DEPLOY_PROVIDERS.JDCLOUD_ALB:
|
|
||||||
return <DeployNodeConfigFormJDCloudALBConfig {...nestedFormProps} />;
|
|
||||||
case DEPLOY_PROVIDERS.JDCLOUD_CDN:
|
case DEPLOY_PROVIDERS.JDCLOUD_CDN:
|
||||||
return <DeployNodeConfigFormJDCloudCDNConfig {...nestedFormProps} />;
|
return <DeployNodeConfigFormJDCloudCDNConfig {...nestedFormProps} />;
|
||||||
case DEPLOY_PROVIDERS.JDCLOUD_LIVE:
|
case DEPLOY_PROVIDERS.JDCLOUD_LIVE:
|
||||||
|
@ -1,142 +0,0 @@
|
|||||||
import { useTranslation } from "react-i18next";
|
|
||||||
import { Form, type FormInstance, Input, Select } from "antd";
|
|
||||||
import { createSchemaFieldRule } from "antd-zod";
|
|
||||||
import { z } from "zod";
|
|
||||||
|
|
||||||
import Show from "@/components/Show";
|
|
||||||
import { validDomainName } from "@/utils/validators";
|
|
||||||
|
|
||||||
type DeployNodeConfigFormJDCloudALBConfigFieldValues = Nullish<{
|
|
||||||
resourceType: string;
|
|
||||||
regionId: string;
|
|
||||||
loadbalancerId?: string;
|
|
||||||
listenerId?: string;
|
|
||||||
domain?: string;
|
|
||||||
}>;
|
|
||||||
|
|
||||||
export type DeployNodeConfigFormJDCloudALBConfigProps = {
|
|
||||||
form: FormInstance;
|
|
||||||
formName: string;
|
|
||||||
disabled?: boolean;
|
|
||||||
initialValues?: DeployNodeConfigFormJDCloudALBConfigFieldValues;
|
|
||||||
onValuesChange?: (values: DeployNodeConfigFormJDCloudALBConfigFieldValues) => void;
|
|
||||||
};
|
|
||||||
|
|
||||||
const RESOURCE_TYPE_LOADBALANCER = "loadbalancer" as const;
|
|
||||||
const RESOURCE_TYPE_LISTENER = "listener" as const;
|
|
||||||
|
|
||||||
const initFormModel = (): DeployNodeConfigFormJDCloudALBConfigFieldValues => {
|
|
||||||
return {};
|
|
||||||
};
|
|
||||||
|
|
||||||
const DeployNodeConfigFormJDCloudALBConfig = ({
|
|
||||||
form: formInst,
|
|
||||||
formName,
|
|
||||||
disabled,
|
|
||||||
initialValues,
|
|
||||||
onValuesChange,
|
|
||||||
}: DeployNodeConfigFormJDCloudALBConfigProps) => {
|
|
||||||
const { t } = useTranslation();
|
|
||||||
|
|
||||||
const formSchema = z.object({
|
|
||||||
resourceType: z.union([z.literal(RESOURCE_TYPE_LOADBALANCER), z.literal(RESOURCE_TYPE_LISTENER)], {
|
|
||||||
message: t("workflow_node.deploy.form.jdcloud_alb_resource_type.placeholder"),
|
|
||||||
}),
|
|
||||||
regionId: z
|
|
||||||
.string({ message: t("workflow_node.deploy.form.jdcloud_alb_region_id.placeholder") })
|
|
||||||
.nonempty(t("workflow_node.deploy.form.jdcloud_alb_region_id.placeholder"))
|
|
||||||
.trim(),
|
|
||||||
loadbalancerId: z
|
|
||||||
.string()
|
|
||||||
.max(64, t("common.errmsg.string_max", { max: 64 }))
|
|
||||||
.trim()
|
|
||||||
.nullish()
|
|
||||||
.refine((v) => fieldResourceType !== RESOURCE_TYPE_LOADBALANCER || !!v?.trim(), t("workflow_node.deploy.form.jdcloud_alb_loadbalancer_id.placeholder")),
|
|
||||||
listenerId: z
|
|
||||||
.string()
|
|
||||||
.max(64, t("common.errmsg.string_max", { max: 64 }))
|
|
||||||
.trim()
|
|
||||||
.nullish()
|
|
||||||
.refine((v) => fieldResourceType !== RESOURCE_TYPE_LISTENER || !!v?.trim(), t("workflow_node.deploy.form.jdcloud_alb_listener_id.placeholder")),
|
|
||||||
domain: z
|
|
||||||
.string()
|
|
||||||
.nullish()
|
|
||||||
.refine((v) => {
|
|
||||||
if (![RESOURCE_TYPE_LOADBALANCER, RESOURCE_TYPE_LISTENER].includes(fieldResourceType)) return true;
|
|
||||||
return !v || validDomainName(v!, { allowWildcard: true });
|
|
||||||
}, t("common.errmsg.domain_invalid")),
|
|
||||||
});
|
|
||||||
const formRule = createSchemaFieldRule(formSchema);
|
|
||||||
|
|
||||||
const fieldResourceType = Form.useWatch("resourceType", formInst);
|
|
||||||
|
|
||||||
const handleFormChange = (_: unknown, values: z.infer<typeof formSchema>) => {
|
|
||||||
onValuesChange?.(values);
|
|
||||||
};
|
|
||||||
|
|
||||||
return (
|
|
||||||
<Form
|
|
||||||
form={formInst}
|
|
||||||
disabled={disabled}
|
|
||||||
initialValues={initialValues ?? initFormModel()}
|
|
||||||
layout="vertical"
|
|
||||||
name={formName}
|
|
||||||
onValuesChange={handleFormChange}
|
|
||||||
>
|
|
||||||
<Form.Item name="resourceType" label={t("workflow_node.deploy.form.jdcloud_alb_resource_type.label")} rules={[formRule]}>
|
|
||||||
<Select placeholder={t("workflow_node.deploy.form.jdcloud_alb_resource_type.placeholder")}>
|
|
||||||
<Select.Option key={RESOURCE_TYPE_LOADBALANCER} value={RESOURCE_TYPE_LOADBALANCER}>
|
|
||||||
{t("workflow_node.deploy.form.jdcloud_alb_resource_type.option.loadbalancer.label")}
|
|
||||||
</Select.Option>
|
|
||||||
<Select.Option key={RESOURCE_TYPE_LISTENER} value={RESOURCE_TYPE_LISTENER}>
|
|
||||||
{t("workflow_node.deploy.form.jdcloud_alb_resource_type.option.listener.label")}
|
|
||||||
</Select.Option>
|
|
||||||
</Select>
|
|
||||||
</Form.Item>
|
|
||||||
|
|
||||||
<Form.Item
|
|
||||||
name="regionId"
|
|
||||||
label={t("workflow_node.deploy.form.jdcloud_alb_region_id.label")}
|
|
||||||
rules={[formRule]}
|
|
||||||
tooltip={<span dangerouslySetInnerHTML={{ __html: t("workflow_node.deploy.form.jdcloud_alb_region_id.tooltip") }}></span>}
|
|
||||||
>
|
|
||||||
<Input placeholder={t("workflow_node.deploy.form.jdcloud_alb_region_id.placeholder")} />
|
|
||||||
</Form.Item>
|
|
||||||
|
|
||||||
<Show when={fieldResourceType === RESOURCE_TYPE_LOADBALANCER}>
|
|
||||||
<Form.Item
|
|
||||||
name="loadbalancerId"
|
|
||||||
label={t("workflow_node.deploy.form.jdcloud_alb_loadbalancer_id.label")}
|
|
||||||
rules={[formRule]}
|
|
||||||
tooltip={<span dangerouslySetInnerHTML={{ __html: t("workflow_node.deploy.form.jdcloud_alb_loadbalancer_id.tooltip") }}></span>}
|
|
||||||
>
|
|
||||||
<Input placeholder={t("workflow_node.deploy.form.jdcloud_alb_loadbalancer_id.placeholder")} />
|
|
||||||
</Form.Item>
|
|
||||||
</Show>
|
|
||||||
|
|
||||||
<Show when={fieldResourceType === RESOURCE_TYPE_LISTENER}>
|
|
||||||
<Form.Item
|
|
||||||
name="listenerId"
|
|
||||||
label={t("workflow_node.deploy.form.jdcloud_alb_listener_id.label")}
|
|
||||||
rules={[formRule]}
|
|
||||||
tooltip={<span dangerouslySetInnerHTML={{ __html: t("workflow_node.deploy.form.jdcloud_alb_listener_id.tooltip") }}></span>}
|
|
||||||
>
|
|
||||||
<Input placeholder={t("workflow_node.deploy.form.jdcloud_alb_listener_id.placeholder")} />
|
|
||||||
</Form.Item>
|
|
||||||
</Show>
|
|
||||||
|
|
||||||
<Show when={fieldResourceType === RESOURCE_TYPE_LOADBALANCER || fieldResourceType === RESOURCE_TYPE_LISTENER}>
|
|
||||||
<Form.Item
|
|
||||||
name="domain"
|
|
||||||
label={t("workflow_node.deploy.form.jdcloud_alb_snidomain.label")}
|
|
||||||
rules={[formRule]}
|
|
||||||
tooltip={<span dangerouslySetInnerHTML={{ __html: t("workflow_node.deploy.form.jdcloud_alb_snidomain.tooltip") }}></span>}
|
|
||||||
>
|
|
||||||
<Input placeholder={t("workflow_node.deploy.form.jdcloud_alb_snidomain.placeholder")} />
|
|
||||||
</Form.Item>
|
|
||||||
</Show>
|
|
||||||
</Form>
|
|
||||||
);
|
|
||||||
};
|
|
||||||
|
|
||||||
export default DeployNodeConfigFormJDCloudALBConfig;
|
|
@ -221,7 +221,6 @@ export const DEPLOY_PROVIDERS = Object.freeze({
|
|||||||
HUAWEICLOUD_CDN: `${ACCESS_PROVIDERS.HUAWEICLOUD}-cdn`,
|
HUAWEICLOUD_CDN: `${ACCESS_PROVIDERS.HUAWEICLOUD}-cdn`,
|
||||||
HUAWEICLOUD_ELB: `${ACCESS_PROVIDERS.HUAWEICLOUD}-elb`,
|
HUAWEICLOUD_ELB: `${ACCESS_PROVIDERS.HUAWEICLOUD}-elb`,
|
||||||
HUAWEICLOUD_WAF: `${ACCESS_PROVIDERS.HUAWEICLOUD}-waf`,
|
HUAWEICLOUD_WAF: `${ACCESS_PROVIDERS.HUAWEICLOUD}-waf`,
|
||||||
JDCLOUD_ALB: `${ACCESS_PROVIDERS.JDCLOUD}-alb`,
|
|
||||||
JDCLOUD_CDN: `${ACCESS_PROVIDERS.JDCLOUD}-cdn`,
|
JDCLOUD_CDN: `${ACCESS_PROVIDERS.JDCLOUD}-cdn`,
|
||||||
JDCLOUD_LIVE: `${ACCESS_PROVIDERS.JDCLOUD}-live`,
|
JDCLOUD_LIVE: `${ACCESS_PROVIDERS.JDCLOUD}-live`,
|
||||||
KUBERNETES_SECRET: `${ACCESS_PROVIDERS.KUBERNETES}-secret`,
|
KUBERNETES_SECRET: `${ACCESS_PROVIDERS.KUBERNETES}-secret`,
|
||||||
@ -310,7 +309,6 @@ export const deployProvidersMap: Map<DeployProvider["type"] | string, DeployProv
|
|||||||
[DEPLOY_PROVIDERS.VOLCENGINE_CLB, "provider.volcengine.clb", DEPLOY_CATEGORIES.LOADBALANCE],
|
[DEPLOY_PROVIDERS.VOLCENGINE_CLB, "provider.volcengine.clb", DEPLOY_CATEGORIES.LOADBALANCE],
|
||||||
[DEPLOY_PROVIDERS.VOLCENGINE_IMAGEX, "provider.volcengine.imagex", DEPLOY_CATEGORIES.STORAGE],
|
[DEPLOY_PROVIDERS.VOLCENGINE_IMAGEX, "provider.volcengine.imagex", DEPLOY_CATEGORIES.STORAGE],
|
||||||
[DEPLOY_PROVIDERS.VOLCENGINE_LIVE, "provider.volcengine.live", DEPLOY_CATEGORIES.LIVE],
|
[DEPLOY_PROVIDERS.VOLCENGINE_LIVE, "provider.volcengine.live", DEPLOY_CATEGORIES.LIVE],
|
||||||
[DEPLOY_PROVIDERS.JDCLOUD_ALB, "provider.jdcloud.alb", DEPLOY_CATEGORIES.LOADBALANCE],
|
|
||||||
[DEPLOY_PROVIDERS.JDCLOUD_CDN, "provider.jdcloud.cdn", DEPLOY_CATEGORIES.CDN],
|
[DEPLOY_PROVIDERS.JDCLOUD_CDN, "provider.jdcloud.cdn", DEPLOY_CATEGORIES.CDN],
|
||||||
[DEPLOY_PROVIDERS.JDCLOUD_LIVE, "provider.jdcloud.live", DEPLOY_CATEGORIES.LIVE],
|
[DEPLOY_PROVIDERS.JDCLOUD_LIVE, "provider.jdcloud.live", DEPLOY_CATEGORIES.LIVE],
|
||||||
[DEPLOY_PROVIDERS.QINIU_CDN, "provider.qiniu.cdn", DEPLOY_CATEGORIES.CDN],
|
[DEPLOY_PROVIDERS.QINIU_CDN, "provider.qiniu.cdn", DEPLOY_CATEGORIES.CDN],
|
||||||
|
@ -54,7 +54,6 @@
|
|||||||
"provider.huaweicloud.elb": "Huawei Cloud - ELB (Elastic Load Balance)",
|
"provider.huaweicloud.elb": "Huawei Cloud - ELB (Elastic Load Balance)",
|
||||||
"provider.huaweicloud.waf": "Huawei Cloud - WAF (Web Application Firewall)",
|
"provider.huaweicloud.waf": "Huawei Cloud - WAF (Web Application Firewall)",
|
||||||
"provider.jdcloud": "JD Cloud",
|
"provider.jdcloud": "JD Cloud",
|
||||||
"provider.jdcloud.alb": "JD Cloud - ALB (Application Load Balancer)",
|
|
||||||
"provider.jdcloud.cdn": "JD Cloud - CDN (Content Delivery Network)",
|
"provider.jdcloud.cdn": "JD Cloud - CDN (Content Delivery Network)",
|
||||||
"provider.jdcloud.dns": "JD Cloud - DNS",
|
"provider.jdcloud.dns": "JD Cloud - DNS",
|
||||||
"provider.jdcloud.live": "JD Cloud - Live Video",
|
"provider.jdcloud.live": "JD Cloud - Live Video",
|
||||||
|
@ -267,22 +267,6 @@
|
|||||||
"workflow_node.deploy.form.huaweicloud_waf_domain.label": "Huawei Cloud WAF domain",
|
"workflow_node.deploy.form.huaweicloud_waf_domain.label": "Huawei Cloud WAF domain",
|
||||||
"workflow_node.deploy.form.huaweicloud_waf_domain.placeholder": "Please enter Huawei Cloud WAF domain name",
|
"workflow_node.deploy.form.huaweicloud_waf_domain.placeholder": "Please enter Huawei Cloud WAF domain name",
|
||||||
"workflow_node.deploy.form.huaweicloud_waf_domain.tooltip": "For more information, see <a href=\"https://console-intl.huaweicloud.com/console/#/waf/domain/list\" target=\"_blank\">https://console-intl.huaweicloud.com/console/#/waf/domain/list</a>",
|
"workflow_node.deploy.form.huaweicloud_waf_domain.tooltip": "For more information, see <a href=\"https://console-intl.huaweicloud.com/console/#/waf/domain/list\" target=\"_blank\">https://console-intl.huaweicloud.com/console/#/waf/domain/list</a>",
|
||||||
"workflow_node.deploy.form.jdcloud_alb_resource_type.label": "Resource type",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_resource_type.placeholder": "Please select resource type",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_resource_type.option.loadbalancer.label": "ALB load balancer",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_resource_type.option.listener.label": "ALB listener",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_region_id.label": "JD Cloud ALB region ID",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_region_id.placeholder": "Please enter JD Cloud ALB region ID (e.g. cn-north-1)",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_region_id.tooltip": "For more information, see <a href=\"https://docs.jdcloud.com/en/common-declaration/api/introduction\" target=\"_blank\">https://docs.jdcloud.com/en/common-declaration/api/introduction</a>",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_loadbalancer_id.label": "JD Cloud ALB load balancer ID",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_loadbalancer_id.placeholder": "Please enter JD Cloud ALB load balancer ID",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_loadbalancer_id.tooltip": "For more information, see <a href=\"https://cns-console.jdcloud.com/host/loadBalance/list\" target=\"_blank\">https://cns-console.jdcloud.com/host/loadBalance/list</a>",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_listener_id.label": "JD Cloud ALB listener ID",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_listener_id.placeholder": "Please enter JD Cloud ALB listener ID",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_listener_id.tooltip": "For more information, see <a href=\"https://cns-console.jdcloud.com/host/loadBalance/list\" target=\"_blank\">https://cns-console.jdcloud.com/host/loadBalance/list</a>",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_snidomain.label": "JD Cloud ALB SNI domain (Optional)",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_snidomain.placeholder": "Please enter JD Cloud ALB SNI domain name",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_snidomain.tooltip": "For more information, see <a href=\"https://cns-console.jdcloud.com/host/loadBalance/list\" target=\"_blank\">https://cns-console.jdcloud.com/host/loadBalance/list</a>",
|
|
||||||
"workflow_node.deploy.form.jdcloud_cdn_domain.label": "JD Cloud CDN domain",
|
"workflow_node.deploy.form.jdcloud_cdn_domain.label": "JD Cloud CDN domain",
|
||||||
"workflow_node.deploy.form.jdcloud_cdn_domain.placeholder": "Please enter JD Cloud CDN domain name",
|
"workflow_node.deploy.form.jdcloud_cdn_domain.placeholder": "Please enter JD Cloud CDN domain name",
|
||||||
"workflow_node.deploy.form.jdcloud_cdn_domain.tooltip": "For more information, see <a href=\"https://cdn-console.jdcloud.com/\" target=\"_blank\">https://cdn-console.jdcloud.com/</a>",
|
"workflow_node.deploy.form.jdcloud_cdn_domain.tooltip": "For more information, see <a href=\"https://cdn-console.jdcloud.com/\" target=\"_blank\">https://cdn-console.jdcloud.com/</a>",
|
||||||
|
@ -54,7 +54,6 @@
|
|||||||
"provider.huaweicloud.elb": "华为云 - 弹性负载均衡 ELB",
|
"provider.huaweicloud.elb": "华为云 - 弹性负载均衡 ELB",
|
||||||
"provider.huaweicloud.waf": "华为云 - Web 应用防火墙 WAF",
|
"provider.huaweicloud.waf": "华为云 - Web 应用防火墙 WAF",
|
||||||
"provider.jdcloud": "京东云",
|
"provider.jdcloud": "京东云",
|
||||||
"provider.jdcloud.alb": "京东云 - 应用负载均衡 ALB",
|
|
||||||
"provider.jdcloud.cdn": "京东云 - 内容分发网络 CDN",
|
"provider.jdcloud.cdn": "京东云 - 内容分发网络 CDN",
|
||||||
"provider.jdcloud.dns": "京东云 - 云解析 DNS",
|
"provider.jdcloud.dns": "京东云 - 云解析 DNS",
|
||||||
"provider.jdcloud.live": "京东云 - 视频直播",
|
"provider.jdcloud.live": "京东云 - 视频直播",
|
||||||
|
@ -104,7 +104,7 @@
|
|||||||
"workflow_node.deploy.form.aliyun_alb_listener_id.placeholder": "请输入阿里云 ALB 监听器 ID",
|
"workflow_node.deploy.form.aliyun_alb_listener_id.placeholder": "请输入阿里云 ALB 监听器 ID",
|
||||||
"workflow_node.deploy.form.aliyun_alb_listener_id.tooltip": "这是什么?请参阅 <a href=\"https://slb.console.aliyun.com/alb\" target=\"_blank\">https://slb.console.aliyun.com/alb</a>",
|
"workflow_node.deploy.form.aliyun_alb_listener_id.tooltip": "这是什么?请参阅 <a href=\"https://slb.console.aliyun.com/alb\" target=\"_blank\">https://slb.console.aliyun.com/alb</a>",
|
||||||
"workflow_node.deploy.form.aliyun_alb_snidomain.label": "阿里云 ALB 扩展域名(可选)",
|
"workflow_node.deploy.form.aliyun_alb_snidomain.label": "阿里云 ALB 扩展域名(可选)",
|
||||||
"workflow_node.deploy.form.aliyun_alb_snidomain.placeholder": "请输入阿里云 ALB 扩展域名(支持泛域名)",
|
"workflow_node.deploy.form.aliyun_alb_snidomain.placeholder": "请输入阿里云 ALB 扩展域名",
|
||||||
"workflow_node.deploy.form.aliyun_alb_snidomain.tooltip": "这是什么?请参阅 <a href=\"https://slb.console.aliyun.com/alb\" target=\"_blank\">https://slb.console.aliyun.com/alb</a><br><br>不填写时,将替换监听器的默认证书。",
|
"workflow_node.deploy.form.aliyun_alb_snidomain.tooltip": "这是什么?请参阅 <a href=\"https://slb.console.aliyun.com/alb\" target=\"_blank\">https://slb.console.aliyun.com/alb</a><br><br>不填写时,将替换监听器的默认证书。",
|
||||||
"workflow_node.deploy.form.aliyun_cas_deploy.guide": "小贴士:由于阿里云证书部署任务是异步的,此节点若执行成功仅代表已创建部署任务,实际部署结果需要你自行前往阿里云控制台查询。",
|
"workflow_node.deploy.form.aliyun_cas_deploy.guide": "小贴士:由于阿里云证书部署任务是异步的,此节点若执行成功仅代表已创建部署任务,实际部署结果需要你自行前往阿里云控制台查询。",
|
||||||
"workflow_node.deploy.form.aliyun_cas_deploy_region.label": "阿里云 CAS 服务地域",
|
"workflow_node.deploy.form.aliyun_cas_deploy_region.label": "阿里云 CAS 服务地域",
|
||||||
@ -136,7 +136,7 @@
|
|||||||
"workflow_node.deploy.form.aliyun_clb_listener_port.placeholder": "请输入阿里云 CLB 监听端口",
|
"workflow_node.deploy.form.aliyun_clb_listener_port.placeholder": "请输入阿里云 CLB 监听端口",
|
||||||
"workflow_node.deploy.form.aliyun_clb_listener_port.tooltip": "这是什么?请参阅 <a href=\"https://slb.console.aliyun.com/clb\" target=\"_blank\">https://slb.console.aliyun.com/clb</a>",
|
"workflow_node.deploy.form.aliyun_clb_listener_port.tooltip": "这是什么?请参阅 <a href=\"https://slb.console.aliyun.com/clb\" target=\"_blank\">https://slb.console.aliyun.com/clb</a>",
|
||||||
"workflow_node.deploy.form.aliyun_clb_snidomain.label": "阿里云 CLB 扩展域名(可选)",
|
"workflow_node.deploy.form.aliyun_clb_snidomain.label": "阿里云 CLB 扩展域名(可选)",
|
||||||
"workflow_node.deploy.form.aliyun_clb_snidomain.placeholder": "请输入阿里云 CLB 扩展域名(支持泛域名)",
|
"workflow_node.deploy.form.aliyun_clb_snidomain.placeholder": "请输入阿里云 CLB 扩展域名",
|
||||||
"workflow_node.deploy.form.aliyun_clb_snidomain.tooltip": "这是什么?请参阅 <a href=\"https://slb.console.aliyun.com/clb\" target=\"_blank\">https://slb.console.aliyun.com/clb</a><br><br>不填写时,将替换监听器的默认证书。",
|
"workflow_node.deploy.form.aliyun_clb_snidomain.tooltip": "这是什么?请参阅 <a href=\"https://slb.console.aliyun.com/clb\" target=\"_blank\">https://slb.console.aliyun.com/clb</a><br><br>不填写时,将替换监听器的默认证书。",
|
||||||
"workflow_node.deploy.form.aliyun_cdn_domain.label": "阿里云 CDN 加速域名",
|
"workflow_node.deploy.form.aliyun_cdn_domain.label": "阿里云 CDN 加速域名",
|
||||||
"workflow_node.deploy.form.aliyun_cdn_domain.placeholder": "请输入阿里云 CDN 加速域名(支持泛域名)",
|
"workflow_node.deploy.form.aliyun_cdn_domain.placeholder": "请输入阿里云 CDN 加速域名(支持泛域名)",
|
||||||
@ -267,22 +267,6 @@
|
|||||||
"workflow_node.deploy.form.huaweicloud_waf_domain.label": "华为云 WAF 防护域名",
|
"workflow_node.deploy.form.huaweicloud_waf_domain.label": "华为云 WAF 防护域名",
|
||||||
"workflow_node.deploy.form.huaweicloud_waf_domain.placeholder": "请输入华为云 WAF 防护域名(支持泛域名)",
|
"workflow_node.deploy.form.huaweicloud_waf_domain.placeholder": "请输入华为云 WAF 防护域名(支持泛域名)",
|
||||||
"workflow_node.deploy.form.huaweicloud_waf_domain.tooltip": "这是什么?请参阅 <a href=\"https://console.huaweicloud.com/console/#/waf/domain/list\" target=\"_blank\">https://console.huaweicloud.com/console/#/waf/domain/list</a>",
|
"workflow_node.deploy.form.huaweicloud_waf_domain.tooltip": "这是什么?请参阅 <a href=\"https://console.huaweicloud.com/console/#/waf/domain/list\" target=\"_blank\">https://console.huaweicloud.com/console/#/waf/domain/list</a>",
|
||||||
"workflow_node.deploy.form.jdcloud_alb_resource_type.label": "证书替换方式",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_resource_type.placeholder": "请选择证书替换方式",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_resource_type.option.loadbalancer.label": "替换指定负载均衡器下的全部 HTTPS/TLS 监听的证书",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_resource_type.option.listener.label": "替换指定负载均衡监听器的证书",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_region_id.label": "京东云 ALB 服务地域 ID",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_region_id.placeholder": "请输入京东云 ALB 服务地域 ID(例如:cn-north-1",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_region_id.tooltip": "这是什么?请参阅 <a href=\"https://docs.jdcloud.com/cn/common-declaration/api/introduction\" target=\"_blank\">https://docs.jdcloud.com/cn/common-declaration/api/introduction</a>",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_loadbalancer_id.label": "京东云 ALB 负载均衡器 ID",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_loadbalancer_id.placeholder": "请输入京东云 ALB 负载均衡器 ID",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_loadbalancer_id.tooltip": "这是什么?请参阅 <a href=\"https://cns-console.jdcloud.com/host/loadBalance/list\" target=\"_blank\">https://cns-console.jdcloud.com/host/loadBalance/list</a>",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_listener_id.label": "京东云 ALB 监听器 ID",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_listener_id.placeholder": "请输入京东云 ALB 监听器 ID",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_listener_id.tooltip": "这是什么?请参阅 <a href=\"https://cns-console.jdcloud.com/host/loadBalance/list\" target=\"_blank\">https://cns-console.jdcloud.com/host/loadBalance/list</a>",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_snidomain.label": "京东云 ALB 扩展域名(可选)",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_snidomain.placeholder": "请输入京东云 ALB 扩展域名(支持泛域名)",
|
|
||||||
"workflow_node.deploy.form.jdcloud_alb_snidomain.tooltip": "这是什么?请参阅 <a href=\"https://cns-console.jdcloud.com/host/loadBalance/list\" target=\"_blank\">https://cns-console.jdcloud.com/host/loadBalance/list</a><br><br>不填写时,将替换监听器的默认证书。",
|
|
||||||
"workflow_node.deploy.form.jdcloud_cdn_domain.label": "京东云 CDN 加速域名",
|
"workflow_node.deploy.form.jdcloud_cdn_domain.label": "京东云 CDN 加速域名",
|
||||||
"workflow_node.deploy.form.jdcloud_cdn_domain.placeholder": "请输入京东云 CDN 加速域名(支持泛域名)",
|
"workflow_node.deploy.form.jdcloud_cdn_domain.placeholder": "请输入京东云 CDN 加速域名(支持泛域名)",
|
||||||
"workflow_node.deploy.form.jdcloud_cdn_domain.tooltip": "这是什么?请参阅 <a href=\"https://cdn-console.jdcloud.com/\" target=\"_blank\">https://cdn-console.jdcloud.com/</a>",
|
"workflow_node.deploy.form.jdcloud_cdn_domain.tooltip": "这是什么?请参阅 <a href=\"https://cdn-console.jdcloud.com/\" target=\"_blank\">https://cdn-console.jdcloud.com/</a>",
|
||||||
|
Loading…
x
Reference in New Issue
Block a user