mirror of
https://github.com/certimate-go/certimate.git
synced 2026-09-24 23:10:13 +08:00
Merge pull request #955 from fudiwei/dev
This commit is contained in:
@@ -0,0 +1,30 @@
|
||||
package deployers
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
|
||||
"github.com/certimate-go/certimate/internal/domain"
|
||||
"github.com/certimate-go/certimate/pkg/core"
|
||||
huaweicloudobs "github.com/certimate-go/certimate/pkg/core/ssl-deployer/providers/huaweicloud-obs"
|
||||
xmaps "github.com/certimate-go/certimate/pkg/utils/maps"
|
||||
)
|
||||
|
||||
func init() {
|
||||
if err := Registries.Register(domain.DeploymentProviderTypeHuaweiCloudOBS, func(options *ProviderFactoryOptions) (core.SSLDeployer, error) {
|
||||
credentials := domain.AccessConfigForHuaweiCloud{}
|
||||
if err := xmaps.Populate(options.ProviderAccessConfig, &credentials); err != nil {
|
||||
return nil, fmt.Errorf("failed to populate provider access config: %w", err)
|
||||
}
|
||||
|
||||
provider, err := huaweicloudobs.NewSSLDeployerProvider(&huaweicloudobs.SSLDeployerProviderConfig{
|
||||
AccessKeyId: credentials.AccessKeyId,
|
||||
SecretAccessKey: credentials.SecretAccessKey,
|
||||
Region: xmaps.GetString(options.ProviderExtendedConfig, "region"),
|
||||
Bucket: xmaps.GetString(options.ProviderExtendedConfig, "bucket"),
|
||||
Domain: xmaps.GetString(options.ProviderExtendedConfig, "domain"),
|
||||
})
|
||||
return provider, err
|
||||
}); err != nil {
|
||||
panic(err)
|
||||
}
|
||||
}
|
||||
@@ -11,7 +11,6 @@ import (
|
||||
"fmt"
|
||||
"log/slog"
|
||||
"net/http"
|
||||
"strings"
|
||||
"time"
|
||||
|
||||
"github.com/certimate-go/certimate/pkg/core"
|
||||
@@ -22,11 +21,11 @@ type SSLDeployerProviderConfig struct {
|
||||
AccessKeyId string `json:"accessKeyId"`
|
||||
// 华为云 SecretAccessKey。
|
||||
SecretAccessKey string `json:"secretAccessKey"`
|
||||
// 华为云 Bucket 对应的 Endpoint。
|
||||
Endpoint string `json:"endpoint"`
|
||||
// 华为云 OBS 桶名。
|
||||
// 华为云区域。
|
||||
Region string `json:"region"`
|
||||
// 存储桶名。
|
||||
Bucket string `json:"bucket"`
|
||||
// 自定义域名。
|
||||
// 自定义域名(不支持泛域名)。
|
||||
Domain string `json:"domain"`
|
||||
}
|
||||
|
||||
@@ -42,8 +41,6 @@ func NewSSLDeployerProvider(config *SSLDeployerProviderConfig) (*SSLDeployerProv
|
||||
return nil, errors.New("the configuration of the ssl deployer provider is nil")
|
||||
}
|
||||
|
||||
config.Endpoint = strings.TrimPrefix(strings.TrimPrefix(config.Endpoint, "http://"), "https://")
|
||||
|
||||
return &SSLDeployerProvider{
|
||||
config: config,
|
||||
logger: slog.Default(),
|
||||
@@ -58,14 +55,20 @@ func (d *SSLDeployerProvider) SetLogger(logger *slog.Logger) {
|
||||
}
|
||||
}
|
||||
|
||||
// REF: https://support.huaweicloud.com/usermanual-obs/obs_06_3200.html
|
||||
// REF: https://support.huaweicloud.com/api-obs/obs_04_0059.html
|
||||
func (d *SSLDeployerProvider) Deploy(ctx context.Context, certPEM string, privkeyPEM string) (*core.SSLDeployResult, error) {
|
||||
if d.config.Region == "" {
|
||||
return nil, fmt.Errorf("config `region` is required")
|
||||
}
|
||||
if d.config.Bucket == "" {
|
||||
return nil, fmt.Errorf("config `bucket` is required")
|
||||
}
|
||||
if d.config.Domain == "" {
|
||||
return nil, fmt.Errorf("config `domain` is required")
|
||||
}
|
||||
|
||||
url := fmt.Sprintf("https://%s.%s/?customdomain=%s", d.config.Bucket, d.config.Endpoint, d.config.Domain)
|
||||
// REF: https://support.huaweicloud.com/usermanual-obs/obs_06_3200.html
|
||||
// REF: https://support.huaweicloud.com/api-obs/obs_04_0059.html
|
||||
url := fmt.Sprintf("https://%s.obs.%s.myhuaweicloud.com/?customdomain=%s", d.config.Bucket, d.config.Region, d.config.Domain)
|
||||
bodyXML := fmt.Sprintf(`
|
||||
<CustomDomainConfiguration>
|
||||
<Name>%s</Name>
|
||||
@@ -78,16 +81,14 @@ func (d *SSLDeployerProvider) Deploy(ctx context.Context, certPEM string, privke
|
||||
|
||||
// 计算 Content-MD5(Base64 编码)
|
||||
md5sum := md5.Sum([]byte(bodyXML))
|
||||
contentMD5 := base64.StdEncoding.EncodeToString(md5sum[:])
|
||||
|
||||
// 日期
|
||||
date := time.Now().UTC().Format(http.TimeFormat)
|
||||
md5sumEncoded := base64.StdEncoding.EncodeToString(md5sum[:])
|
||||
|
||||
// 构造签名字符串
|
||||
date := time.Now().UTC().Format(http.TimeFormat)
|
||||
method := "PUT"
|
||||
contentType := "application/xml"
|
||||
canonicalizedResource := fmt.Sprintf("/%s/?customdomain=%s", d.config.Bucket, d.config.Domain)
|
||||
stringToSign := fmt.Sprintf("%s\n%s\n%s\n%s\n%s", method, contentMD5, contentType, date, canonicalizedResource)
|
||||
stringToSign := fmt.Sprintf("%s\n%s\n%s\n%s\n%s", method, md5sumEncoded, contentType, date, canonicalizedResource)
|
||||
|
||||
// HMAC-SHA1 签名
|
||||
h := hmac.New(sha1.New, []byte(d.config.SecretAccessKey))
|
||||
@@ -100,25 +101,26 @@ func (d *SSLDeployerProvider) Deploy(ctx context.Context, certPEM string, privke
|
||||
// 创建请求
|
||||
req, err := http.NewRequest(method, url, bytes.NewBuffer([]byte(bodyXML)))
|
||||
if err != nil {
|
||||
return nil, err
|
||||
return nil, fmt.Errorf("huaweicloud obs api error: %w", err)
|
||||
}
|
||||
|
||||
req.Header.Set("Date", date)
|
||||
req.Header.Set("Authorization", authHeader)
|
||||
req.Header.Set("Content-MD5", contentMD5)
|
||||
req.Header.Set("Content-MD5", md5sumEncoded)
|
||||
req.Header.Set("Content-Type", contentType)
|
||||
|
||||
// 请求
|
||||
resp, err := http.DefaultClient.Do(req)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
return nil, fmt.Errorf("huaweicloud obs api error: %w", err)
|
||||
}
|
||||
defer resp.Body.Close()
|
||||
|
||||
// 响应
|
||||
if resp.StatusCode != http.StatusOK {
|
||||
body := new(bytes.Buffer)
|
||||
body := &bytes.Buffer{}
|
||||
body.ReadFrom(resp.Body)
|
||||
return nil, fmt.Errorf("HTTP request failed with status %d: %s", resp.StatusCode, body.String())
|
||||
return nil, fmt.Errorf("huaweicloud obs api error: unexpected status code: %d, resp: %s", resp.StatusCode, body.String())
|
||||
}
|
||||
|
||||
return &core.SSLDeployResult{}, nil
|
||||
}
|
||||
|
||||
@@ -16,19 +16,19 @@ var (
|
||||
fInputKeyPath string
|
||||
fAccessKeyId string
|
||||
fSecretAccessKey string
|
||||
fEndpoint string
|
||||
fRegion string
|
||||
fBucket string
|
||||
fDomain string
|
||||
)
|
||||
|
||||
func init() {
|
||||
argsPrefix := "CERTIMATE_SSLDEPLOYER_HUAWEICLOUDCDN_"
|
||||
argsPrefix := "CERTIMATE_SSLDEPLOYER_HUAWEICLOUDOBS_"
|
||||
|
||||
flag.StringVar(&fInputCertPath, argsPrefix+"INPUTCERTPATH", "", "")
|
||||
flag.StringVar(&fInputKeyPath, argsPrefix+"INPUTKEYPATH", "", "")
|
||||
flag.StringVar(&fAccessKeyId, argsPrefix+"ACCESSKEYID", "", "")
|
||||
flag.StringVar(&fSecretAccessKey, argsPrefix+"SECRETACCESSKEY", "", "")
|
||||
flag.StringVar(&fEndpoint, argsPrefix+"ENDPOINT", "", "")
|
||||
flag.StringVar(&fRegion, argsPrefix+"REGION", "", "")
|
||||
flag.StringVar(&fBucket, argsPrefix+"BUCKET", "", "")
|
||||
flag.StringVar(&fDomain, argsPrefix+"DOMAIN", "", "")
|
||||
}
|
||||
@@ -37,13 +37,13 @@ func init() {
|
||||
Shell command to run this test:
|
||||
|
||||
go test -v ./huaweicloud_obs_test.go -args \
|
||||
--CERTIMATE_SSLDEPLOYER_HUAWEICLOUDCDN_INPUTCERTPATH="/path/to/your-input-cert.pem" \
|
||||
--CERTIMATE_SSLDEPLOYER_HUAWEICLOUDCDN_INPUTKEYPATH="/path/to/your-input-key.pem" \
|
||||
--CERTIMATE_SSLDEPLOYER_HUAWEICLOUDCDN_ACCESSKEYID="your-access-key-id" \
|
||||
--CERTIMATE_SSLDEPLOYER_HUAWEICLOUDCDN_SECRETACCESSKEY="your-secret-access-key" \
|
||||
--CERTIMATE_SSLDEPLOYER_HUAWEICLOUDCDN_ENDPOINT="https://your-endpoint" \
|
||||
--CERTIMATE_SSLDEPLOYER_HUAWEICLOUDCDN_BUCKET="your-bucket" \
|
||||
--CERTIMATE_SSLDEPLOYER_HUAWEICLOUDCDN_DOMAIN="example.com"
|
||||
--CERTIMATE_SSLDEPLOYER_HUAWEICLOUDOBS_INPUTCERTPATH="/path/to/your-input-cert.pem" \
|
||||
--CERTIMATE_SSLDEPLOYER_HUAWEICLOUDOBS_INPUTKEYPATH="/path/to/your-input-key.pem" \
|
||||
--CERTIMATE_SSLDEPLOYER_HUAWEICLOUDOBS_ACCESSKEYID="your-access-key-id" \
|
||||
--CERTIMATE_SSLDEPLOYER_HUAWEICLOUDOBS_SECRETACCESSKEY="your-secret-access-key" \
|
||||
--CERTIMATE_SSLDEPLOYER_HUAWEICLOUDOBS_REGION="cn-north-4" \
|
||||
--CERTIMATE_SSLDEPLOYER_HUAWEICLOUDOBS_BUCKET="your-bucket" \
|
||||
--CERTIMATE_SSLDEPLOYER_HUAWEICLOUDOBS_DOMAIN="example.com"
|
||||
*/
|
||||
func TestDeploy(t *testing.T) {
|
||||
flag.Parse()
|
||||
@@ -55,7 +55,7 @@ func TestDeploy(t *testing.T) {
|
||||
fmt.Sprintf("INPUTKEYPATH: %v", fInputKeyPath),
|
||||
fmt.Sprintf("ACCESSKEYID: %v", fAccessKeyId),
|
||||
fmt.Sprintf("SECRETACCESSKEY: %v", fSecretAccessKey),
|
||||
fmt.Sprintf("ENDPOINT: %v", fEndpoint),
|
||||
fmt.Sprintf("REGION: %v", fRegion),
|
||||
fmt.Sprintf("BUCKET: %v", fBucket),
|
||||
fmt.Sprintf("DOMAIN: %v", fDomain),
|
||||
}, "\n"))
|
||||
@@ -63,7 +63,7 @@ func TestDeploy(t *testing.T) {
|
||||
deployer, err := provider.NewSSLDeployerProvider(&provider.SSLDeployerProviderConfig{
|
||||
AccessKeyId: fAccessKeyId,
|
||||
SecretAccessKey: fSecretAccessKey,
|
||||
Endpoint: fEndpoint,
|
||||
Region: fRegion,
|
||||
Bucket: fBucket,
|
||||
Domain: fDomain,
|
||||
})
|
||||
|
||||
+9
-9
@@ -20,13 +20,13 @@ const BizDeployNodeConfigFieldsProviderHuaweiCloudOBS = () => {
|
||||
return (
|
||||
<>
|
||||
<Form.Item
|
||||
name={[parentNamePath, "endpoint"]}
|
||||
initialValue={initialValues.endpoint}
|
||||
label={t("workflow_node.deploy.form.huaweicloud_obs_endpoint.label")}
|
||||
name={[parentNamePath, "region"]}
|
||||
initialValue={initialValues.region}
|
||||
label={t("workflow_node.deploy.form.huaweicloud_obs_region.label")}
|
||||
rules={[formRule]}
|
||||
tooltip={<span dangerouslySetInnerHTML={{ __html: t("workflow_node.deploy.form.huaweicloud_obs_endpoint.tooltip") }}></span>}
|
||||
tooltip={<span dangerouslySetInnerHTML={{ __html: t("workflow_node.deploy.form.huaweicloud_obs_region.tooltip") }}></span>}
|
||||
>
|
||||
<Input placeholder={t("workflow_node.deploy.form.huaweicloud_obs_endpoint.placeholder")} />
|
||||
<Input placeholder={t("workflow_node.deploy.form.huaweicloud_obs_region.placeholder")} />
|
||||
</Form.Item>
|
||||
|
||||
<Form.Item
|
||||
@@ -54,7 +54,7 @@ const BizDeployNodeConfigFieldsProviderHuaweiCloudOBS = () => {
|
||||
|
||||
const getInitialValues = (): Nullish<z.infer<ReturnType<typeof getSchema>>> => {
|
||||
return {
|
||||
endpoint: "",
|
||||
region: "",
|
||||
bucket: "",
|
||||
domain: "",
|
||||
};
|
||||
@@ -64,9 +64,9 @@ const getSchema = ({ i18n = getI18n() }: { i18n?: ReturnType<typeof getI18n> })
|
||||
const { t } = i18n;
|
||||
|
||||
return z.object({
|
||||
endpoint: z
|
||||
.string(t("workflow_node.deploy.form.huaweicloud_obs_endpoint.placeholder"))
|
||||
.nonempty(t("workflow_node.deploy.form.huaweicloud_obs_endpoint.placeholder")),
|
||||
region: z
|
||||
.string(t("workflow_node.deploy.form.huaweicloud_obs_region.placeholder"))
|
||||
.nonempty(t("workflow_node.deploy.form.huaweicloud_obs_region.placeholder")),
|
||||
bucket: z
|
||||
.string(t("workflow_node.deploy.form.huaweicloud_obs_bucket.placeholder"))
|
||||
.nonempty(t("workflow_node.deploy.form.huaweicloud_obs_bucket.placeholder")),
|
||||
|
||||
@@ -95,8 +95,8 @@
|
||||
"provider.huaweicloud.cdn": "Huawei Cloud - CDN (Content Delivery Network)",
|
||||
"provider.huaweicloud.dns": "Huawei Cloud - DNS",
|
||||
"provider.huaweicloud.elb": "Huawei Cloud - ELB (Elastic Load Balance)",
|
||||
"provider.huaweicloud.scm_upload": "Huawei Cloud - Upload to SCM (SSL Certificate Manager)",
|
||||
"provider.huaweicloud.obs": "Huawei Cloud - OBS (Object Storage Service)",
|
||||
"provider.huaweicloud.scm_upload": "Huawei Cloud - Upload to SCM (SSL Certificate Manager)",
|
||||
"provider.huaweicloud.waf": "Huawei Cloud - WAF (Web Application Firewall)",
|
||||
"provider.jdcloud": "JD Cloud",
|
||||
"provider.jdcloud.alb": "JD Cloud - ALB (Application Load Balancer)",
|
||||
|
||||
@@ -518,15 +518,15 @@
|
||||
"workflow_node.deploy.form.huaweicloud_cdn_domain.label": "Huawei Cloud CDN domain",
|
||||
"workflow_node.deploy.form.huaweicloud_cdn_domain.placeholder": "Please enter Huawei Cloud CDN domain name",
|
||||
"workflow_node.deploy.form.huaweicloud_cdn_domain.tooltip": "For more information, see <a href=\"https://console-intl.huaweicloud.com/cdn\" target=\"_blank\">https://console-intl.huaweicloud.com/cdn</a>",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_endpoint.label": "Huawei Cloud OBS Endpoint",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_endpoint.placeholder": "Please enter the Huawei Cloud OBS endpoint (e.g., obs.cn-north-4.myhuaweicloud.com)",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_endpoint.tooltip": "What is this? Please refer to <a href=\"https://support.huaweicloud.com/productdesc-obs/obs_03_0152.html\" target=\"_blank\">https://support.huaweicloud.com/productdesc-obs/obs_03_0152.html</a>",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_bucket.label": "Huawei Cloud COS Bucket Name",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_bucket.placeholder": "Please enter the Huawei Cloud COS bucket name",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_bucket.tooltip": "What is this? Please refer to <a href=\"https://support.huaweicloud.com/productdesc-obs/obs_03_0207.html\" target=\"_blank\">https://support.huaweicloud.com/productdesc-obs/obs_03_0207.html</a>",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_domain.label": "Huawei Cloud COS Custom Domain",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_domain.placeholder": "Please enter the Huawei Cloud COS custom domain",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_domain.tooltip": "What is this? Please refer to <a href=\"https://support.huaweicloud.com/productdesc-obs/obs_03_0207.html\" target=\"_blank\">https://support.huaweicloud.com/productdesc-obs/obs_03_0207.html</a>",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_region.label": "Huawei Cloud OBS region",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_region.placeholder": "Please enter the Huawei Cloud OBS region (e.g. cn-north-1)",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_region.tooltip": "For more information, see <a href=\"https://console-intl.huaweicloud.com/apiexplorer/#/endpoint?locale=en-us\" target=\"_blank\">https://console-intl.huaweicloud.com/apiexplorer/#/endpoint</a>",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_bucket.label": "Huawei Cloud OBS bucket name",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_bucket.placeholder": "Please enter the Huawei Cloud OBS bucket name",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_bucket.tooltip": "For more information, see <a href=\"https://support.huaweicloud.com/productdesc-obs/obs_03_0207.html\" target=\"_blank\">https://support.huaweicloud.com/productdesc-obs/obs_03_0207.html</a>",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_domain.label": "Huawei Cloud OBS custom domain",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_domain.placeholder": "Please enter the Huawei Cloud OBS custom domain name",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_domain.tooltip": "For more information, see <a href=\"https://support.huaweicloud.com/productdesc-obs/obs_03_0207.html\" target=\"_blank\">https://support.huaweicloud.com/productdesc-obs/obs_03_0207.html</a>",
|
||||
"workflow_node.deploy.form.huaweicloud_elb_region.label": "Huawei Cloud ELB region",
|
||||
"workflow_node.deploy.form.huaweicloud_elb_region.placeholder": "Please enter Huawei Cloud ELB region (e.g. cn-north-1)",
|
||||
"workflow_node.deploy.form.huaweicloud_elb_region.tooltip": "For more information, see <a href=\"https://console-intl.huaweicloud.com/apiexplorer/#/endpoint?locale=en-us\" target=\"_blank\">https://console-intl.huaweicloud.com/apiexplorer/#/endpoint</a>",
|
||||
|
||||
@@ -95,8 +95,8 @@
|
||||
"provider.huaweicloud.cdn": "华为云 - 内容分发网络 CDN",
|
||||
"provider.huaweicloud.dns": "华为云 - 云解析 DNS",
|
||||
"provider.huaweicloud.elb": "华为云 - 弹性负载均衡 ELB",
|
||||
"provider.huaweicloud.obs": "华为云 - 对象储存服务 OBS",
|
||||
"provider.huaweicloud.scm_upload": "华为云 - 上传到云证书管理服务 SCM",
|
||||
"provider.huaweicloud.obs": "华为云 - 对象储存 OBS",
|
||||
"provider.huaweicloud.waf": "华为云 - Web 应用防火墙 WAF",
|
||||
"provider.jdcloud": "京东云",
|
||||
"provider.jdcloud.alb": "京东云 - 应用负载均衡 ALB",
|
||||
|
||||
@@ -516,14 +516,14 @@
|
||||
"workflow_node.deploy.form.huaweicloud_cdn_domain.label": "华为云 CDN 加速域名",
|
||||
"workflow_node.deploy.form.huaweicloud_cdn_domain.placeholder": "请输入华为云 CDN 加速域名(支持泛域名)",
|
||||
"workflow_node.deploy.form.huaweicloud_cdn_domain.tooltip": "这是什么?请参阅 <a href=\"https://console.huaweicloud.com/cdn\" target=\"_blank\">https://console.huaweicloud.com/cdn</a>",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_endpoint.label": "华为云 OBS 接口端点",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_endpoint.placeholder": "请输入华为云 OBS 接口端点(例如:obs.cn-north-4.myhuaweicloud.com)",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_endpoint.tooltip": "这是什么?请参阅 <a href=\"https://support.huaweicloud.com/productdesc-obs/obs_03_0152.html\" target=\"_blank\">https://support.huaweicloud.com/productdesc-obs/obs_03_0152.html</a>",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_bucket.label": "华为云 COS 存储桶名",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_bucket.placeholder": "请输入华为云 COS 存储桶名",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_region.label": "华为云 OBS 服务区域",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_region.placeholder": "请输入华为云 OBS 服务区域(例如:cn-north-1)",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_region.tooltip": "这是什么?请参阅 <a href=\"https://console.huaweicloud.com/apiexplorer/#/endpoint\" target=\"_blank\">https://console.huaweicloud.com/apiexplorer/#/endpoint</a>",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_bucket.label": "华为云 OBS 存储桶名",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_bucket.placeholder": "请输入华为云 OBS 存储桶名",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_bucket.tooltip": "这是什么?请参阅 <a href=\"https://support.huaweicloud.com/productdesc-obs/obs_03_0207.html\" target=\"_blank\">https://support.huaweicloud.com/productdesc-obs/obs_03_0207.html</a>",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_domain.label": "华为云 COS 自定义域名",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_domain.placeholder": "请输入华为云 COS 自定义域名",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_domain.label": "华为云 OBS 自定义域名",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_domain.placeholder": "请输入华为云 OBS 自定义域名",
|
||||
"workflow_node.deploy.form.huaweicloud_obs_domain.tooltip": "这是什么?请参阅 <a href=\"https://support.huaweicloud.com/productdesc-obs/obs_03_0207.html\" target=\"_blank\">https://support.huaweicloud.com/productdesc-obs/obs_03_0207.html</a>",
|
||||
"workflow_node.deploy.form.huaweicloud_elb_region.label": "华为云 ELB 服务区域",
|
||||
"workflow_node.deploy.form.huaweicloud_elb_region.placeholder": "请输入华为云 ELB 服务区域(例如:cn-north-1)",
|
||||
|
||||
Reference in New Issue
Block a user