ESLint 升级到 recommended-type-checked + stylistic-type-checked, 引入 perfectionist 导入排序和 import 插件导入验证。 Prettier 显式声明全部格式化参数,消除跨环境差异。 TypeScript 启用 noUnusedLocals 和 noPropertyAccessFromIndexSignature。 完善 ignore 列表,排除 .agents/、bun.lock、data/ 等。 引入 husky + lint-staged(pre-commit)+ commitlint(commit-msg)。 更新 DEVELOPMENT.md 代码质量章节。 修复所有新增规则检测到的类型和风格违规。
93 lines
2.8 KiB
TypeScript
93 lines
2.8 KiB
TypeScript
import type { PrimaryTableCellParams, PrimaryTableCol } from "tdesign-react";
|
|
|
|
import { Progress, Tag } from "tdesign-react";
|
|
|
|
import type { TargetStatus } from "../../shared/api";
|
|
|
|
import { StatusBar } from "../components/StatusBar";
|
|
import { StatusDot } from "../components/StatusDot";
|
|
import { getAvailabilityProgressColor } from "./color-threshold";
|
|
import { statusFilter, typeFilter } from "./target-table-filters";
|
|
import { availabilitySorter, latencySorter, nameSorter } from "./target-table-sorters";
|
|
import { getTargetTypeDisplay } from "./target-type-display";
|
|
|
|
export const TARGET_TABLE_COLUMNS: Array<PrimaryTableCol<TargetStatus>> = [
|
|
{
|
|
align: "center",
|
|
cell: ({ row }: PrimaryTableCellParams<TargetStatus>) => <StatusDot up={!!row.latestCheck?.matched} />,
|
|
colKey: "latestCheck.matched",
|
|
filter: statusFilter,
|
|
fixed: "left",
|
|
title: "#",
|
|
width: 60,
|
|
},
|
|
{
|
|
colKey: "name",
|
|
ellipsis: true,
|
|
sorter: nameSorter,
|
|
sortType: "all",
|
|
title: "名称",
|
|
},
|
|
{
|
|
cell: ({ row }: PrimaryTableCellParams<TargetStatus>) => (
|
|
<Tag size="small" theme="primary" variant="light-outline">
|
|
{getTargetTypeDisplay(row.type)}
|
|
</Tag>
|
|
),
|
|
colKey: "type",
|
|
filter: typeFilter,
|
|
title: "类型",
|
|
width: 80,
|
|
},
|
|
{
|
|
cell: ({ row }: PrimaryTableCellParams<TargetStatus>) => {
|
|
const availability = row.stats?.availability;
|
|
if (availability === undefined || availability === null) return "-";
|
|
const color = getAvailabilityProgressColor(availability);
|
|
return (
|
|
<Progress
|
|
color={color}
|
|
label={`${availability.toFixed(1)}%`}
|
|
percentage={availability}
|
|
size="small"
|
|
theme="line"
|
|
/>
|
|
);
|
|
},
|
|
colKey: "stats.availability",
|
|
sorter: availabilitySorter,
|
|
sortType: "all",
|
|
title: "可用率",
|
|
width: 160,
|
|
},
|
|
{
|
|
cell: ({ row }: PrimaryTableCellParams<TargetStatus>) => <StatusBar samples={row.recentSamples} />,
|
|
colKey: "recentSamples",
|
|
title: "最近状态",
|
|
width: 220,
|
|
},
|
|
{
|
|
align: "right",
|
|
cell: ({ row }: PrimaryTableCellParams<TargetStatus>) => {
|
|
const ms = row.latestCheck?.durationMs;
|
|
if (ms === null || ms === undefined) return <span className="text-disabled">-</span>;
|
|
const colorClass = ms <= 100 ? "latency-ok" : ms <= 500 ? "latency-warn" : "latency-error";
|
|
return <span className={`${colorClass} tabular-nums`}>{Math.round(ms)}ms</span>;
|
|
},
|
|
colKey: "latestCheck.durationMs",
|
|
sorter: latencySorter,
|
|
sortType: "all",
|
|
title: "延迟",
|
|
width: 80,
|
|
},
|
|
{
|
|
align: "center",
|
|
colKey: "interval",
|
|
title: "间隔",
|
|
width: 72,
|
|
},
|
|
];
|
|
|
|
export { statusFilter, typeFilter } from "./target-table-filters";
|
|
export { availabilitySorter, latencySorter, nameSorter, statusSorter } from "./target-table-sorters";
|