统一状态流转为前端状态机
This commit is contained in:
@@ -0,0 +1,19 @@
|
||||
import type { StateMachine } from "./types";
|
||||
|
||||
export const aeMachine: StateMachine = {
|
||||
states: {
|
||||
NEW: { value: "NEW", label: "新增", color: "info" },
|
||||
FOLLOW_UP: { value: "FOLLOW_UP", label: "随访中", color: "warning" },
|
||||
CLOSED: { value: "CLOSED", label: "已关闭", color: "success", isTerminal: true },
|
||||
},
|
||||
actions: {
|
||||
close: {
|
||||
key: "close",
|
||||
label: "关闭",
|
||||
from: ["NEW", "FOLLOW_UP"],
|
||||
to: "CLOSED",
|
||||
confirm: true,
|
||||
confirmText: "确定关闭该 AE?该操作不可撤销。",
|
||||
},
|
||||
},
|
||||
};
|
||||
@@ -0,0 +1,43 @@
|
||||
import type { StateMachine } from "./types";
|
||||
|
||||
export const financeMachine: StateMachine = {
|
||||
states: {
|
||||
DRAFT: { value: "DRAFT", label: "草稿", color: "info" },
|
||||
SUBMITTED: { value: "SUBMITTED", label: "已提交", color: "warning" },
|
||||
APPROVED: { value: "APPROVED", label: "已审批", color: "success" },
|
||||
REJECTED: { value: "REJECTED", label: "已驳回", color: "danger", isTerminal: true },
|
||||
PAID: { value: "PAID", label: "已支付", color: "success", isTerminal: true },
|
||||
},
|
||||
actions: {
|
||||
submit: {
|
||||
key: "submit",
|
||||
label: "提交",
|
||||
from: ["DRAFT"],
|
||||
to: "SUBMITTED",
|
||||
},
|
||||
approve: {
|
||||
key: "approve",
|
||||
label: "审批通过",
|
||||
from: ["SUBMITTED"],
|
||||
to: "APPROVED",
|
||||
},
|
||||
reject: {
|
||||
key: "reject",
|
||||
label: "驳回",
|
||||
from: ["SUBMITTED"],
|
||||
to: "REJECTED",
|
||||
confirm: true,
|
||||
confirmText: "确认驳回该费用吗?",
|
||||
danger: true,
|
||||
},
|
||||
pay: {
|
||||
key: "pay",
|
||||
label: "确认支付",
|
||||
from: ["APPROVED"],
|
||||
to: "PAID",
|
||||
confirm: true,
|
||||
confirmText: "确认支付该费用吗?",
|
||||
danger: true,
|
||||
},
|
||||
},
|
||||
};
|
||||
@@ -0,0 +1,8 @@
|
||||
import type { StateMachine } from "./types";
|
||||
|
||||
export const impMachine: StateMachine = {
|
||||
states: {
|
||||
CREATED: { value: "CREATED", label: "已创建", color: "info" },
|
||||
},
|
||||
actions: {},
|
||||
};
|
||||
@@ -0,0 +1,30 @@
|
||||
import type { StateMachine } from "./types";
|
||||
|
||||
export const getStateLabel = (machine: StateMachine, stateValue?: string | null) => {
|
||||
if (!stateValue) return "";
|
||||
return machine.states[stateValue]?.label || stateValue;
|
||||
};
|
||||
|
||||
export const getStateColor = (machine: StateMachine, stateValue?: string | null) => {
|
||||
if (!stateValue) return undefined;
|
||||
return machine.states[stateValue]?.color;
|
||||
};
|
||||
|
||||
export const getAvailableActions = (machine: StateMachine, currentState?: string | null) => {
|
||||
if (!currentState) return [];
|
||||
return Object.values(machine.actions).filter((a) => a.from.includes(currentState));
|
||||
};
|
||||
|
||||
export const canDoAction = (machine: StateMachine, actionKey: string, currentState?: string | null) => {
|
||||
if (!currentState) return false;
|
||||
const action = machine.actions[actionKey];
|
||||
if (!action) return false;
|
||||
return action.from.includes(currentState);
|
||||
};
|
||||
|
||||
export * from "./types";
|
||||
export * from "./task.machine";
|
||||
export * from "./subject.machine";
|
||||
export * from "./ae.machine";
|
||||
export * from "./finance.machine";
|
||||
export * from "./imp.machine";
|
||||
@@ -0,0 +1,33 @@
|
||||
import type { StateMachine } from "./types";
|
||||
|
||||
export const subjectMachine: StateMachine = {
|
||||
states: {
|
||||
SCREENING: { value: "SCREENING", label: "筛选中", color: "info" },
|
||||
ENROLLED: { value: "ENROLLED", label: "已入组", color: "success" },
|
||||
COMPLETED: { value: "COMPLETED", label: "已完成", color: "success", isTerminal: true },
|
||||
DROPPED: { value: "DROPPED", label: "已脱落", color: "danger", isTerminal: true },
|
||||
},
|
||||
actions: {
|
||||
enroll: {
|
||||
key: "enroll",
|
||||
label: "标记入组",
|
||||
from: ["SCREENING"],
|
||||
to: "ENROLLED",
|
||||
},
|
||||
complete: {
|
||||
key: "complete",
|
||||
label: "标记完成",
|
||||
from: ["ENROLLED"],
|
||||
to: "COMPLETED",
|
||||
},
|
||||
drop: {
|
||||
key: "drop",
|
||||
label: "标记脱落",
|
||||
from: ["SCREENING", "ENROLLED"],
|
||||
to: "DROPPED",
|
||||
danger: true,
|
||||
confirm: true,
|
||||
confirmText: "确定将该受试者标记为脱落?",
|
||||
},
|
||||
},
|
||||
};
|
||||
@@ -0,0 +1,16 @@
|
||||
import type { StateMachine } from "./types";
|
||||
|
||||
export const taskMachine: StateMachine = {
|
||||
states: {
|
||||
TODO: { value: "TODO", label: "待处理", color: "info" },
|
||||
DONE: { value: "DONE", label: "已完成", color: "success", isTerminal: true },
|
||||
},
|
||||
actions: {
|
||||
complete: {
|
||||
key: "complete",
|
||||
label: "完成",
|
||||
from: ["TODO"],
|
||||
to: "DONE",
|
||||
},
|
||||
},
|
||||
};
|
||||
@@ -0,0 +1,21 @@
|
||||
export interface StateConfig {
|
||||
value: string;
|
||||
label: string;
|
||||
color?: string;
|
||||
isTerminal?: boolean;
|
||||
}
|
||||
|
||||
export interface ActionConfig {
|
||||
key: string;
|
||||
label: string;
|
||||
from: string[];
|
||||
to: string;
|
||||
confirm?: boolean;
|
||||
confirmText?: string;
|
||||
danger?: boolean;
|
||||
}
|
||||
|
||||
export interface StateMachine {
|
||||
states: Record<string, StateConfig>;
|
||||
actions: Record<string, ActionConfig>;
|
||||
}
|
||||
Reference in New Issue
Block a user