工单模型设计:字段定义、状态机、流程模板配置
工单系统能不能玩得转,模型设计是根基。说白了,字段、状态、流程这三样东西没定义好,后面做联动、做自动化全是坑。我这些年见过不少团队,上来就写业务代码,结果后来字段不够用、状态满天飞、流程改不动——全要返工。所以这一章,咱们把模型设计掰开揉碎讲讲。
1. 字段定义——工单的骨架
字段就是工单的数据载体。你想想看,一个工单从创建到关闭,需要记录哪些信息?
- 核心字段:工单ID、标题、描述、创建人、创建时间、当前状态、优先级。
- 业务字段:根据场景加,比如故障工单要有“故障分类”、“影响范围”;变更工单要有“变更内容”、“回滚方案”。
- 扩展字段:用自定义属性或JSON字段兜底,给未来不确定性留口子。
我个人习惯在设计表结构时,把不变的和变的分开。举个例子:
CREATE TABLE ticket (
id BIGINT PRIMARY KEY,
title VARCHAR(200),
description TEXT,
creator VARCHAR(50),
created_at DATETIME,
status VARCHAR(30), -- 当前状态
priority TINYINT,
category VARCHAR(50), -- 业务分类
ext_attr JSON, -- 扩展属性兜底
version INT DEFAULT 0 -- 乐观锁
);
注意那个 ext_attr 字段。我在项目中遇到过业务方临时要加一个“机房楼层”字段,开发来不及上线新的列,直接往JSON里塞,半小时就搞定了。这就是扩展字段的价值。但也别滥用,核心字段还是要用正式列,否则查询索引和约束没法做。
2. 状态机——工单的生命线
状态机定义了工单从生到死的路径。很多新手喜欢用一堆 if-else 判断流转,结果状态组合成指数级增长,维护成本爆炸。正确的做法是:定义有限状态机(FSM),明确每个状态的可达转换和触发动作。
状态机三个核心要素:
- 状态(State):工单在某个时刻的稳定阶段,例如待处理、处理中、待验收、已关闭。
- 事件(Event):触发状态转换的外部动作,例如提交、分配、复核、驳回。
- 动作(Action):状态转换时附带的业务操作,例如发送通知、记录日志、更新关联资产。
我通常会用一张表把状态机规则存起来,而不是硬编码在代码里。下面是一个典型的状态机表格:
| 当前状态 | 事件 | 目标状态 | 动作 |
|---|---|---|---|
| 待处理 | 受理 | 处理中 | 通知处理人,记录受理时间 |
| 处理中 | 完成 | 待验收 | 通知发起人,记录完成时间 |
| 待验收 | 通过 | 已关闭 | 记录验收人,关闭子任务 |
| 待验收 | 驳回 | 处理中 | 退回处理人,附加驳回原因 |
| 处理中 | 转派 | 待处理 | 清空当前处理人,重新分配 |
你想想看,如果这些逻辑写死在代码里,每增加一个状态就要改核心逻辑,风险极高。用配置表驱动状态机,改配置就能上线,这才是运维思维。
3. 流程模板配置——让工单跑起来
有了字段和状态机,还需要流程模板把“谁来做、做什么、按什么顺序做”串起来。流程模板本质上是状态机的超集,它给每个状态分配审批人、限时、抄送等规则。
一个完整的流程模板包括:
- 节点定义:每个状态对应一个节点,包含节点名称、处理角色、超时时长。
- 转换规则:状态之间的转移条件,支持条件分支(比如金额大于10000需要二级审批)。
- 扩展动作:节点进入/离开时执行的hook,例如调用外部API、发送企微消息。
我习惯用YAML来描述流程模板,可读性高,也方便版本管理。给你看一个简化的例子:
# 故障工单流程模板
version: "1.0"
states:
- name: pending
label: 待处理
assigned_role: L1_engineer
timeout_seconds: 7200
on_enter:
- notify_channel: wecom
template: "新工单 {{ticket_title}} 已分配"
on_leave:
- log_action: accepted
- name: processing
label: 处理中
assigned_role: assignee
allowed_events:
- event: complete
target: review
- event: reassign
target: pending
condition: "user.role == 'manager'"
- name: review
label: 待验收
assigned_role: reporter
timeout_seconds: 3600
最后提醒一点:字段、状态机、流程模板三者必须保持数据一致性。字段里的状态字段值,必须对应状态机里定义的状态;流程模板引用的状态,也必须在状态机注册过。我建议用一个统一的状态注册表来管理,生成代码时自动校验,避免出现“运行时报错说状态找不到”的尴尬。
好了,模型设计的三个核心要素就聊到这里。字段定义了工单“长什么样”,状态机定义了“怎么变”,流程模板定义了“谁来变”。三者配合好,后面的联动机制才能稳稳落地。