# v0.2 hwlab-gateway 服务规格

`hwlab-gateway` 是 v02 的真实硬件/host transport 边界服务，内部端口 `7001`。它用于 gateway 主动出站 demo 和受控 shell dispatch，不是普通用户或前端可直连的硬件 API。

## 在系统中的职责划分

- 向 `hwlab-cloud-api` 注册 gateway session、resource 和 capability。
- 通过主动轮询 `/v1/gateway/poll` 获取 cloud-api 分发的 `hardware.invoke.shell` 请求，并把结果回传 `/v1/gateway/result`。
- 只做 transport 和 bounded command execution，不理解用户权限或业务授权。
- transport 稳定性是 P0 基础能力：大 stdout、长单行 stdout、stderr flood、命令 timeout、gateway 超容量并发和结果回传失败都必须返回结构化 JSON 状态；禁止让 poll/result、Cloud API request、Code Agent commandExecution 或 `hwlab-cli` 调用进入无 stdout、无 trace、无 terminal status 的黑洞。

## 内部架构

- `cmd/hwlab-gateway/main.ts` 维护 gateway state、outbound poll loop、inflight request map 和 command execution，运行入口必须使用 Bun。
- `internal/cloud/gateway-demo-registry.ts` 在 cloud-api 内保存 gateway session、队列和 pending result。
- command execution 默认关闭；只有显式 `HWLAB_GATEWAY_CMD_EXEC_ENABLED=1` 或 demo open 时才执行 shell。
- command execution 必须同时读取 stdout/stderr，并对每路输出做有界收集和 `stdoutTruncated`/`stderrTruncated` 标记，避免任一路 pipe 填满导致子进程或 gateway result 卡死。默认 bounded body 可以截断，但必须保留字节数、truncated 标记和 enough preview；需要完整超大输出时应另设计 evidence/spool，不得把完整无限输出塞进同步 JSON 响应。
- gateway inflight 上限是背压机制，不是黑洞机制。超过 `maxInflightRequests` 时，Cloud API/gateway 必须返回包含 `reason=gateway_busy`、`inflightCount` 和 `maxInflightRequests` 的结构化结果，调用方可重试或排队。
- gateway 回传的 JSON-RPC `meta.environment`、dispatch audit 和 evidence 的 `environment` 必须跟随 cloud-api 请求 meta；没有合法请求 meta 时才回退到 gateway 进程的 `HWLAB_ENVIRONMENT` / `HWLAB_GITOPS_PROFILE`，v02 lane 不得把硬件证据标成 `dev`。

## API 接口说明

| 接口 | 说明 |
| --- | --- |
| `GET /health/live` | 返回 gateway health、gatewayId、gatewaySessionId 和 outboundConnected。 |
| `GET /status` | 返回 session、registry、outbound poll 和 inflight 摘要。 |
| `GET /capabilities` | 返回 resource/capability 列表。 |
| `POST cloud-api /v1/gateway/poll` | gateway 主动向 cloud-api 取任务。 |
| `POST cloud-api /v1/gateway/result` | gateway 回传 JSON-RPC response。 |

## 测试规格

## T1

阅读 docs/reference/spec-v02-hwlab-gateway.md，然后用 cli 手动测试以下内容：访问 gateway `/health/live` 和 `/status`，确认 gatewaySessionId、resourceId、capability 列表存在，且 command execution 状态清晰。

## T2

阅读 docs/reference/spec-v02-hwlab-gateway.md，然后用 cli 手动测试以下内容：通过 cloud-api `/v1/gateway/sessions` 观察 gateway online/stale 状态；不要直接从前端或普通用户请求 gateway shell。

## T3

阅读 docs/reference/spec-v02-hwlab-gateway.md，然后在 `G14:/root/hwlab-v02` 用 `hwlab-cli client gateway pressure` 手动测试以下内容：对目标 gateway 运行 small stdout、至少 128KiB stdout、至少 128KiB 单行 stdout、至少 128KiB stderr、短 timeout 和超过 gateway `maxInflightRequests` 的并发请求。验收条件是全部场景在 CLI timeout 内返回结构化 JSON；大输出显示 truncated 标记，timeout 显示 `timed_out`，超容量显示 `gateway_busy`，不能出现无输出、HTTP transport timeout 或 Code Agent trace 黑洞。

## T4

阅读 docs/reference/spec-v02-hwlab-gateway.md，然后通过 v02 cloud-api 的 gateway 诊断入口触发一次 bounded shell dispatch，确认 JSON-RPC response meta、dispatch audit 和 evidence 的 `environment` 都是 `v02`。

## 规格的实现情况

| 规格项 | 状态 | 说明 |
| --- | --- | --- |
| health/status/capabilities | 已实现 | gateway service 提供只读观测。 |
| outbound poll/result | 已实现 | 与 cloud-api registry 对接。 |
| bounded shell execution | 已实现 | 受 env 开关、timeout 和 output limit 约束。 |
| gateway 压测闭环 | 已实现 | `hwlab-cli client gateway pressure` 覆盖大输出、timeout 和并发背压，不依赖 shell pipe 裁剪。 |
| v02 environment 标记 | 已实现 | response meta、audit 和 evidence 从请求 meta 或 gateway env 派生，不把 v02 dispatch 证据落回 `dev`。 |
| 生产级 gateway 多租户隔离 | 未完全实现 | 当前是 demo/transport skeleton。 |

