feat(ui): improve i18n

This commit is contained in:
Fu Diwei
2025-07-21 19:28:46 +08:00
parent 6f52c47fd5
commit a09be88920
27 changed files with 162 additions and 150 deletions
@@ -11,17 +11,17 @@ import { getErrMsg } from "@/utils/error";
import AccessForm, { type AccessFormInstance, type AccessFormProps } from "./AccessForm";
export type AccessEditDrawerProps = {
action: AccessFormProps["action"];
data?: AccessFormProps["initialValues"];
loading?: boolean;
open?: boolean;
scene: AccessFormProps["scene"];
trigger?: React.ReactNode;
usage?: AccessFormProps["usage"];
onOpenChange?: (open: boolean) => void;
afterSubmit?: (record: AccessModel) => void;
};
const AccessEditDrawer = ({ data, loading, trigger, scene, usage, afterSubmit, ...props }: AccessEditDrawerProps) => {
const AccessEditDrawer = ({ action, data, loading, trigger, usage, afterSubmit, ...props }: AccessEditDrawerProps) => {
const { t } = useTranslation();
const { notification } = App.useApp();
@@ -51,20 +51,20 @@ const AccessEditDrawer = ({ data, loading, trigger, scene, usage, afterSubmit, .
try {
let values: AccessModel = formRef.current!.getFieldsValue();
if (scene === "create") {
if (action === "create") {
if (data?.id) {
throw "Invalid props: `data`";
}
values = await createAccess(values);
} else if (scene === "edit") {
} else if (action === "edit") {
if (!data?.id) {
throw "Invalid props: `data`";
}
values = await updateAccess({ ...data, ...values });
} else {
throw "Invalid props: `scene`";
throw "Invalid props: `action`";
}
afterSubmit?.(values);
@@ -96,18 +96,18 @@ const AccessEditDrawer = ({ data, loading, trigger, scene, usage, afterSubmit, .
<Space className="w-full justify-end">
<Button onClick={handleCancelClick}>{t("common.button.cancel")}</Button>
<Button loading={formPending} type="primary" onClick={handleOkClick}>
{scene === "edit" ? t("common.button.save") : t("common.button.submit")}
{action === "edit" ? t("common.button.save") : t("common.button.submit")}
</Button>
</Space>
}
loading={loading}
maskClosable={!formPending}
open={open}
title={t(`access.action.${scene}`)}
title={t(`access.action.${action}.modal.title`)}
width={720}
onClose={() => setOpen(false)}
>
<AccessForm ref={formRef} initialValues={data} scene={scene === "create" ? "create" : "edit"} usage={usage} />
<AccessForm ref={formRef} initialValues={data} action={action === "create" ? "create" : "edit"} usage={usage} />
</Drawer>
</>
);
+8 -8
View File
@@ -11,17 +11,17 @@ import { getErrMsg } from "@/utils/error";
import AccessForm, { type AccessFormInstance, type AccessFormProps } from "./AccessForm";
export type AccessEditModalProps = {
action: AccessFormProps["action"];
data?: AccessFormProps["initialValues"];
loading?: boolean;
open?: boolean;
usage?: AccessFormProps["usage"];
scene: AccessFormProps["scene"];
trigger?: React.ReactNode;
onOpenChange?: (open: boolean) => void;
afterSubmit?: (record: AccessModel) => void;
};
const AccessEditModal = ({ data, loading, trigger, scene, usage, afterSubmit, ...props }: AccessEditModalProps) => {
const AccessEditModal = ({ action, data, loading, trigger, usage, afterSubmit, ...props }: AccessEditModalProps) => {
const { t } = useTranslation();
const { notification } = App.useApp();
@@ -51,20 +51,20 @@ const AccessEditModal = ({ data, loading, trigger, scene, usage, afterSubmit, ..
try {
let values: AccessModel = formRef.current!.getFieldsValue();
if (scene === "create") {
if (action === "create") {
if (data?.id) {
throw "Invalid props: `data`";
}
values = await createAccess(values);
} else if (scene === "edit") {
} else if (action === "edit") {
if (!data?.id) {
throw "Invalid props: `data`";
}
values = await updateAccess({ ...data, ...values });
} else {
throw "Invalid props: `preset`";
throw "Invalid props: `action`";
}
afterSubmit?.(values);
@@ -103,15 +103,15 @@ const AccessEditModal = ({ data, loading, trigger, scene, usage, afterSubmit, ..
confirmLoading={formPending}
destroyOnHidden
loading={loading}
okText={scene === "edit" ? t("common.button.save") : t("common.button.submit")}
okText={action === "edit" ? t("common.button.save") : t("common.button.submit")}
open={open}
title={t(`access.action.${scene}`)}
title={t(`access.action.${action}`)}
width={480}
onOk={handleOkClick}
onCancel={handleCancelClick}
>
<div className="pt-4 pb-2">
<AccessForm ref={formRef} initialValues={data} scene={scene === "create" ? "create" : "edit"} usage={usage} />
<AccessForm ref={formRef} initialValues={data} action={action === "create" ? "create" : "edit"} usage={usage} />
</div>
</Modal>
</>
+4 -4
View File
@@ -86,15 +86,15 @@ import AccessFormWestcnConfig from "./AccessFormWestcnConfig";
import AccessFormZeroSSLConfig from "./AccessFormZeroSSLConfig";
type AccessFormFieldValues = Partial<MaybeModelRecord<AccessModel>>;
type AccessFormScenes = "create" | "edit";
type AccessFormActions = "create" | "edit";
type AccessFormUsages = "both-dns-hosting" | "ca-only" | "notification-only";
export type AccessFormProps = {
className?: string;
style?: React.CSSProperties;
action: AccessFormActions;
disabled?: boolean;
initialValues?: AccessFormFieldValues;
scene: AccessFormScenes;
usage?: AccessFormUsages;
onValuesChange?: (values: AccessFormFieldValues) => void;
};
@@ -105,7 +105,7 @@ export type AccessFormInstance = {
validateFields: FormInstance<AccessFormFieldValues>["validateFields"];
};
const AccessForm = forwardRef<AccessFormInstance, AccessFormProps>(({ className, style, disabled, initialValues, usage, scene, onValuesChange }, ref) => {
const AccessForm = forwardRef<AccessFormInstance, AccessFormProps>(({ className, style, action, disabled, initialValues, usage, onValuesChange }, ref) => {
const { t } = useTranslation();
const formSchema = z.object({
@@ -406,7 +406,7 @@ const AccessForm = forwardRef<AccessFormInstance, AccessFormProps>(({ className,
<Form.Item name="provider" label={providerLabel} rules={[formRule]} tooltip={providerTooltip}>
<AccessProviderSelect
filter={providerFilter}
disabled={scene !== "create"}
disabled={action !== "create"}
placeholder={providerPlaceholder}
showOptionTags={usage == null || (usage === "both-dns-hosting" ? { [ACCESS_USAGES.DNS]: true, [ACCESS_USAGES.HOSTING]: true } : false)}
showSearch={!disabled}
@@ -118,7 +118,7 @@ const CertificateDetail = ({ data, ...props }: CertificateDetailProps) => {
}}
>
<Button icon={<IconChevronDown size="1.25em" />} iconPosition="end" type="primary">
{t("certificate.action.download")}
{t("common.button.download")}
</Button>
</Dropdown>
</div>
@@ -35,7 +35,7 @@ const CAProviderSelect = ({ filter, ...props }: CAProviderSelectProps) => {
temp.unshift({
key: "",
value: "",
label: t("provider.default_ca_provider.label"),
label: t("provider.text.default_ca_provider.label"),
data: {} as CAProvider,
});
@@ -47,7 +47,7 @@ const CAProviderSelect = ({ filter, ...props }: CAProviderSelectProps) => {
return (
<div className="flex items-center gap-2 truncate overflow-hidden">
<Typography.Text className="italic" ellipsis italic>
{t("provider.default_ca_provider.label")}
{t("provider.text.default_ca_provider.label")}
</Typography.Text>
</div>
);
@@ -299,7 +299,7 @@ const WorkflowRunArtifacts = ({ runId }: { runId: string }) => {
<CertificateDetailDrawer
data={record}
trigger={
<Tooltip title={t("certificate.action.view")}>
<Tooltip title={t("common.button.view")}>
<Button color="primary" disabled={!!record.deleted} icon={<IconBrowserShare size="1.25em" />} variant="text" />
</Tooltip>
}
+9 -7
View File
@@ -106,7 +106,7 @@ const WorkflowRuns = ({ className, style, workflowId }: WorkflowRunsProps) => {
return (
<div className="flex items-center justify-end">
<Tooltip title={t("workflow_run.action.view")}>
<Tooltip title={t("common.button.view")}>
<Button
color="primary"
icon={<IconBrowserShare size="1.25em" />}
@@ -117,7 +117,7 @@ const WorkflowRuns = ({ className, style, workflowId }: WorkflowRunsProps) => {
}}
/>
</Tooltip>
<Tooltip title={t("workflow_run.action.cancel")}>
<Tooltip title={t("workflow_run.action.cancel.button")}>
<Button
color="default"
disabled={!allowCancel}
@@ -129,7 +129,7 @@ const WorkflowRuns = ({ className, style, workflowId }: WorkflowRunsProps) => {
}}
/>
</Tooltip>
<Tooltip title={t("workflow_run.action.delete")}>
<Tooltip title={t("common.button.delete")}>
<Button
color="danger"
danger
@@ -216,8 +216,8 @@ const WorkflowRuns = ({ className, style, workflowId }: WorkflowRunsProps) => {
const handleRecordCancelClick = (workflowRun: WorkflowRunModel) => {
modal.confirm({
title: t("workflow_run.action.cancel"),
content: t("workflow_run.action.cancel.confirm"),
title: t("workflow_run.action.cancel.modal.title"),
content: t("workflow_run.action.cancel.modal.content"),
onOk: async () => {
try {
const resp = await cancelWorkflowRun(workflowId, workflowRun.id);
@@ -234,10 +234,12 @@ const WorkflowRuns = ({ className, style, workflowId }: WorkflowRunsProps) => {
const handleRecordDeleteClick = (workflowRun: WorkflowRunModel) => {
modal.confirm({
title: <span className="text-error">{t("workflow_run.action.delete")}</span>,
title: <span className="text-error">{t("workflow_run.action.modal.title")}</span>,
content: (
<span
dangerouslySetInnerHTML={{ __html: t("workflow_run.action.delete.confirm", { name: dayjs(workflowRun.startedAt).format("YYYY-MM-DD HH:mm:ss") }) }}
dangerouslySetInnerHTML={{
__html: t("workflow_run.action.delete.modal.content", { name: dayjs(workflowRun.startedAt).format("YYYY-MM-DD HH:mm:ss") }),
}}
/>
),
icon: (
@@ -326,7 +326,7 @@ const ApplyNodeConfigForm = forwardRef<ApplyNodeConfigFormInstance, ApplyNodeCon
</div>
<div className="text-right">
<AccessEditModal
scene="create"
action="create"
trigger={
<Button size="small" type="link">
{t("workflow_node.apply.form.provider_access.button")}
@@ -408,7 +408,7 @@ const ApplyNodeConfigForm = forwardRef<ApplyNodeConfigFormInstance, ApplyNodeCon
<div className="text-right">
<AccessEditModal
data={{ provider: caProvidersMap.get(fieldCAProvider!)?.provider }}
scene="create"
action="create"
trigger={
<Button size="small" type="link">
{t("workflow_node.apply.form.ca_provider_access.button")}
@@ -489,7 +489,7 @@ const DeployNodeConfigForm = forwardRef<DeployNodeConfigFormInstance, DeployNode
<div className="text-right">
<AccessEditModal
data={{ provider: deploymentProvidersMap.get(fieldProvider!)?.provider }}
scene="create"
action="create"
trigger={
<Button size="small" type="link">
{t("workflow_node.deploy.form.provider_access.button")}
@@ -199,7 +199,7 @@ const NotifyNodeConfigForm = forwardRef<NotifyNodeConfigFormInstance, NotifyNode
</div>
<div className="text-right">
<AccessEditModal
scene="create"
action="create"
trigger={
<Button size="small" type="link">
{t("workflow_node.notify.form.provider_access.button")}
+6 -5
View File
@@ -9,11 +9,12 @@
"access.search.placeholder": "Search by credential name ...",
"access.action.create": "Create credential",
"access.action.edit": "Edit credential",
"access.action.duplicate": "Duplicate credential",
"access.action.delete": "Delete credential",
"access.action.delete.confirm": "Are you sure want to delete this \"{{name}}\" credential?<br>This action cannot be undone.",
"access.action.create.button": "Create credential",
"access.action.create.modal.title": "Create credential",
"access.action.edit.modal.title": "Edit credential",
"access.action.duplicate.modal.title": "Duplicate credential",
"access.action.delete.modal.title": "Delete credential",
"access.action.delete.modal.content": "Are you sure want to delete this \"{{name}}\" credential?<br>This action cannot be undone.",
"access.props.name": "Name",
"access.props.provider.usage.dns": "DNS",
+2 -4
View File
@@ -8,10 +8,8 @@
"certificate.search.placeholder": "Search by certificate name or serial number ...",
"certificate.action.view": "View certificate",
"certificate.action.delete": "Delete certificate",
"certificate.action.delete.confirm": "Are you sure want to delete this \"{{name}}\" certificate?<br>This action cannot be undone.",
"certificate.action.download": "Download certificate",
"certificate.action.delete.modal.title": "Delete certificate",
"certificate.action.delete.modal.content": "Are you sure want to delete this \"{{name}}\" certificate?<br>This action cannot be undone.",
"certificate.props.subject_alt_names": "Name",
"certificate.props.validity": "Expiry",
+4
View File
@@ -2,8 +2,11 @@
"common.button.add": "Add",
"common.button.cancel": "Cancel",
"common.button.confirm": "Confirm",
"common.button.create": "Create",
"common.button.copy": "Copy",
"common.button.delete": "Delete",
"common.button.download": "Download",
"common.button.duplicate": "Duplicate",
"common.button.edit": "Edit",
"common.button.more": "More",
"common.button.ok": "Ok",
@@ -11,6 +14,7 @@
"common.button.reset": "Reset",
"common.button.save": "Save changes",
"common.button.submit": "Submit",
"common.button.view": "View",
"common.text.copied": "Copied",
"common.text.import_from_file": "Import from file ...",
+1 -1
View File
@@ -193,5 +193,5 @@
"provider.category.nas": "NAS",
"provider.category.other": "Other",
"provider.default_ca_provider.label": "(Default) Follow global settings"
"provider.text.default_ca_provider.label": "(Default) Follow global settings"
}
+19 -17
View File
@@ -8,15 +8,25 @@
"workflow.search.placeholder": "Search by workflow name ...",
"workflow.action.create": "Create workflow",
"workflow.action.edit": "Edit workflow",
"workflow.action.duplicate": "Duplicate workflow",
"workflow.action.duplicate.confirm": "Are you sure to duplicate this workflow?",
"workflow.action.delete": "Delete workflow",
"workflow.action.delete.confirm": "Are you sure want to delete this \"{{name}}\" workflow?<br>This action cannot be undone.",
"workflow.action.enable": "Enable",
"workflow.action.enable.failed.uncompleted": "Please complete the orchestration and publish the changes first",
"workflow.action.disable": "Disable",
"workflow.action.create.button": "Create workflow",
"workflow.action.duplicate.modal.title": "Duplicate workflow",
"workflow.action.duplicate.modal.content": "Are you sure to duplicate this \"{{name}}\" workflow?",
"workflow.action.delete.modal.title": "Delete workflow",
"workflow.action.delete.modal.content": "Are you sure want to delete this \"{{name}}\" workflow?<br>This action cannot be undone.",
"workflow.action.enable.button": "Activate",
"workflow.action.enable.errmsg.uncompleted": "Please complete the orchestration and publish the changes first",
"workflow.action.disable.button": "Deactivate",
"workflow.action.release.button": "Release",
"workflow.action.release.modal.title": "Release changes",
"workflow.action.release.modal.content": "Are you sure to release your changes?",
"workflow.action.release.errmsg.uncompleted": "Please complete the orchestration first",
"workflow.action.discard.button": "Discard",
"workflow.action.discard.modal.title": "Discard changes",
"workflow.action.discard.modal.content": "Are you sure to discard your changes?",
"workflow.action.run.button": "Run",
"workflow.action.run.modal.title": "Run workflow",
"workflow.action.run.modal.content": "You have unreleased changes. Do you really want to run this workflow based on the latest released version?",
"workflow.action.run.prompt": "Running... Please check the history later",
"workflow.props.name": "Name",
"workflow.props.description": "Description",
@@ -53,13 +63,5 @@
"workflow.detail.baseinfo.form.description.placeholder": "Please enter workflow description",
"workflow.detail.orchestration.tab": "Orchestration",
"workflow.detail.orchestration.draft.alert": "The orchestration is not released yet.",
"workflow.detail.orchestration.action.discard": "Discard changes",
"workflow.detail.orchestration.action.discard.confirm": "Are you sure to discard your changes?",
"workflow.detail.orchestration.action.release": "Release",
"workflow.detail.orchestration.action.release.confirm": "Are you sure to release your changes?",
"workflow.detail.orchestration.action.release.failed.uncompleted": "Please complete the orchestration first",
"workflow.detail.orchestration.action.run": "Run",
"workflow.detail.orchestration.action.run.confirm": "You have unreleased changes. Do you really want to run this workflow based on the latest released version?",
"workflow.detail.orchestration.action.run.prompt": "Running... Please check the history later",
"workflow.detail.runs.tab": "History runs"
}
@@ -1,9 +1,9 @@
{
"workflow_run.action.view": "View detail",
"workflow_run.action.cancel": "Cancel run",
"workflow_run.action.cancel.confirm": "Are you sure to cancel this run?",
"workflow_run.action.delete": "Delete run",
"workflow_run.action.delete.confirm": "Are you sure want to delete this \"{{name}}\" workflow run?<br>This action cannot be undone.",
"workflow_run.action.cancel.button": "Cancel",
"workflow_run.action.cancel.modal.title": "Cancel run",
"workflow_run.action.cancel.modal.content": "Are you sure to cancel this run?",
"workflow_run.action.delete.modal.title": "Delete run",
"workflow_run.action.delete.modal.content": "Are you sure want to delete this \"{{name}}\" workflow run?<br>This action cannot be undone.",
"workflow_run.table.alert": "The workflow run contains the execution results of each node. Deleting it may trigger re-application or re-deployment of certificates due to the inability to find the previous execution result. Please do not delete unless necessary. It is recommended to keep it for at least 180 days.",
+6 -5
View File
@@ -8,11 +8,12 @@
"access.search.placeholder": "按授权名称搜索……",
"access.action.create": "新建授权",
"access.action.edit": "编辑授权",
"access.action.duplicate": "复制授权",
"access.action.delete": "删除授权",
"access.action.delete.confirm": "确定要删除授权「{{name}}」吗?<br>注意此操作不可撤销,请谨慎操作。",
"access.action.create.button": "新建授权",
"access.action.create.modal.title": "新建授权",
"access.action.edit.modal.title": "编辑授权",
"access.action.duplicate.modal.title": "复制授权",
"access.action.delete.modal.title": "删除授权",
"access.action.delete.modal.content": "确定要删除授权「{{name}}」吗?<br>注意此操作不可撤销,请谨慎操作。",
"access.props.name": "名称",
"access.props.provider.usage.dns": "DNS 提供商",
+2 -4
View File
@@ -8,10 +8,8 @@
"certificate.search.placeholder": "按证书名称或序列号搜索……",
"certificate.action.view": "查看证书",
"certificate.action.delete": "删除证书",
"certificate.action.delete.confirm": "确定要删除证书「{{name}}」吗?<br>注意此操作不可撤销,请谨慎操作。",
"certificate.action.download": "下载证书",
"certificate.action.delete.modal.title": "删除证书",
"certificate.action.delete.modal.content": "确定要删除证书「{{name}}」吗?<br>注意此操作不可撤销,请谨慎操作。",
"certificate.props.subject_alt_names": "名称",
"certificate.props.validity": "有效期限",
+5 -1
View File
@@ -2,8 +2,11 @@
"common.button.add": "新增",
"common.button.cancel": "取消",
"common.button.confirm": "确定",
"common.button.create": "新建",
"common.button.copy": "复制",
"common.button.delete": "刪除",
"common.button.download": "下载",
"common.button.duplicate": "复制",
"common.button.edit": "编辑",
"common.button.more": "更多",
"common.button.ok": "确定",
@@ -11,8 +14,9 @@
"common.button.reset": "重置",
"common.button.save": "保存更改",
"common.button.submit": "提交",
"common.button.view": "查看",
"common.text.copied": "已复制",
"common.text.copied": "已复制到剪贴板",
"common.text.import_from_file": "从文件导入 ……",
"common.text.happy_browser": "当前浏览器版本过低,Certimate WebUI 无法正常工作。推荐使用 Google Chrome v119.0 或更高版本的现代浏览器。",
"common.text.nodata": "暂无数据",
+1 -1
View File
@@ -193,5 +193,5 @@
"provider.category.nas": "NAS",
"provider.category.other": "其他",
"provider.default_ca_provider.label": "(默认)不指定,跟随全局设置"
"provider.text.default_ca_provider.label": "(默认)不指定,跟随全局设置"
}
+19 -17
View File
@@ -8,15 +8,25 @@
"workflow.search.placeholder": "按工作流名称搜索……",
"workflow.action.create": "新建工作流",
"workflow.action.edit": "编辑工作流",
"workflow.action.duplicate": "复制工作流",
"workflow.action.duplicate.confirm": "确定要复制此工作流吗?",
"workflow.action.delete": "删除工作流",
"workflow.action.delete.confirm": "确定要删除工作流「{{name}}」吗?<br>注意此操作不可撤销,请谨慎操作。",
"workflow.action.enable": "启用",
"workflow.action.enable.failed.uncompleted": "请先完成流程编排并发布更改",
"workflow.action.disable": "停用",
"workflow.action.create.button": "新建工作流",
"workflow.action.duplicate.modal.title": "复制工作流",
"workflow.action.duplicate.modal.content": "确定要复制工作流「{{name}}」吗?",
"workflow.action.delete.modal.title": "删除工作流",
"workflow.action.delete.modal.content": "确定要删除工作流「{{name}}」吗?<br>注意此操作不可撤销,请谨慎操作。",
"workflow.action.enable.button": "启用",
"workflow.action.enable.errmsg.uncompleted": "请先完成流程编排并发布更改",
"workflow.action.disable.button": "停用",
"workflow.action.release.button": "发布更改",
"workflow.action.release.modal.title": "发布更改",
"workflow.action.release.modal.content": "确定要发布更改吗?",
"workflow.action.release.errmsg.uncompleted": "流程编排未完成,请检查是否有节点未配置",
"workflow.action.discard.button": "撤销更改",
"workflow.action.discard.modal.title": "撤销更改",
"workflow.action.discard.modal.content": "确定要撤销更改并回退到最近一次发布的版本吗?",
"workflow.action.run.button": "执行",
"workflow.action.run.modal.title": "执行工作流",
"workflow.action.run.modal.content": "你有尚未发布的更改。确定要以最近一次发布的版本继续执行吗?",
"workflow.action.run.prompt": "执行中……请稍后查看执行历史",
"workflow.props.name": "名称",
"workflow.props.description": "描述",
@@ -53,13 +63,5 @@
"workflow.detail.baseinfo.form.description.placeholder": "请输入工作流描述",
"workflow.detail.orchestration.tab": "流程编排",
"workflow.detail.orchestration.draft.alert": "当前编排有未发布的更改。",
"workflow.detail.orchestration.action.discard": "撤销更改",
"workflow.detail.orchestration.action.discard.confirm": "确定要撤销更改并回退到最近一次发布的版本吗?",
"workflow.detail.orchestration.action.release": "发布更改",
"workflow.detail.orchestration.action.release.confirm": "确定要发布更改吗?",
"workflow.detail.orchestration.action.release.failed.uncompleted": "流程编排未完成,请检查是否有节点未配置",
"workflow.detail.orchestration.action.run": "执行",
"workflow.detail.orchestration.action.run.confirm": "你有尚未发布的更改。确定要以最近一次发布的版本继续执行吗?",
"workflow.detail.orchestration.action.run.prompt": "执行中……请稍后查看执行历史",
"workflow.detail.runs.tab": "执行历史"
}
@@ -1,6 +1,6 @@
{
"workflow_node.action.configure_node": "配置节点",
"workflow_node.branch.add_node": "添加节点",
"workflow_node.action.add_node": "添加节点",
"workflow_node.action.rename_node": "重命名",
"workflow_node.action.duplicate_node": "复制节点",
"workflow_node.action.remove_node": "删除节点",
@@ -1,11 +1,11 @@
{
"workflow_run.action.view": "查看详情",
"workflow_run.action.cancel": "取消执行",
"workflow_run.action.cancel.confirm": "确定要取消此执行吗?此操作仅中止流程,但不会回滚已执行的节点。",
"workflow_run.action.delete": "删除执行",
"workflow_run.action.delete.confirm": "确定要删除工作流执行记录「{{name}}」吗?<br>此操作仅清除日志历史,但不会影响签发的证书。<br>注意此操作不可撤销,请谨慎操作。",
"workflow_run.action.cancel.button": "取消执行",
"workflow_run.action.cancel.modal.title": "取消执行",
"workflow_run.action.cancel.modal.content": "确定要取消此执行吗?此操作仅中止流程,但不会回滚已执行的节点。",
"workflow_run.action.delete.modal.title": "删除执行",
"workflow_run.action.delete.modal.content": "确定要删除工作流执行记录「{{name}}」吗?<br>此操作仅清除日志历史,但不会影响签发的证书。<br>注意此操作不可撤销,请谨慎操作。",
"workflow_run.table.alert": "注意:执行记录中包含工作流各节点的执行结果,删除后可能导致因找不到前次执行结果而触发重新申请或部署证书。如无必要请勿提前删除,建议保留至少 180 天。",
"workflow_run.table.alert": "执行记录中包含工作流各节点的执行结果,删除后可能导致因找不到前次执行结果而触发重新申请或部署证书。如无必要请勿提前删除,建议保留至少 180 天。",
"workflow_run.props.id": "ID",
"workflow_run.props.status": "状态",
+19 -13
View File
@@ -77,7 +77,7 @@ const AccessList = () => {
width: 120,
render: (_, record) => (
<div className="flex items-center justify-end">
<Tooltip title={t("access.action.edit")}>
<Tooltip title={t("common.button.edit")}>
<Button
color="primary"
icon={<IconEdit size="1.25em" />}
@@ -88,7 +88,7 @@ const AccessList = () => {
}}
/>
</Tooltip>
<Tooltip title={t("access.action.duplicate")}>
<Tooltip title={t("common.button.duplicate")}>
<Button
color="primary"
icon={<IconCopy size="1.25em" />}
@@ -99,7 +99,7 @@ const AccessList = () => {
}}
/>
</Tooltip>
<Tooltip title={t("access.action.delete")}>
<Tooltip title={t("common.button.delete")}>
<Button
color="danger"
icon={<IconTrash size="1.25em" />}
@@ -183,25 +183,25 @@ const AccessList = () => {
};
const [detailRecord, setDetailRecord] = useState<MaybeModelRecord<AccessModel>>();
const [detailScene, setDetailScene] = useState<AccessEditDrawerProps["scene"]>("create");
const [detailAction, setDetailAction] = useState<AccessEditDrawerProps["action"]>("create");
const [detailOpen, setDetailOpen] = useState<boolean>(false);
const handleRecordDetailClick = (access: AccessModel) => {
setDetailRecord(access);
setDetailScene("edit");
setDetailAction("edit");
setDetailOpen(true);
};
const handleRecordDuplicateClick = (access: AccessModel) => {
setDetailRecord({ ...access, id: undefined, name: `${access.name}-copy` });
setDetailScene("create");
setDetailAction("create");
setDetailOpen(true);
};
const handleRecordDeleteClick = async (access: AccessModel) => {
modal.confirm({
title: <span className="text-error">{t("access.action.delete")}</span>,
content: <span dangerouslySetInnerHTML={{ __html: t("access.action.delete.confirm", { name: access.name }) }} />,
title: <span className="text-error">{t("access.action.delete.modal.title")}</span>,
content: <span dangerouslySetInnerHTML={{ __html: t("access.action.delete.modal.content", { name: access.name }) }} />,
icon: (
<span className="anticon" role="img">
<IconTrash className="text-error" size="1em" />
@@ -246,11 +246,11 @@ const AccessList = () => {
</div>
<div>
<AccessEditDrawer
scene="create"
action="create"
usage={filters["usage"] as AccessUsageProp}
trigger={
<Button className="text-sm" icon={<IconPlus size="1.25em" />} size="large" type="primary">
{t("access.action.create")}
{t("access.action.create.button")}
</Button>
}
/>
@@ -292,11 +292,11 @@ const AccessList = () => {
icon={<IconFingerprint size={24} />}
extra={
<AccessEditDrawer
scene="create"
action="create"
usage={filters["usage"] as AccessUsageProp}
trigger={
<Button icon={<IconCirclePlus size="1.25em" />} type="primary">
{t("access.action.create")}
{t("access.action.create.button")}
</Button>
}
/>
@@ -328,7 +328,13 @@ const AccessList = () => {
})}
/>
<AccessEditDrawer data={detailRecord} open={detailOpen} scene={detailScene} usage={filters["usage"] as AccessUsageProp} onOpenChange={setDetailOpen} />
<AccessEditDrawer
data={detailRecord}
open={detailOpen}
action={detailAction}
usage={filters["usage"] as AccessUsageProp}
onOpenChange={setDetailOpen}
/>
</div>
</div>
);
@@ -139,7 +139,7 @@ const CertificateList = () => {
width: 120,
render: (_, record) => (
<div className="flex items-center justify-end">
<Tooltip title={t("certificate.action.view")}>
<Tooltip title={t("common.button.view")}>
<Button
color="primary"
icon={<IconBrowserShare size="1.25em" />}
@@ -150,7 +150,7 @@ const CertificateList = () => {
}}
/>
</Tooltip>
<Tooltip title={t("certificate.action.delete")}>
<Tooltip title={t("common.button.delete")}>
<Button
color="danger"
icon={<IconTrash size="1.25em" />}
@@ -227,8 +227,8 @@ const CertificateList = () => {
const handleRecordDeleteClick = (certificate: CertificateModel) => {
modal.confirm({
title: <span className="text-error">{t("certificate.action.delete")}</span>,
content: <span dangerouslySetInnerHTML={{ __html: t("certificate.action.delete.confirm", { name: certificate.subjectAltNames }) }} />,
title: <span className="text-error">{t("certificate.action.delete.modal.title")}</span>,
content: <span dangerouslySetInnerHTML={{ __html: t("certificate.action.delete.modal.content", { name: certificate.subjectAltNames }) }} />,
icon: (
<span className="anticon" role="img">
<IconTrash className="text-error" size="1em" />
+16 -20
View File
@@ -76,7 +76,7 @@ const WorkflowDetail = () => {
const handleEnableChange = async () => {
if (!workflow.enabled && (!workflow.content || !isAllNodesValidated(workflow.content))) {
message.warning(t("workflow.action.enable.failed.uncompleted"));
message.warning(t("workflow.action.enable.errmsg.uncompleted"));
return;
}
@@ -90,8 +90,8 @@ const WorkflowDetail = () => {
const handleDeleteClick = () => {
modal.confirm({
title: <span className="text-error">{t("workflow.action.delete")}</span>,
content: <span dangerouslySetInnerHTML={{ __html: t("workflow.action.delete.confirm", { name: workflow.name }) }} />,
title: <span className="text-error">{t("workflow.action.delete.modal.title")}</span>,
content: <span dangerouslySetInnerHTML={{ __html: t("workflow.action.delete.modal.content", { name: workflow.name }) }} />,
icon: (
<span className="anticon" role="img">
<IconTrash className="text-error" size="1em" />
@@ -115,8 +115,8 @@ const WorkflowDetail = () => {
const handleDiscardClick = () => {
modal.confirm({
title: t("workflow.detail.orchestration.action.discard"),
content: t("workflow.detail.orchestration.action.discard.confirm"),
title: t("workflow.action.discard.modal.title"),
content: t("workflow.action.discard.modal.content"),
onOk: async () => {
try {
await workflowState.discard();
@@ -132,13 +132,13 @@ const WorkflowDetail = () => {
const handleReleaseClick = () => {
if (!isAllNodesValidated(workflow.draft!)) {
message.warning(t("workflow.detail.orchestration.action.release.failed.uncompleted"));
message.warning(t("workflow.action.release.errmsg.uncompleted"));
return;
}
modal.confirm({
title: t("workflow.detail.orchestration.action.release"),
content: t("workflow.detail.orchestration.action.release.confirm"),
title: t("workflow.action.release.modal.title"),
content: t("workflow.action.release.modal.content"),
onOk: async () => {
try {
await workflowState.release();
@@ -156,8 +156,8 @@ const WorkflowDetail = () => {
const { promise, resolve, reject } = Promise.withResolvers();
if (workflow.hasDraft) {
modal.confirm({
title: t("workflow.detail.orchestration.action.run"),
content: t("workflow.detail.orchestration.action.run.confirm"),
title: t("workflow.action.run.modal.title"),
content: t("workflow.action.run.modal.content"),
onOk: () => resolve(void 0),
onCancel: () => reject(),
});
@@ -181,7 +181,7 @@ const WorkflowDetail = () => {
await startWorkflowRun(workflowId!);
message.info(t("workflow.detail.orchestration.action.run.prompt"));
message.info(t("workflow.action.run.prompt"));
} catch (err) {
setIsPendingOrRunning(false);
unsubscribeFn?.();
@@ -206,18 +206,16 @@ const WorkflowDetail = () => {
{initialized
? [
<WorkflowBaseInfoModal key="edit" trigger={<Button>{t("common.button.edit")}</Button>} />,
<Button key="enable" onClick={handleEnableChange}>
{workflow.enabled ? t("workflow.action.disable") : t("workflow.action.enable")}
{workflow.enabled ? t("workflow.action.disable.button") : t("workflow.action.enable.button")}
</Button>,
<Dropdown
key="more"
menu={{
items: [
{
key: "delete",
label: t("workflow.action.delete"),
label: t("common.button.delete"),
danger: true,
icon: <IconTrash size="1.25em" />,
onClick: () => {
@@ -291,21 +289,19 @@ const WorkflowDetail = () => {
<div className="flex justify-end">
<Space>
<Button disabled={!allowRun} icon={<IconPlayerPlay size="1.25em" />} loading={isPendingOrRunning} type="primary" onClick={handleRunClick}>
{t("workflow.detail.orchestration.action.run")}
{t("workflow.action.run.button")}
</Button>
<Space.Compact>
<Button color="primary" disabled={!allowRelease} variant="outlined" onClick={handleReleaseClick}>
{t("workflow.detail.orchestration.action.release")}
{t("workflow.action.release.button")}
</Button>
<Dropdown
menu={{
items: [
{
key: "discard",
disabled: !allowDiscard,
label: t("workflow.detail.orchestration.action.discard"),
label: t("workflow.action.discard.button"),
icon: <IconArrowBackUp size="1.25em" />,
onClick: handleDiscardClick,
},
+9 -11
View File
@@ -118,7 +118,7 @@ const WorkflowList = () => {
width: 120,
render: (_, record) => (
<div className="flex items-center justify-end">
<Tooltip title={t("workflow.action.edit")}>
<Tooltip title={t("common.button.edit")}>
<Button
color="primary"
icon={<IconEdit size="1.25em" />}
@@ -129,8 +129,7 @@ const WorkflowList = () => {
}}
/>
</Tooltip>
<Tooltip title={t("workflow.action.duplicate")}>
<Tooltip title={t("common.button.duplicate")}>
<Button
color="primary"
icon={<IconCopy size="1.25em" />}
@@ -141,8 +140,7 @@ const WorkflowList = () => {
}}
/>
</Tooltip>
<Tooltip title={t("workflow.action.delete")}>
<Tooltip title={t("common.button.delete")}>
<Button
color="danger"
danger
@@ -215,7 +213,7 @@ const WorkflowList = () => {
const handleRecordActiveChange = async (workflow: WorkflowModel) => {
try {
if (!workflow.enabled && (!workflow.content || !isAllNodesValidated(workflow.content))) {
message.warning(t("workflow.action.enable.failed.uncompleted"));
message.warning(t("workflow.action.enable.errmsg.uncompleted"));
return;
}
@@ -241,8 +239,8 @@ const WorkflowList = () => {
const handleRecordDuplicateClick = (workflow: WorkflowModel) => {
modal.confirm({
title: t("workflow.action.duplicate"),
content: t("workflow.action.duplicate.confirm"),
title: t("workflow.action.duplicate.modal.title"),
content: t("workflow.action.duplicate.modal.content", { name: workflow.name }),
onOk: async () => {
try {
const workflowCopy = {
@@ -271,8 +269,8 @@ const WorkflowList = () => {
const handleRecordDeleteClick = (workflow: WorkflowModel) => {
modal.confirm({
title: <span className="text-error">{t("workflow.action.delete")}</span>,
content: <span dangerouslySetInnerHTML={{ __html: t("workflow.action.delete.confirm", { name: workflow.name }) }} />,
title: <span className="text-error">{t("workflow.action.delete.modal.title")}</span>,
content: <span dangerouslySetInnerHTML={{ __html: t("workflow.action.delete.modal.content", { name: workflow.name }) }} />,
icon: (
<span className="anticon" role="img">
<IconTrash className="text-error" size="1em" />
@@ -335,7 +333,7 @@ const WorkflowList = () => {
</div>
<div>
<Button className="text-sm" icon={<IconPlus size="1.25em" />} size="large" type="primary" onClick={handleCreateClick}>
{t("workflow.action.create")}
{t("workflow.action.create.button")}
</Button>
</div>
</div>