跳转到内容
v0.8.4正式版

Usage 与 Governance 数据交接 FinOps

Halro 当前不会主动向外部 FinOps 平台发送数据。所谓“交接 FinOps”,是管理员在 Halro 所在主机 生成并验证本地导出,再由部署方通过受信通道把批准的文件交给外部导入作业。

两份数据分别回答什么
数据产品默认位置内容不能回答
Usage export<data_dir>/usage/manifest.json 及其分区Attempt、Token、实际/估算费用、Project、Work Unit、Run、Route、Deployment、Provider 和价格快照Work Unit 最终是否成功
Governance export<data_dir>/governance/export/gex_.../work_units.ndjsonruns.ndjsonoutcomes.ndjsonoutcome_definitions.ndjson 与 manifestAttempt 的实际费用

Governance 中的 Run 行只有预算上限,不是消费金额。FinOps 必须以稳定的 project_idwork_unit_idrun_id 关联 Usage Attempt;不能把 Run 预算加总成实际成本。

Halro 运行时按 usage.parquet_interval 周期把已结算 Attempt 写到 <data_dir>/usage/。新分区使用 usage.export_format 选择 Parquet 或 NDJSON,已有分区不会因配置变化而改写格式。manifest schema 6 包括:

  • last_sequence:已经进入 Usage 分区的最高 Attempt 账本序号;
  • 每个文件的路径、格式、schema、最小/最大序号、记录数和 SHA-256;
  • 文件级输入/输出 Token 与已知费用合计。

需要立即刷新时,先停止 Halro,再使用实际二进制和配置路径执行:

Terminal window
./halro usage compact --config ./config.yaml
./halro usage verify --config ./config.yaml

这些是离线命令,会读取并认证 Accounting Ledger;实例仍持有数据目录时不应并发执行。compact 输出当前 manifest,verify 对 Ledger 与导出分区做 reconciliation。验证失败、出现 missing、duplicate 或 extra 时,不得把该批送入财务聚合。

仅复制 manifest 不够;必须连同它列出的全部分区文件一起交接。先复制到不可变暂存区,再逐项核对 manifest 中的 SHA-256、记录数和文件级合计。

Governance export 是 Admin 变更端点:

POST /admin/api/v1/governance/export
Cookie: <已登录的管理员会话>
X-CSRF-Token: <该会话返回的 CSRF token>
Origin: <与 admin.external_origin 一致的 origin>

它要求管理员角色、有效 Admin Session、同源校验和 CSRF;只读 Admin 和 Gateway Key 都不能触发。 当前没有适合长期无人值守作业的服务身份,不要把管理员密码、Session Cookie 或 TOTP Seed 写进 cron、 CI 变量或 FinOps 管道。应由受控管理员客户端触发,再由主机侧受限作业读取返回的 directory

当前控制台尚未提供导出按钮。已在自己的 Admin origin 登录的管理员,可在该页面的浏览器开发者控制台 执行一次同源请求;代码先从当前会话读取 CSRF token,再触发导出:

const sessionResponse = await fetch('/admin/api/v1/session', { credentials: 'same-origin' });
if (!sessionResponse.ok) throw new Error(`session: ${sessionResponse.status}`);
const session = await sessionResponse.json();
const exportResponse = await fetch('/admin/api/v1/governance/export', {
method: 'POST',
credentials: 'same-origin',
headers: { 'X-CSRF-Token': session.csrf_token },
});
const exportResult = await exportResponse.json();
if (!exportResponse.ok) throw new Error(JSON.stringify(exportResult));
console.log(exportResult);

只在自己控制的 Halro Admin 页面执行这段固定代码,不要粘贴来源不明的浏览器脚本。响应只是告诉你 服务器上的本地目录;它不会把文件下载到浏览器。

成功响应返回导出 ID、本机绝对目录和 manifest。文件写入:

<data_dir>/governance/export/gex_.../
├── manifest.json
├── outcome_definitions.ndjson
├── outcomes.ndjson
├── runs.ndjson
└── work_units.ndjson

manifest v1 记录生成时间、Accounting/Governance 两种水位,以及每个数据集的 schema、格式、路径、 SHA-256 和记录数。Outcome 数据还记录治理 sequence 范围。触发失败时不会把不一致快照冒充成功导出。

三、形成一个当前可验证的交接批次

Section titled “三、形成一个当前可验证的交接批次”

当前两类导出没有共同的原子“导出全部”按钮。需要财务关账或一次性验收时,使用下面的受控流程:

  1. 暂停新的业务提交,并等待正在执行的请求、Run 和 Outcome 写入到达可解释状态;
  2. 保持 Halro 运行,由管理员会话触发 Governance export,保存返回的导出 ID 和目录;
  3. 停止 Halro,确认进程已释放数据目录;
  4. 执行 halro usage compacthalro usage verify
  5. 固化两份 manifest 和它们引用的所有文件,计算交接批次 ID;
  6. 通过受信通道送到不可变原始区,先验证再按稳定 ID join;
  7. 只有验证、关联和完整性判定通过后,才生成财务聚合。

如果不能暂停流量,这两份快照来自不同时间,应作为增量批次处理并标记 partial。不要用本地复制 完成时间伪造共同截止点。

Governance manifest 的 accounting_watermark.sequence 是完整 Accounting Ledger 快照位置,包含 Work Unit/Run 创建、关闭等治理事件。Usage manifest 的 last_sequence 只表示已经导出的最高 Attempt 序号。最后一次 Attempt 之后关闭 Run 或 Work Unit 时,前者会继续前进而后者不会;因此:

usage.last_sequence < governance.accounting_watermark.sequence 不等于缺少费用记录,等待下一次 Usage export 也不保证两个数会相等。

两个 sequence 可以用于各自数据产品的增量和排障,不能作为跨产品完整性的充分条件。跨产品交接应 依赖:Usage verify 的 reconciliation、manifest 文件校验、稳定 ID join、资源终态,以及报表自身的 completeness/reason。

以下任一情况都不能产出“完整成本/成功率”:

  • Usage verify 未通过,或 manifest 引用文件缺失、摘要/记录数不一致;
  • 目标 Work Unit 仍开放,或仍有 pending/inflight Attempt;
  • Outcome 是 provisional,或成熟 Work Unit 尚未上报 Outcome;
  • Attempt 的成本未知,或 ID 无法关联到导出的 Project/Run/Work Unit;
  • 在线导出的两个快照没有共同受控截止点。

保留并传播 cost_completenessoutcome_completeness 和 reason。partial 是“已知数据不完整”, unknown 是“当前无法判断完整性”;两者都不能填成零、失败或成功。估算费用仍属于已知金额中的 估算子集,应保留 cost_estimated,不能与 Provider 已报告费用混在一起。

cost_completenessoutcome_completeness 和 reason 是内置 Summary 的报表口径,不是 Governance NDJSON 每一行自带的字段。外部 FinOps 要么按相同成熟度规则计算并保留 reason,要么把对应 Admin Summary 作为另一个明确时间点的快照;不能声称原始导出已经直接提供这些结论。

建议把“Governance export ID + 两份 manifest 摘要”作为导入幂等键。处理顺序是:

  1. 原样保存导出文件和 manifest,不在原始层重写;
  2. 校验路径、SHA-256、schema、格式和记录数;
  3. 先导入 Project、Work Unit、Run、Definition、Outcome 和 Attempt 明细;
  4. 再生成 Project、业务群组、Definition 版本和时间窗口聚合;
  5. 重复导入同一批次不得增加 Attempt 数或金额;
  6. 对账至少比较 Project/Work Unit/Run/Attempt 数量、已知费用、估算费用和未知费用数量。

SHA-256 只能发现内容变化,不能证明文件来自哪台 Halro。主机到 FinOps 的传输还需要受信通道,或 对 manifest 增加组织自己的签名/MAC。不要外送 Provider Credential、Gateway Key、Prompt、Response、 失败捕获正文或管理员 Session。

  • Governance export 只能由管理员会话触发,文件只能从服务器受限目录取得;
  • Usage compact/verify 在实例停止后运行,验证报告无 missing、duplicate 或 extra;
  • 两份 manifest 及全部数据文件均已校验,原始分区不可变;
  • 重复导入不增加金额,未知/估算费用没有被转成 $0
  • 一个 Work Unit 的多个 Run 和全部 Attempt 只汇总成一个最终业务结果;
  • provisional、partial、unknown 和没有 Outcome 的情况在 FinOps 中仍可见;
  • 传输不包含 Prompt、Response、凭据、Session 或失败捕获正文;
  • 生产自动化需求已明确记录为外部编排边界,没有把 Admin Session 当服务账号。

Outcome 的来源和字段见接入运行治理,组合案例见 Governance Export 交给 FinOps