mirror of
https://github.com/hansjone/netx.git
synced 2026-10-11 05:43:20 +08:00
Show full copyable batch ids in biz-state/cutover UI and document batch list tools.
Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
parent
04850b942c
commit
83cf086d8c
6 changed files with 123 additions and 22 deletions
|
|
@ -37,6 +37,7 @@ import {
|
|||
} from "../../services/api";
|
||||
// bizStateListTasks not needed for create — NEs + auto HF
|
||||
import type { CliTargetItem } from "../../types";
|
||||
import { writeClipboardText } from "../../utils/clipboard";
|
||||
import { pageCount } from "../../utils/display";
|
||||
import { formatSystemTime, localDatetimeInputToUtcIso, utcIsoToLocalDatetimeInput } from "../../utils/time";
|
||||
import { jobChipColor, NmStatusChip, sourceChipColor } from "./nmChips";
|
||||
|
|
@ -1426,14 +1427,26 @@ export function BizMigrationPage() {
|
|||
const batchOptions = (items: { id: string; started_at?: string | null }[]) => (
|
||||
<>
|
||||
<option value="">—</option>
|
||||
{items.map((x) => (
|
||||
<option key={x.id} value={x.id}>
|
||||
{fmtTime(x.started_at) !== "—" ? fmtTime(x.started_at) : x.id.slice(0, 12)}
|
||||
</option>
|
||||
))}
|
||||
{items.map((x) => {
|
||||
const when = fmtTime(x.started_at);
|
||||
const label = when !== "—" ? `${when} · ${x.id}` : x.id;
|
||||
return (
|
||||
<option key={x.id} value={x.id} title={x.id}>
|
||||
{label}
|
||||
</option>
|
||||
);
|
||||
})}
|
||||
</>
|
||||
);
|
||||
|
||||
const copyBatchId = (id: string) => {
|
||||
void (async () => {
|
||||
const ok = await writeClipboardText(id);
|
||||
if (ok) showOk(t("common.copied"));
|
||||
else showError(t("common.opFailed"));
|
||||
})();
|
||||
};
|
||||
|
||||
return (
|
||||
<section className="panel nm-page-panel">
|
||||
<div className="panel__toolbar">
|
||||
|
|
@ -2340,8 +2353,8 @@ export function BizMigrationPage() {
|
|||
aria-label={t("bizMigration.batches")}
|
||||
>
|
||||
{batches.map((b) => (
|
||||
<option key={b.id} value={b.id}>
|
||||
{b.batch_label} ({statusLabel(b.status)})
|
||||
<option key={b.id} value={b.id} title={b.id}>
|
||||
{b.batch_label} ({statusLabel(b.status)}) · {b.id}
|
||||
</option>
|
||||
))}
|
||||
</FieldSelect>
|
||||
|
|
@ -2397,6 +2410,15 @@ export function BizMigrationPage() {
|
|||
) : null}
|
||||
</div>
|
||||
</div>
|
||||
{batch ? (
|
||||
<div className="bs-id-row" title={batch.id}>
|
||||
<span className="bs-id-row__label">{t("bizMigration.batchId")}</span>
|
||||
<code className="bs-id-row__value">{batch.id}</code>
|
||||
<Button size="sm" variant="ghost" onPress={() => copyBatchId(batch.id)}>
|
||||
{t("bizMigration.copyBatchId")}
|
||||
</Button>
|
||||
</div>
|
||||
) : null}
|
||||
|
||||
<div className="ct-editor__main bm-batches__main">
|
||||
<aside className="ct-editor__nav" aria-label={t("bizMigration.pickExpectPorts")}>
|
||||
|
|
@ -2530,11 +2552,20 @@ export function BizMigrationPage() {
|
|||
aria-label={t("bizMigration.batches")}
|
||||
>
|
||||
{batches.map((b) => (
|
||||
<option key={b.id} value={b.id}>
|
||||
{b.batch_label} ({statusLabel(b.status)})
|
||||
<option key={b.id} value={b.id} title={b.id}>
|
||||
{b.batch_label} ({statusLabel(b.status)}) · {b.id}
|
||||
</option>
|
||||
))}
|
||||
</FieldSelect>
|
||||
{batchId ? (
|
||||
<div className="bs-id-row bs-id-row--inline" title={batchId}>
|
||||
<span className="bs-id-row__label">{t("bizMigration.batchId")}</span>
|
||||
<code className="bs-id-row__value">{batchId}</code>
|
||||
<Button size="sm" variant="ghost" onPress={() => copyBatchId(batchId)}>
|
||||
{t("bizMigration.copyBatchId")}
|
||||
</Button>
|
||||
</div>
|
||||
) : null}
|
||||
<FieldSelect
|
||||
value={pinOldBatchId}
|
||||
onChange={(e) => setPinOldBatchId(e.target.value)}
|
||||
|
|
|
|||
|
|
@ -30,6 +30,7 @@ import {
|
|||
} from "../../services/api";
|
||||
import type { CliTargetItem } from "../../types";
|
||||
import { pageCount } from "../../utils/display";
|
||||
import { writeClipboardText } from "../../utils/clipboard";
|
||||
import { formatSystemTime } from "../../utils/time";
|
||||
import { jobChipColor, NmStatusChip, sourceChipColor } from "./nmChips";
|
||||
|
||||
|
|
@ -1502,9 +1503,7 @@ export function BizStatePage() {
|
|||
className="app-heroui-modal--xl bs-workbook-modal"
|
||||
>
|
||||
<Modal.Header>
|
||||
<Modal.Heading>
|
||||
{t("bizState.batchWorkbook")} · {batchDetail?.id?.slice(0, 8)}…
|
||||
</Modal.Heading>
|
||||
<Modal.Heading>{t("bizState.batchWorkbook")}</Modal.Heading>
|
||||
<Modal.CloseTrigger />
|
||||
</Modal.Header>
|
||||
<Modal.Body className="flex flex-col gap-2 bs-workbook-body">
|
||||
|
|
@ -1517,6 +1516,24 @@ export function BizStatePage() {
|
|||
{batchDetail.command_count} cmd · {batchDetail.row_count} rows ·{" "}
|
||||
{fmtTime(batchDetail.started_at)}
|
||||
</span>
|
||||
<div className="bs-id-row" title={String(batchDetail.id || "")}>
|
||||
<span className="bs-id-row__label">{t("bizState.batchId")}</span>
|
||||
<code className="bs-id-row__value">{String(batchDetail.id || "")}</code>
|
||||
<Button
|
||||
size="sm"
|
||||
variant="ghost"
|
||||
isDisabled={!batchDetail.id}
|
||||
onPress={() => {
|
||||
void (async () => {
|
||||
const ok = await writeClipboardText(String(batchDetail.id || ""));
|
||||
if (ok) showOk(t("common.copied"));
|
||||
else showError(t("common.opFailed"));
|
||||
})();
|
||||
}}
|
||||
>
|
||||
{t("bizState.copyBatchId")}
|
||||
</Button>
|
||||
</div>
|
||||
</div>
|
||||
) : null}
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue