Files
yuanshuai c91a64fddb
CI / Python 3.12 (push) Waiting to run
CI / Python 3.9 (push) Waiting to run
chore(repo): initialize team collaboration repository
2026-07-27 20:40:12 +08:00

4.5 KiB
Raw Permalink Blame History

领域模型:7 个核心对象 → 14 张表

方案 §5.3 列了 7 个核心领域对象。当前 SQLAlchemy 元数据包含 14 张表。 额外表用于事件溯源、恢复动作、资源锁、失败实例与审计;它们不是新的顶层产品概念, 而是核心对象的行为记录和读模型。

对象 → 表

方案对象 补充说明
DUT duts 序列号是防错盘的第一信号
Test Host test_hosts + oob_controllers 带外控制器独立成表:它必须能在主机死后独活
Firmware Artifact firmware_artifacts 哈希 + 签名 + 适用型号,缺一不可审计
Workflow workflows 存 spec 原文 + spec_hash,改一个字就是新版本
Run runs + run_steps + run_events + recovery_actions 见下
Failure Signature failure_signatures + run_failures 签名是聚类锚点,失败实例挂在它下面
Evidence Bundle evidence_bundles manifest 记录完整率,缺字段要能查出来
—(新增) resource_locks DUT/主机独占,防并发踩踏
—(新增) audit_log 谁在什么时候用哪个模板做了什么

Run 为什么拆成四张表

runs 只存当前投影(状态、进度、结论)。真相在 run_events

run_events  (append-only, 唯一真相)
    │  projection
    ▼
runs / run_steps / recovery_actions  (可重建的读模型)

任何时刻都能靠重放 run_events 重建 runs 的状态——这是"事件溯源"落地的含义, 也是统一时间线、审计、自动复现三个功能的共同地基。

代价:写路径必须走 events/recorder.py。仓储层故意没有 update_run_state() 这种 API。想改状态?记一条事件,投影自己会跟上。

关键字段的设计理由

duts.allow_destructive + duts.serial

破坏性动作(Format / Sanitize / 刷写)的三重校验:序列号匹配、 allow_destructive=True、设备路径不是系统盘。三个信号缺一个就拒绝执行。 误盘一次 = PoC 判定失败(方案 §9.3),所以这个字段不给 API 直接改, 只能走带审批记录的资产管理接口。

runs.env_fingerprintJSON,不可变快照)

任务开始时冻结:主板 / BIOS / OS / 内核 / 驱动 / Agent 版本 / 工具版本 / DUT 固件。 A/B 对比的前提是环境相同——固件之外任何一项变了,对比结论就不成立。 签名哈希也吃这个指纹,所以"换了台机器复现不出来"能被自动识别为不同签名。

runs.unattended_completion + runs.human_touches

这两个字段是销售武器,不是技术指标。UCR(无人值守完成率)和人工触碰次数 是客户签字确认 ROI 的凭据(方案 §9.3、报告 Phase 2 现场指标)。 从第一行代码就记,不要等到要卖了才补。

run_events.seq(每个 run 内单调递增)

时间戳会因为主机断电、时钟漂移、带外控制器与主机时钟不同步而乱序。 seq 由控制平面单点分配,保证时间线可重放。带外事件与 Agent 事件 进同一条序列——双通道观测的交叉校验靠它。

failure_signatures.hash8 要素)

hash(workflow_step, normalized_error_codes, log_templates, host_state,
     dut_enumeration_state, data_integrity_state, recovery_outcome,
     environment_fingerprint)

只用错误码会把"掉盘"和"脚本超时"归成一类,聚类就废了。 log_templates 是日志模板化后的结果(数字/路径/时间被替换为占位符), 不是原始日志——否则每条日志都是新签名。

run_failures.failure_class

DUT_DEFECT / INFRA_FAILURE / SCRIPT_FAILURE / DATA_INTEGRITY / UNKNOWN

INFRA_FAILURE 必须与 DUT_DEFECT 分开统计(方案 §4.3)。 把网络断了、磁盘满了算成 SSD 缺陷,客户第一周就不信任这个系统了。 基础设施误报率 <5% 是 MVP 硬指标。

状态字段一览

字段 取值
runs state QUEUED / PREFLIGHT / RUNNING / RECOVERING / PAUSED / FROZEN / COMPLETED / ABORTED / REJECTED
runs verdict PASS / FAIL / INCONCLUSIVE / null
run_steps state PENDING / DISPATCHED / RUNNING / SUCCEEDED / FAILED / TIMED_OUT / SKIPPED / CANCELLED
test_hosts status ONLINE / DEGRADED / OFFLINE / UNKNOWN
duts status IDLE / IN_USE / QUARANTINED / MISSING
recovery_actions outcome RECOVERED / FAILED / ESCALATED / FROZEN

详见 state-machine.md