feat: 结构化 observation 替代 statusDetail,API 层动态构造 detail
- CheckResult: statusDetail -> observation (持久化) + detail (API 动态派生) - 存储: status_detail 列 -> observation TEXT (JSON) - CheckerDefinition: 新增 buildDetail(observation) 方法 - 各 checker 返回结构化 observation,API 层通过 registry 调用 buildDetail - HTTP: bodyPreview 在 status/header 失败时也提前采集 - UDP: observation 包含 durationMs,未响应归为 error failure - CMD: 超时/输出超限时保留已收集 observation - TCP: connectTimeMs 仅含连接建立耗时,不含 banner 等待 - 新增 buildDetail 单测和 mapCheckResult 覆盖测试 - 同步 openspec 主规范,归档 checker-observation 变更
This commit is contained in:
@@ -75,11 +75,11 @@
|
||||
- **THEN** 系统 SHALL 以配置错误退出,提示 udp.payload 与 udp.encoding 不匹配
|
||||
|
||||
### Requirement: udp checker 执行
|
||||
系统 SHALL 使用 Bun connected UDP socket 向目标发送单个 datagram,等待第一个 UDP 响应 datagram,记录完整执行耗时,并在发送失败、超时、资源超限或底层 socket 错误时产生结构化失败信息。
|
||||
系统 SHALL 使用 Bun connected UDP socket 向目标发送单个 datagram,等待第一个 UDP 响应 datagram,记录完整执行耗时和 UDP observation,并在发送失败、超时、资源超限或底层 socket 错误时产生结构化失败信息。
|
||||
|
||||
#### Scenario: UDP 请求响应成功
|
||||
- **WHEN** udp target 指向会返回 `PONG` 的 UDP 服务,且未配置 expect 或 `expect.responded` 为 `true`
|
||||
- **THEN** 系统 SHALL 记录 `matched=true`、`durationMs` 和包含响应大小的 `statusDetail`,并关闭 socket
|
||||
- **THEN** 系统 SHALL 记录 `matched=true`、`durationMs` 和包含响应大小的 observation,并关闭 socket
|
||||
|
||||
#### Scenario: 使用 hostname 执行 UDP 探测
|
||||
- **WHEN** udp target 的 `udp.host` 为可解析域名或 `localhost`
|
||||
@@ -91,19 +91,19 @@
|
||||
|
||||
#### Scenario: UDP 无响应且默认期望响应
|
||||
- **WHEN** udp target 指向在 timeout 内不返回 UDP datagram 的服务,且未配置 expect 或 `expect.responded` 为 `true`
|
||||
- **THEN** 系统 SHALL 在 `ctx.signal` abort 后记录 `matched=false`,failure 的 kind 为 `error`,phase 为 `response`,message 包含超时或未响应信息
|
||||
- **THEN** 系统 SHALL 在 `ctx.signal` abort 后记录 `matched=false`,observation SHALL 包含 responded=false 和 error,failure 的 kind 为 `error`,phase 为 `response`,message 包含超时或未响应信息
|
||||
|
||||
#### Scenario: 期望无响应且实际无响应
|
||||
- **WHEN** udp target 配置 `expect.responded: false`,且 timeout 内未收到 UDP datagram
|
||||
- **THEN** 系统 SHALL 记录 `matched=true`,statusDetail SHALL 表示未收到响应
|
||||
- **THEN** 系统 SHALL 记录 `matched=true`,observation SHALL 包含 responded=false,API detail SHALL 表示未收到响应
|
||||
|
||||
#### Scenario: 期望无响应但实际收到响应
|
||||
- **WHEN** udp target 配置 `expect.responded: false`,但收到了 UDP datagram
|
||||
- **THEN** 系统 SHALL 记录 `matched=false`,failure 的 kind 为 `mismatch`,phase 为 `responded`
|
||||
- **THEN** 系统 SHALL 记录 `matched=false`,observation SHALL 包含 responded=true 和响应摘要,failure 的 kind 为 `mismatch`,phase 为 `responded`
|
||||
|
||||
#### Scenario: UDP socket 底层错误
|
||||
- **WHEN** Bun UDP socket 在发送或接收过程中触发 error 事件
|
||||
- **THEN** 系统 SHALL best-effort 关闭 socket,并记录 `matched=false`、failure.kind=`error` 和可读错误信息
|
||||
- **THEN** 系统 SHALL best-effort 关闭 socket,并记录 `matched=false`、failure.kind=`error` 和可读错误信息,并在可收集时记录 observation
|
||||
|
||||
#### Scenario: ICMP unreachable 不作为 UDP 响应
|
||||
- **WHEN** 底层系统因目标端口不可达产生 ICMP unreachable
|
||||
@@ -187,17 +187,17 @@
|
||||
- **WHEN** YAML 中 udp target 的 expect 包含 `status: [200]`、`maxDurationMs: 1000` 或其他非 udp expect 字段
|
||||
- **THEN** 系统 SHALL 以配置错误退出,提示 expect 包含未知字段
|
||||
|
||||
### Requirement: udp statusDetail 摘要
|
||||
系统 SHALL 在 udp 执行后生成简短 statusDetail 摘要,展示关键结果并避免写入过长响应内容。
|
||||
### Requirement: udp detail 摘要
|
||||
系统 SHALL 在 udp API 序列化时从 observation 动态生成简短 detail 摘要,展示关键结果和执行耗时并避免返回过长响应内容。UDP observation SHALL 包含 durationMs 以支持 detail 构造。
|
||||
|
||||
#### Scenario: 收到响应的摘要
|
||||
- **WHEN** udp target 收到 4 字节响应且完整执行耗时为 12ms
|
||||
- **THEN** statusDetail SHALL 包含 `responded in 12ms` 和 `4 bytes`
|
||||
- **THEN** detail SHALL 包含 `responded in 12ms` 和 `4 bytes`
|
||||
|
||||
#### Scenario: 未收到响应的摘要
|
||||
- **WHEN** udp target 配置 `expect.responded: false` 且 timeout 内未收到 UDP datagram
|
||||
- **THEN** statusDetail SHALL 包含 `no response` 和执行耗时
|
||||
- **THEN** detail SHALL 包含 `no response` 和执行耗时
|
||||
|
||||
#### Scenario: 响应内容摘要截断
|
||||
- **WHEN** udp target 收到较长响应内容
|
||||
- **THEN** statusDetail SHALL 只展示按 `responseEncoding` 转换并截断后的响应摘要
|
||||
- **THEN** detail SHALL 只展示按 `responseEncoding` 转换并截断后的响应摘要
|
||||
|
||||
Reference in New Issue
Block a user