feat: configure k8s secret type

This commit is contained in:
Fu Diwei 2025-01-01 19:13:48 +08:00
parent 880c8819b4
commit e2d29b8fa2
13 changed files with 98 additions and 73 deletions

View File

@ -221,6 +221,7 @@ func createDeployer(target string, accessConfig string, deployConfig map[string]
KubeConfig: access.KubeConfig,
Namespace: maps.GetValueOrDefaultAsString(deployConfig, "namespace", "default"),
SecretName: maps.GetValueAsString(deployConfig, "secretName"),
SecretType: maps.GetValueOrDefaultAsString(deployConfig, "secretType", "kubernetes.io/tls"),
SecretDataKeyForCrt: maps.GetValueOrDefaultAsString(deployConfig, "secretDataKeyForCrt", "tls.crt"),
SecretDataKeyForKey: maps.GetValueOrDefaultAsString(deployConfig, "secretDataKeyForKey", "tls.key"),
}, logger)

View File

@ -20,13 +20,15 @@ import (
type K8sSecretDeployerConfig struct {
// kubeconfig 文件内容。
KubeConfig string `json:"kubeConfig,omitempty"`
// K8s 命名空间。
// Kubernetes 命名空间。
Namespace string `json:"namespace,omitempty"`
// K8s Secret 名称。
// Kubernetes Secret 名称。
SecretName string `json:"secretName"`
// K8s Secret 中用于存放证书的 Key。
// Kubernetes Secret 类型。
SecretType string `json:"secretType"`
// Kubernetes Secret 中用于存放证书的 Key。
SecretDataKeyForCrt string `json:"secretDataKeyForCrt,omitempty"`
// K8s Secret 中用于存放私钥的 Key。
// Kubernetes Secret 中用于存放私钥的 Key。
SecretDataKeyForKey string `json:"secretDataKeyForKey,omitempty"`
}
@ -102,7 +104,7 @@ func (d *K8sSecretDeployer) Deploy(ctx context.Context, certPem string, privkeyP
Name: d.config.SecretName,
Annotations: secretAnnotations,
},
Type: k8sCore.SecretType("kubernetes.io/tls"),
Type: k8sCore.SecretType(d.config.SecretType),
}
secretPayload.Data = make(map[string][]byte)
secretPayload.Data[d.config.SecretDataKeyForCrt] = []byte(certPem)
@ -118,7 +120,7 @@ func (d *K8sSecretDeployer) Deploy(ctx context.Context, certPem string, privkeyP
}
// 更新 Secret 实例
secretPayload.Type = k8sCore.SecretType("kubernetes.io/tls")
secretPayload.Type = k8sCore.SecretType(d.config.SecretType)
if secretPayload.ObjectMeta.Annotations == nil {
secretPayload.ObjectMeta.Annotations = secretAnnotations
} else {

View File

@ -5,7 +5,7 @@ const End = () => {
return (
<div className="flex flex-col items-center">
<div className="size-[20px] rounded-full bg-stone-400"></div>
<div className="text-sm text-stone-400 mt-2">{t("workflow_node.end.title")}</div>
<div className="text-sm text-stone-400 mt-2">{t("workflow_node.end.label")}</div>
</div>
);
};

View File

@ -45,6 +45,10 @@ const DeployNodeFormAliyunCLBFields = () => {
const formRule = createSchemaFieldRule(formSchema);
const formInst = Form.useFormInstance();
const initialValues: Partial<z.infer<typeof formSchema>> = {
listenerPort: 443,
};
const fieldResourceType = Form.useWatch("resourceType", formInst);
return (
@ -84,7 +88,7 @@ const DeployNodeFormAliyunCLBFields = () => {
label={t("workflow_node.deploy.form.aliyun_clb_listener_port.label")}
rules={[formRule]}
tooltip={<span dangerouslySetInnerHTML={{ __html: t("workflow_node.deploy.form.aliyun_clb_listener_port.tooltip") }}></span>}
initialValue={443}
initialValue={initialValues.listenerPort}
>
<Input type="number" min={1} max={65535} placeholder={t("workflow_node.deploy.form.aliyun_clb_listener_port.placeholder")} />
</Form.Item>

View File

@ -17,6 +17,11 @@ const DeployNodeFormKubernetesSecretFields = () => {
.nonempty(t("workflow_node.deploy.form.k8s_secret_name.placeholder"))
.max(256, t("common.errmsg.string_max", { max: 256 }))
.trim(),
secretType: z
.string({ message: t("workflow_node.deploy.form.k8s_secret_type.placeholder") })
.nonempty(t("workflow_node.deploy.form.k8s_secret_type.placeholder"))
.max(256, t("common.errmsg.string_max", { max: 256 }))
.trim(),
secretDataKeyForCrt: z
.string({ message: t("workflow_node.deploy.form.k8s_secret_data_key_for_crt.placeholder") })
.nonempty(t("workflow_node.deploy.form.k8s_secret_data_key_for_crt.placeholder"))
@ -30,6 +35,13 @@ const DeployNodeFormKubernetesSecretFields = () => {
});
const formRule = createSchemaFieldRule(formSchema);
const initialValues: Partial<z.infer<typeof formSchema>> = {
namespace: "default",
secretType: "kubernetes.io/tls",
secretDataKeyForCrt: "tls.crt",
secretDataKeyForKey: "tls.key",
};
return (
<>
<Form.Item
@ -37,7 +49,7 @@ const DeployNodeFormKubernetesSecretFields = () => {
label={t("workflow_node.deploy.form.k8s_namespace.label")}
rules={[formRule]}
tooltip={<span dangerouslySetInnerHTML={{ __html: t("workflow_node.deploy.form.k8s_namespace.tooltip") }}></span>}
initialValue="default"
initialValue={initialValues.namespace}
>
<Input placeholder={t("workflow_node.deploy.form.k8s_namespace.placeholder")} />
</Form.Item>
@ -51,12 +63,22 @@ const DeployNodeFormKubernetesSecretFields = () => {
<Input placeholder={t("workflow_node.deploy.form.k8s_secret_name.placeholder")} />
</Form.Item>
<Form.Item
name="secretType"
label={t("workflow_node.deploy.form.k8s_secret_type.label")}
rules={[formRule]}
tooltip={<span dangerouslySetInnerHTML={{ __html: t("workflow_node.deploy.form.k8s_secret_type.tooltip") }}></span>}
initialValue={initialValues.secretType}
>
<Input placeholder={t("workflow_node.deploy.form.k8s_secret_type.placeholder")} />
</Form.Item>
<Form.Item
name="secretDataKeyForCrt"
label={t("workflow_node.deploy.form.k8s_secret_data_key_for_crt.label")}
rules={[formRule]}
tooltip={<span dangerouslySetInnerHTML={{ __html: t("workflow_node.deploy.form.k8s_secret_data_key_for_crt.tooltip") }}></span>}
initialValue="tls.crt"
initialValue={initialValues.secretDataKeyForCrt}
>
<Input placeholder={t("workflow_node.deploy.form.k8s_secret_data_key_for_crt.placeholder")} />
</Form.Item>
@ -66,7 +88,7 @@ const DeployNodeFormKubernetesSecretFields = () => {
label={t("workflow_node.deploy.form.k8s_secret_data_key_for_key.label")}
rules={[formRule]}
tooltip={<span dangerouslySetInnerHTML={{ __html: t("workflow_node.deploy.form.k8s_secret_data_key_for_key.tooltip") }}></span>}
initialValue="tls.key"
initialValue={initialValues.secretDataKeyForKey}
>
<Input placeholder={t("workflow_node.deploy.form.k8s_secret_data_key_for_key.placeholder")} />
</Form.Item>

View File

@ -71,6 +71,13 @@ const DeployNodeFormLocalFields = () => {
const formRule = createSchemaFieldRule(formSchema);
const formInst = Form.useFormInstance();
const initialValues: Partial<z.infer<typeof formSchema>> = {
format: FORMAT_PEM,
certPath: "/etc/ssl/certs/cert.crt",
keyPath: "/etc/ssl/certs/cert.key",
shellEnv: SHELLENV_SH,
};
const fieldFormat = Form.useWatch("format", formInst);
const fieldCertPath = Form.useWatch("certPath", formInst);
@ -183,7 +190,7 @@ Remove-Item -Path "$pfxPath" -Force
return (
<>
<Form.Item name="format" label={t("workflow_node.deploy.form.local_format.label")} rules={[formRule]} initialValue={FORMAT_PEM}>
<Form.Item name="format" label={t("workflow_node.deploy.form.local_format.label")} rules={[formRule]} initialValue={initialValues.format}>
<Select placeholder={t("workflow_node.deploy.form.local_format.placeholder")} onSelect={handleFormatSelect}>
<Select.Option key={FORMAT_PEM} value={FORMAT_PEM}>
{t("workflow_node.deploy.form.local_format.option.pem.label")}
@ -202,7 +209,7 @@ Remove-Item -Path "$pfxPath" -Force
label={t("workflow_node.deploy.form.local_cert_path.label")}
rules={[formRule]}
tooltip={<span dangerouslySetInnerHTML={{ __html: t("workflow_node.deploy.form.local_cert_path.tooltip") }}></span>}
initialValue="/etc/ssl/certs/cert.crt"
initialValue={initialValues.certPath}
>
<Input placeholder={t("workflow_node.deploy.form.local_cert_path.placeholder")} />
</Form.Item>
@ -213,7 +220,7 @@ Remove-Item -Path "$pfxPath" -Force
label={t("workflow_node.deploy.form.local_key_path.label")}
rules={[formRule]}
tooltip={<span dangerouslySetInnerHTML={{ __html: t("workflow_node.deploy.form.local_key_path.tooltip") }}></span>}
initialValue="/etc/ssl/certs/cert.key"
initialValue={initialValues.keyPath}
>
<Input placeholder={t("workflow_node.deploy.form.local_key_path.placeholder")} />
</Form.Item>
@ -259,7 +266,7 @@ Remove-Item -Path "$pfxPath" -Force
</Form.Item>
</Show>
<Form.Item name="shellEnv" label={t("workflow_node.deploy.form.local_shell_env.label")} rules={[formRule]} initialValue={SHELLENV_SH}>
<Form.Item name="shellEnv" label={t("workflow_node.deploy.form.local_shell_env.label")} rules={[formRule]} initialValue={initialValues.shellEnv}>
<Select placeholder={t("workflow_node.deploy.form.local_shell_env.placeholder")}>
<Select.Option key={SHELLENV_SH} value={SHELLENV_SH}>
{t("workflow_node.deploy.form.local_shell_env.option.sh.label")}

View File

@ -64,6 +64,12 @@ const DeployNodeFormSSHFields = () => {
const formRule = createSchemaFieldRule(formSchema);
const formInst = Form.useFormInstance();
const initialValues: Partial<z.infer<typeof formSchema>> = {
format: FORMAT_PEM,
certPath: "/etc/ssl/certs/cert.crt",
keyPath: "/etc/ssl/certs/cert.key",
};
const fieldFormat = Form.useWatch("format", formInst);
const fieldCertPath = Form.useWatch("certPath", formInst);
@ -109,7 +115,7 @@ const DeployNodeFormSSHFields = () => {
return (
<>
<Form.Item name="format" label={t("workflow_node.deploy.form.ssh_format.label")} rules={[formRule]} initialValue={FORMAT_PEM}>
<Form.Item name="format" label={t("workflow_node.deploy.form.ssh_format.label")} rules={[formRule]} initialValue={initialValues.format}>
<Select placeholder={t("workflow_node.deploy.form.ssh_format.placeholder")} onSelect={handleFormatSelect}>
<Select.Option key={FORMAT_PEM} value={FORMAT_PEM}>
{t("workflow_node.deploy.form.ssh_format.option.pem.label")}
@ -128,7 +134,7 @@ const DeployNodeFormSSHFields = () => {
label={t("workflow_node.deploy.form.ssh_cert_path.label")}
rules={[formRule]}
tooltip={<span dangerouslySetInnerHTML={{ __html: t("workflow_node.deploy.form.ssh_cert_path.tooltip") }}></span>}
initialValue="/etc/ssl/certs/cert.crt"
initialValue={initialValues.certPath}
>
<Input placeholder={t("workflow_node.deploy.form.ssh_cert_path.placeholder")} />
</Form.Item>
@ -139,7 +145,7 @@ const DeployNodeFormSSHFields = () => {
label={t("workflow_node.deploy.form.ssh_key_path.label")}
rules={[formRule]}
tooltip={<span dangerouslySetInnerHTML={{ __html: t("workflow_node.deploy.form.ssh_key_path.tooltip") }}></span>}
initialValue="/etc/ssl/certs/cert.key"
initialValue={initialValues.keyPath}
>
<Input placeholder={t("workflow_node.deploy.form.ssh_key_path.placeholder")} />
</Form.Item>

View File

@ -1,7 +1,7 @@
import { useState } from "react";
import { useTranslation } from "react-i18next";
import { useRequest } from "ahooks";
import { Button, Empty, notification, Space, Table, theme, Tooltip, Typography, type TableProps } from "antd";
import { Button, Empty, notification, Space, Table, theme, Typography, type TableProps } from "antd";
import {
CheckCircleOutlined as CheckCircleOutlinedIcon,
CloseCircleOutlined as CloseCircleOutlinedIcon,

View File

@ -4,28 +4,6 @@ import { nanoid } from "nanoid";
import i18n from "@/i18n";
import { deployProvidersMap } from "./provider";
/**
* @deprecated
*/
export type WorkflowRunLog = {
id: string;
workflow: string;
log: WorkflowRunLogItem[];
error: string;
succeed: boolean;
created: string;
updated: string;
};
/**
* @deprecated
*/
export type WorkflowRunLogItem = {
nodeName: string;
error: string;
outputs: WorkflowOutput[];
};
export type WorkflowOutput = {
time: string;
title: string;
@ -56,13 +34,13 @@ export enum WorkflowNodeType {
}
export const workflowNodeTypeDefaultName: Map<WorkflowNodeType, string> = new Map([
[WorkflowNodeType.Start, i18n.t("workflow_node.start.title")],
[WorkflowNodeType.End, i18n.t("workflow_node.end.title")],
[WorkflowNodeType.Branch, i18n.t("workflow_node.branch.title")],
[WorkflowNodeType.Condition, i18n.t("workflow_node.condition.title")],
[WorkflowNodeType.Apply, i18n.t("workflow_node.apply.title")],
[WorkflowNodeType.Deploy, i18n.t("workflow_node.deploy.title")],
[WorkflowNodeType.Notify, i18n.t("workflow_node.notify.title")],
[WorkflowNodeType.Start, i18n.t("workflow_node.start.label")],
[WorkflowNodeType.End, i18n.t("workflow_node.end.label")],
[WorkflowNodeType.Branch, i18n.t("workflow_node.branch.label")],
[WorkflowNodeType.Condition, i18n.t("workflow_node.condition.label")],
[WorkflowNodeType.Apply, i18n.t("workflow_node.apply.label")],
[WorkflowNodeType.Deploy, i18n.t("workflow_node.deploy.label")],
[WorkflowNodeType.Notify, i18n.t("workflow_node.notify.label")],
[WorkflowNodeType.Custom, i18n.t("workflow_node.custom.title")],
]);

View File

@ -40,6 +40,5 @@
"workflow.common.certificate.label": "Certificate",
"workflow.node.setting.label": "Setting Node",
"workflow.node.delete.label": "Delete Node",
"workflow.node.addBranch.label": "Add Branch",
"workflow.node.selectNodeType.label": "Select Node Type"
"workflow.node.addBranch.label": "Add Branch"
}

View File

@ -1,5 +1,5 @@
{
"workflow_node.start.title": "Start",
"workflow_node.start.label": "Start",
"workflow_node.start.form.trigger.label": "Trigger",
"workflow_node.start.form.trigger.placeholder": "Please select trigger",
"workflow_node.start.form.trigger.tooltip": "Auto: Time triggered based on cron expression.<br>Manual: Manually triggered.",
@ -12,7 +12,7 @@
"workflow_node.start.form.trigger_cron.extra": "Expected execution time for the last 5 times:",
"workflow_node.start.form.trigger_cron_alert.content": "Tips: If you have multiple workflows, it is recommended to set them to run at multiple times of the day instead of always running at specific times.<br><br>Reference links:<br>1. <a href=\"https://letsencrypt.org/docs/rate-limits/\" target=\"_blank\">Lets Encrypt rate limits</a><br>2. <a href=\"https://letsencrypt.org/docs/faq/#why-should-my-let-s-encrypt-acme-client-run-at-a-random-time\" target=\"_blank\">Why should my Lets Encrypt (ACME) client run at a random time?</a>",
"workflow_node.apply.title": "Application",
"workflow_node.apply.label": "Application",
"workflow_node.apply.form.domains.label": "Domains",
"workflow_node.apply.form.domains.placeholder": "Please enter domains (separated by semicolons)",
"workflow_node.apply.form.domains.tooltip": "Wildcard domain: *.example.com",
@ -40,7 +40,7 @@
"workflow_node.apply.form.disable_follow_cname.label": "Disable CNAME following",
"workflow_node.apply.form.disable_follow_cname.tooltip": "It determines whether to disable CNAME following during ACME DNS-01 authentication. If you don't understand this option, just keep it by default.<br><a href=\"https://letsencrypt.org/2019/10/09/onboarding-your-customers-with-lets-encrypt-and-acme/#the-advantages-of-a-cname\" target=\"_blank\">Learn more</a>.",
"workflow_node.deploy.title": "Deployment",
"workflow_node.deploy.label": "Deployment",
"workflow_node.deploy.form.provider_type.label": "Deploy target",
"workflow_node.deploy.form.provider_type.placeholder": "Please select deploy target",
"workflow_node.deploy.form.provider_access.label": "Host provider authorization",
@ -138,16 +138,19 @@
"workflow_node.deploy.form.huaweicloud_elb_listener_id.placeholder": "Please enter Huawei Cloud ELB listener ID",
"workflow_node.deploy.form.huaweicloud_elb_listener_id.tooltip": "For more information, see <a href=\"https://console-intl.huaweicloud.com/vpc/#/elb/list/grid\" target=\"_blank\">https://console-intl.huaweicloud.com/vpc/#/elb/list/grid</a>",
"workflow_node.deploy.form.k8s_namespace.label": "Kubernetes Namespace",
"workflow_node.deploy.form.k8s_namespace.placeholder": "Please enter Kubernetes namespace",
"workflow_node.deploy.form.k8s_namespace.placeholder": "Please enter Kubernetes Namespace",
"workflow_node.deploy.form.k8s_namespace.tooltip": "For more information, see <a href=\"https://kubernetes.io/docs/concepts/overview/working-with-objects/namespaces/\" target=\"_blank\">https://kubernetes.io/docs/concepts/overview/working-with-objects/namespaces/</a>",
"workflow_node.deploy.form.k8s_secret_name.label": "Kubernetes secret name",
"workflow_node.deploy.form.k8s_secret_name.placeholder": "Please enter Kubernetes secret name",
"workflow_node.deploy.form.k8s_secret_name.label": "Kubernetes Secret name",
"workflow_node.deploy.form.k8s_secret_name.placeholder": "Please enter Kubernetes Secret name",
"workflow_node.deploy.form.k8s_secret_name.tooltip": "For more information, see <a href=\"https://kubernetes.io/docs/concepts/configuration/secret/\" target=\"_blank\">https://kubernetes.io/docs/concepts/configuration/secret/</a>",
"workflow_node.deploy.form.k8s_secret_data_key_for_crt.label": "Kubernetes secret data key for certificate",
"workflow_node.deploy.form.k8s_secret_data_key_for_crt.placeholder": "Please enter secret data key for certificate",
"workflow_node.deploy.form.k8s_secret_type.label": "Kubernetes Secret type",
"workflow_node.deploy.form.k8s_secret_type.placeholder": "Please enter Kubernetes Secret type",
"workflow_node.deploy.form.k8s_secret_type.tooltip": "For more information, see <a href=\"https://kubernetes.io/docs/concepts/configuration/secret/\" target=\"_blank\">https://kubernetes.io/docs/concepts/configuration/secret/</a>",
"workflow_node.deploy.form.k8s_secret_data_key_for_crt.label": "Kubernetes Secret data key for certificate",
"workflow_node.deploy.form.k8s_secret_data_key_for_crt.placeholder": "Please enter Kubernetes Secret data key for certificate",
"workflow_node.deploy.form.k8s_secret_data_key_for_crt.tooltip": "For more information, see <a href=\"https://kubernetes.io/docs/concepts/configuration/secret/\" target=\"_blank\">https://kubernetes.io/docs/concepts/configuration/secret/</a>",
"workflow_node.deploy.form.k8s_secret_data_key_for_key.label": "Kubernetes secret data key for private key",
"workflow_node.deploy.form.k8s_secret_data_key_for_key.placeholder": "Please enter secret data key for private key",
"workflow_node.deploy.form.k8s_secret_data_key_for_key.label": "Kubernetes Secret data key for private key",
"workflow_node.deploy.form.k8s_secret_data_key_for_key.placeholder": "Please enter Kubernetes Secret data key for private key",
"workflow_node.deploy.form.k8s_secret_data_key_for_key.tooltip": "For more information, see <a href=\"https://kubernetes.io/docs/concepts/configuration/secret/\" target=\"_blank\">https://kubernetes.io/docs/concepts/configuration/secret/</a>",
"workflow_node.deploy.form.local_format.label": "File format",
"workflow_node.deploy.form.local_format.placeholder": "Please select file format",
@ -270,7 +273,7 @@
"workflow_node.deploy.form.webhook_data.label": "Webhook data (JSON format)",
"workflow_node.deploy.form.webhook_data.placeholder": "Please enter Webhook data",
"workflow_node.notify.title": "Notification",
"workflow_node.notify.label": "Notification",
"workflow_node.notify.form.subject.label": "Subject",
"workflow_node.notify.form.subject.placeholder": "Please enter subject",
"workflow_node.notify.form.message.label": "Message",
@ -279,9 +282,9 @@
"workflow_node.notify.form.channel.placeholder": "Please select channel",
"workflow_node.notify.form.channel.button": "Configure",
"workflow_node.end.title": "End",
"workflow_node.end.label": "End",
"workflow_node.branch.title": "Branch",
"workflow_node.branch.label": "Branch",
"workflow_node.condition.title": "Condition"
"workflow_node.condition.label": "Condition"
}

View File

@ -40,6 +40,5 @@
"workflow.common.certificate.label": "证书",
"workflow.node.setting.label": "设置节点",
"workflow.node.delete.label": "删除节点",
"workflow.node.addBranch.label": "添加分支",
"workflow.node.selectNodeType.label": "选择节点类型"
"workflow.node.addBranch.label": "添加分支"
}

View File

@ -1,5 +1,5 @@
{
"workflow_node.start.title": "开始",
"workflow_node.start.label": "开始",
"workflow_node.start.form.trigger.label": "触发方式",
"workflow_node.start.form.trigger.placeholder": "请选择触发方式",
"workflow_node.start.form.trigger.tooltip": "自动触发:基于 Cron 表达式定时触发。<br>手动触发:手动点击执行触发。",
@ -12,7 +12,7 @@
"workflow_node.start.form.trigger_cron.extra": "预计最近 5 次执行时间:",
"workflow_node.start.form.trigger_cron_alert.content": "小贴士:如果你有多个工作流,建议将它们设置为在一天中的多个时间段运行,而非总是在相同的特定时间。<br><br>参考链接:<br>1. <a href=\"https://letsencrypt.org/zh-cn/docs/rate-limits/\" target=\"_blank\">Lets Encrypt 速率限制</a><br>2. <a href=\"https://letsencrypt.org/zh-cn/docs/faq/#%E4%B8%BA%E4%BB%80%E4%B9%88%E6%88%91%E7%9A%84-let-s-encrypt-acme-%E5%AE%A2%E6%88%B7%E7%AB%AF%E5%90%AF%E5%8A%A8%E6%97%B6%E9%97%B4%E5%BA%94%E5%BD%93%E9%9A%8F%E6%9C%BA\" target=\"_blank\">为什么我的 Lets Encrypt (ACME) 客户端启动时间应当随机?</a>",
"workflow_node.apply.title": "申请",
"workflow_node.apply.label": "申请",
"workflow_node.apply.form.domains.label": "域名",
"workflow_node.apply.form.domains.placeholder": "请输入域名(多个值请用半角分号隔开)",
"workflow_node.apply.form.domains.tooltip": "泛域名表示形式为:*.example.com",
@ -40,7 +40,7 @@
"workflow_node.apply.form.disable_follow_cname.label": "禁止 CNAME 跟随",
"workflow_node.apply.form.disable_follow_cname.tooltip": "在 ACME DNS-01 认证时是否禁止 CNAME 跟随。如果你不了解该选项的用途,保持默认即可。<br><a href=\"https://letsencrypt.org/2019/10/09/onboarding-your-customers-with-lets-encrypt-and-acme/#the-advantages-of-a-cname\" target=\"_blank\">点此了解更多</a>。",
"workflow_node.deploy.title": "部署",
"workflow_node.deploy.label": "部署",
"workflow_node.deploy.form.provider_type.label": "部署目标",
"workflow_node.deploy.form.provider_type.placeholder": "请选择部署目标",
"workflow_node.deploy.form.provider_access.label": "主机提供商授权",
@ -143,6 +143,9 @@
"workflow_node.deploy.form.k8s_secret_name.label": "Kubernetes Secret 名称",
"workflow_node.deploy.form.k8s_secret_name.placeholder": "请输入 Kubernetes Secret 名称",
"workflow_node.deploy.form.k8s_secret_name.tooltip": "这是什么?请参阅 <a href=\"https://kubernetes.io/zh-cn/docs/concepts/configuration/secret/\" target=\"_blank\">https://kubernetes.io/zh-cn/docs/concepts/configuration/secret/</a>",
"workflow_node.deploy.form.k8s_secret_type.label": "Kubernetes Secret 类型",
"workflow_node.deploy.form.k8s_secret_type.placeholder": "请输入 Kubernetes Secret 类型",
"workflow_node.deploy.form.k8s_secret_type.tooltip": "这是什么?请参阅 <a href=\"https://kubernetes.io/zh-cn/docs/concepts/configuration/secret/\" target=\"_blank\">https://kubernetes.io/zh-cn/docs/concepts/configuration/secret/</a>",
"workflow_node.deploy.form.k8s_secret_data_key_for_crt.label": "Kubernetes Secret 数据键(用于存放证书的字段)",
"workflow_node.deploy.form.k8s_secret_data_key_for_crt.placeholder": "请输入 Kubernetes Secret 中用于存放证书的数据键",
"workflow_node.deploy.form.k8s_secret_data_key_for_crt.tooltip": "这是什么?请参阅 <a href=\"https://kubernetes.io/zh-cn/docs/concepts/configuration/secret/\" target=\"_blank\">https://kubernetes.io/zh-cn/docs/concepts/configuration/secret/</a>",
@ -270,7 +273,7 @@
"workflow_node.deploy.form.webhook_data.label": "Webhook 回调数据JSON 格式)",
"workflow_node.deploy.form.webhook_data.placeholder": "请输入 Webhook 回调数据",
"workflow_node.notify.title": "通知",
"workflow_node.notify.label": "通知",
"workflow_node.notify.form.subject.label": "通知主题",
"workflow_node.notify.form.subject.placeholder": "请输入通知主题",
"workflow_node.notify.form.message.label": "通知内容",
@ -279,8 +282,9 @@
"workflow_node.notify.form.channel.placeholder": "请选择通知渠道",
"workflow_node.notify.form.channel.button": "去配置",
"workflow_node.end.title": "结束",
"workflow_node.end.label": "结束",
"workflow_node.branch.title": "分支",
"workflow_node.condition.title": "条件"
"workflow_node.branch.label": "分支",
"workflow_node.condition.label": "条件"
}