@viccydev/pi-fpa 0.8.0 → 0.9.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +15 -4
- package/extensions/fpa-artifacts/compose.ts +156 -42
- package/extensions/fpa-artifacts/contracts.ts +202 -2
- package/extensions/fpa-artifacts/forecast-quality.ts +138 -0
- package/extensions/fpa-artifacts/index.ts +24 -1
- package/extensions/fpa-dashboard/coordinator.ts +2 -2
- package/extensions/fpa-dashboard/cycle-operating-projection.ts +5 -4
- package/extensions/fpa-dashboard/forward-outlook.ts +5 -2
- package/extensions/fpa-dashboard/index.ts +12 -3
- package/extensions/fpa-dashboard/projector.ts +58 -1
- package/extensions/fpa-dashboard/service.ts +13 -2
- package/extensions/fpa-dashboard/stage-projector.ts +131 -10
- package/extensions/fpa-routing-guard/graph-installer.ts +234 -0
- package/extensions/fpa-routing-guard/index.ts +114 -28
- package/graphs/fpa-forecast-freeze.json +103 -7
- package/graphs/fpa-strategy-planning.json +159 -0
- package/package.json +2 -2
- package/prompts/fpa-plan-cycle.md +12 -12
- package/skills/fpa-apply-core-rules/SKILL.md +8 -8
- package/skills/fpa-apply-core-rules/references/core-rules.md +11 -13
- package/skills/fpa-diagnose-actuals/references/artifact-contract.md +2 -0
- package/skills/fpa-forecast-approved-strategy/SKILL.md +12 -0
- package/skills/fpa-forecast-approved-strategy/references/artifact-contract.md +26 -1
- package/skills/fpa-recommend-strategy/SKILL.md +1 -1
- package/skills/fpa-recommend-strategy/references/artifact-contract.md +2 -1
- package/skills/fpa-refresh-dashboard/SKILL.md +7 -4
- package/skills/fpa-review-strategy/references/artifact-contract.md +22 -0
- package/graphs/fpa-period-analysis.json +0 -10
- package/graphs/fpa-strategy-recommendation.json +0 -11
|
@@ -0,0 +1,159 @@
|
|
|
1
|
+
{
|
|
2
|
+
"schemaVersion": 1,
|
|
3
|
+
"name": "fpa-strategy-planning",
|
|
4
|
+
"version": "4.2.0",
|
|
5
|
+
"description": "FP&A 组合式策略规划:在一个 Graph 内完成目标规划、并行只读数据/驱动审计、并行只读场景分析、策略推荐与独立审核,最终形成 reviewed_strategy_handoff。必须提供字符串 context.scope_id、context.cycle_id、context.forecast_role;Graph 不审批、不预测、不发布仪表盘。",
|
|
6
|
+
"mutationPolicy": "mutating",
|
|
7
|
+
"start": "plan_cycle",
|
|
8
|
+
"maxSteps": 24,
|
|
9
|
+
"nodes": [
|
|
10
|
+
{
|
|
11
|
+
"id": "plan_cycle",
|
|
12
|
+
"type": "subagent",
|
|
13
|
+
"agentName": "plan_cycle",
|
|
14
|
+
"label": "目标与范围规划",
|
|
15
|
+
"outputKey": "plan_cycle",
|
|
16
|
+
"next": "parallel_analysis",
|
|
17
|
+
"systemPrompt": "你是 FP&A 目标规划 Agent。权威上下文为 scope_id={{context.scope_id}}、cycle_id={{context.cycle_id}}、forecast_role={{context.forecast_role}}。不得从目标文本猜测或替换这些标识。",
|
|
18
|
+
"prompt": "目标:{{goal}}\n\n按 fpa-plan-cycle 先调用 fpa_data_catalog 实测目标期和对比期字段可用性,再写 artifacts/planning_brief.md。明确目标、预算、周期、in_scope/out_of_scope 维度与指标、App 清单及增长/成熟/收缩角色。正式预测指标白名单仅为 spend、revenue、roas。不得生成策略、预测或调用任何 fpa_dashboard_* 工具。",
|
|
19
|
+
"skills": ["fpa-apply-core-rules", "fpa-plan-cycle"],
|
|
20
|
+
"tools": ["read", "write", "fpa_data_catalog"]
|
|
21
|
+
},
|
|
22
|
+
{
|
|
23
|
+
"id": "parallel_analysis",
|
|
24
|
+
"type": "parallel",
|
|
25
|
+
"label": "并行数据与经营审计",
|
|
26
|
+
"concurrency": 2,
|
|
27
|
+
"next": "synthesize_analysis",
|
|
28
|
+
"children": [
|
|
29
|
+
{
|
|
30
|
+
"id": "actuals_audit",
|
|
31
|
+
"type": "subagent",
|
|
32
|
+
"agentName": "actuals_audit",
|
|
33
|
+
"systemPrompt": "你是只读 FP&A 数据质量审计 Agent。不得写文件或发布仪表盘。",
|
|
34
|
+
"prompt": "目标:{{goal}}\n\n读取 artifacts/planning_brief.md,按 fpa-diagnose-actuals 检查数据窗口、字段覆盖、revenue 回刷成熟度、cohort 可用性、scope reduction 与 blocking issue。只输出结构化 JSON 证据给汇总节点,不写任何 artifact。",
|
|
35
|
+
"skills": ["fpa-apply-core-rules", "fpa-diagnose-actuals"],
|
|
36
|
+
"tools": ["read", "fpa_data_catalog", "fpa_query", "fpa_cohort"]
|
|
37
|
+
},
|
|
38
|
+
{
|
|
39
|
+
"id": "driver_audit",
|
|
40
|
+
"type": "subagent",
|
|
41
|
+
"agentName": "driver_audit",
|
|
42
|
+
"systemPrompt": "你是只读 FP&A 经营驱动审计 Agent。不得写文件或发布仪表盘。",
|
|
43
|
+
"prompt": "目标:{{goal}}\n\n读取 artifacts/planning_brief.md,按 in_scope_dimensions 独立查询 spend、revenue、roas、cpi、installs,分析组合、App、商店、渠道和平台驱动;明确每个 App/切片的增长、保持、削减或止损证据。只输出结构化 JSON,不写任何 artifact。",
|
|
44
|
+
"skills": ["fpa-apply-core-rules", "fpa-analyze-drivers"],
|
|
45
|
+
"tools": ["read", "fpa_query", "fpa_cohort", "fpa_compare", "fpa_calc"]
|
|
46
|
+
}
|
|
47
|
+
]
|
|
48
|
+
},
|
|
49
|
+
{
|
|
50
|
+
"id": "synthesize_analysis",
|
|
51
|
+
"type": "subagent",
|
|
52
|
+
"agentName": "synthesize_analysis",
|
|
53
|
+
"label": "汇总上周期分析",
|
|
54
|
+
"outputKey": "driver_analysis",
|
|
55
|
+
"next": "parallel_scenarios",
|
|
56
|
+
"systemPrompt": "你是 FP&A 分析汇总 Agent。只整合并复核并行审计证据,不补造数据。",
|
|
57
|
+
"prompt": "目标:{{goal}}\n\n并行审计:{{data.parallel_analysis}}\n\n读取 planning_brief,交叉核对两个只读审计结果;冲突时重新用确定性工具复算。写 artifacts/actuals_snapshot.md、artifacts/data_issue_report.md、artifacts/driver_analysis.md 和机器可读 artifacts/driver_analysis.json。JSON 必须符合 driver_analysis contract,包含 artifact_type、status、headline_results、drivers、data_limits/limitations,并对每个 App 或 in-scope 切片给出增长/保持/削减/止损结论与证据。不得生成策略或发布仪表盘。",
|
|
58
|
+
"skills": ["fpa-apply-core-rules", "fpa-diagnose-actuals", "fpa-analyze-drivers"],
|
|
59
|
+
"tools": ["read", "write", "fpa_query", "fpa_compare", "fpa_calc"]
|
|
60
|
+
},
|
|
61
|
+
{
|
|
62
|
+
"id": "parallel_scenarios",
|
|
63
|
+
"type": "parallel",
|
|
64
|
+
"label": "并行策略场景分析",
|
|
65
|
+
"concurrency": 3,
|
|
66
|
+
"next": "synthesize_scenarios",
|
|
67
|
+
"children": [
|
|
68
|
+
{
|
|
69
|
+
"id": "efficiency_lane",
|
|
70
|
+
"type": "subagent",
|
|
71
|
+
"agentName": "efficiency_lane",
|
|
72
|
+
"systemPrompt": "你是只读 FP&A 稳健效率场景 Agent。不得写文件、批准策略或发布仪表盘。",
|
|
73
|
+
"prompt": "读取 planning_brief、actuals_snapshot 与 driver_analysis,构造维持硬 ROAS 下限的稳健/效率候选场景,逐 App/商店/渠道给出完整 allocation、downside/base/upside、假设和止损。只输出结构化 JSON 候选,不写 artifact。",
|
|
74
|
+
"skills": ["fpa-apply-core-rules", "fpa-simulate-strategies"],
|
|
75
|
+
"tools": ["read", "fpa_query", "fpa_calc"]
|
|
76
|
+
},
|
|
77
|
+
{
|
|
78
|
+
"id": "growth_lane",
|
|
79
|
+
"type": "subagent",
|
|
80
|
+
"agentName": "growth_lane",
|
|
81
|
+
"systemPrompt": "你是只读 FP&A 增长与探索场景 Agent。不得写文件、批准策略或发布仪表盘。",
|
|
82
|
+
"prompt": "读取 planning_brief、actuals_snapshot 与 driver_analysis,构造增长/探索候选场景;探索预算约 10%,逐 App/商店/渠道给出完整 allocation、downside/base/upside、假设和止损。只输出结构化 JSON 候选,不写 artifact。",
|
|
83
|
+
"skills": ["fpa-apply-core-rules", "fpa-simulate-strategies"],
|
|
84
|
+
"tools": ["read", "fpa_query", "fpa_calc"]
|
|
85
|
+
},
|
|
86
|
+
{
|
|
87
|
+
"id": "risk_lane",
|
|
88
|
+
"type": "subagent",
|
|
89
|
+
"agentName": "risk_lane",
|
|
90
|
+
"systemPrompt": "你是只读 FP&A 约束与风险挑战 Agent。不得写文件、批准策略或发布仪表盘。",
|
|
91
|
+
"prompt": "读取 planning_brief 与 driver_analysis,独立检查预算上下限、ROAS 硬下限、Revenue 次目标、ROAS<0.5 止损、集中度、外推和数据成熟度。输出每个候选策略必须满足的约束、压力测试区间与淘汰规则,只输出结构化 JSON。",
|
|
92
|
+
"skills": ["fpa-apply-core-rules", "fpa-simulate-strategies"],
|
|
93
|
+
"tools": ["read", "fpa_query", "fpa_calc"]
|
|
94
|
+
}
|
|
95
|
+
]
|
|
96
|
+
},
|
|
97
|
+
{
|
|
98
|
+
"id": "synthesize_scenarios",
|
|
99
|
+
"type": "subagent",
|
|
100
|
+
"agentName": "synthesize_scenarios",
|
|
101
|
+
"label": "汇总候选策略",
|
|
102
|
+
"outputKey": "strategy_scenarios",
|
|
103
|
+
"next": "recommend_strategy",
|
|
104
|
+
"systemPrompt": "你是 FP&A 场景汇总 Agent。所有加总、ROAS 和约束判断必须确定性复算。",
|
|
105
|
+
"prompt": "目标:{{goal}}\n\n并行场景与风险审计:{{data.parallel_scenarios}}\n\n读取权威上游工件,合并、去重并复算候选场景,至少保留现状、稳健和增长场景。写 artifacts/strategy_scenarios.md 与符合 contract 的 artifacts/strategy_scenarios.json;逐切片完整覆盖,探索/利用分开,所有 ROAS<0.5 切片必须削减或清零。不得推荐、批准、预测或发布仪表盘。",
|
|
106
|
+
"skills": ["fpa-apply-core-rules", "fpa-simulate-strategies"],
|
|
107
|
+
"tools": ["read", "write", "fpa_calc"]
|
|
108
|
+
},
|
|
109
|
+
{
|
|
110
|
+
"id": "recommend_strategy",
|
|
111
|
+
"type": "subagent",
|
|
112
|
+
"agentName": "recommend_strategy",
|
|
113
|
+
"label": "形成执行策略",
|
|
114
|
+
"outputKey": "strategy_proposal",
|
|
115
|
+
"next": "review_strategy",
|
|
116
|
+
"systemPrompt": "你是 FP&A 策略推荐 Agent。不得自我批准、生成预测或发布仪表盘。",
|
|
117
|
+
"prompt": "目标:{{goal}}\n\n读取 planning_brief、driver_analysis 和 strategy_scenarios,按 fpa-recommend-strategy 选择推荐策略。写 artifacts/strategy_proposal.md 与符合 contract 的 artifacts/strategy_proposal.json。allocation 必须逐 App/商店/渠道包含显式 action(grow/hold/cut/stop)、spend 与 change_from_baseline,使 Dashboard 能明确展示增长、保持、削减和止损;保留完整 expected_outcomes、理由、风险、阈值和 required_human_decisions。",
|
|
118
|
+
"skills": ["fpa-apply-core-rules", "fpa-recommend-strategy"],
|
|
119
|
+
"tools": ["read", "write", "fpa_calc"]
|
|
120
|
+
},
|
|
121
|
+
{
|
|
122
|
+
"id": "review_strategy",
|
|
123
|
+
"type": "subagent",
|
|
124
|
+
"agentName": "review_strategy",
|
|
125
|
+
"label": "独立审核",
|
|
126
|
+
"outputKey": "strategy_review",
|
|
127
|
+
"parseJson": true,
|
|
128
|
+
"next": "route_review",
|
|
129
|
+
"systemPrompt": "你是未参与推荐生成的 FP&A 独立审核 Agent。不得批准策略、生成预测或发布仪表盘。",
|
|
130
|
+
"prompt": "读取 proposal 及全部上游机器工件,按 fpa-review-strategy 独立复算覆盖、加总、ROAS、止损、探索占比、外推与数据血缘。写 artifacts/strategy_review.md 和 artifacts/strategy_review.json。最终只输出路由 JSON:{\"status\":\"support|support_with_conditions|reject\",\"summary\":\"...\",\"conditions\":[]}。",
|
|
131
|
+
"skills": ["fpa-apply-core-rules", "fpa-review-strategy"],
|
|
132
|
+
"tools": ["read", "write", "fpa_query", "fpa_calc"]
|
|
133
|
+
},
|
|
134
|
+
{
|
|
135
|
+
"id": "route_review",
|
|
136
|
+
"type": "router",
|
|
137
|
+
"label": "审核结果路由",
|
|
138
|
+
"path": "data.strategy_review.status",
|
|
139
|
+
"cases": [
|
|
140
|
+
{ "equals": "reject", "label": "审核拒绝,重新推荐", "to": "recommend_strategy" },
|
|
141
|
+
{ "equals": "support", "label": "审核支持", "to": "prepare_strategy_handoff" },
|
|
142
|
+
{ "equals": "support_with_conditions", "label": "有条件支持", "to": "prepare_strategy_handoff" }
|
|
143
|
+
],
|
|
144
|
+
"default": { "label": "其他结果,重新推荐", "to": "recommend_strategy" }
|
|
145
|
+
},
|
|
146
|
+
{
|
|
147
|
+
"id": "prepare_strategy_handoff",
|
|
148
|
+
"type": "subagent",
|
|
149
|
+
"agentName": "prepare_strategy_handoff",
|
|
150
|
+
"label": "形成已审核策略交接",
|
|
151
|
+
"outputKey": "strategy_handoff",
|
|
152
|
+
"parseJson": true,
|
|
153
|
+
"systemPrompt": "你是 FP&A 策略交接 Agent。权威上下文为 scope_id={{context.scope_id}}、cycle_id={{context.cycle_id}}、forecast_role={{context.forecast_role}}。不批准、不预测、不发布仪表盘。",
|
|
154
|
+
"prompt": "读取 planning_brief、driver_analysis.json、strategy_scenarios.json、strategy_proposal.json 与 strategy_review.json,先调用 fpa_json_fingerprint 对 proposal/review 两个 JSON 生成确定性 SHA-256,再严格按 fpa-review-strategy 的 reviewed_strategy_handoff contract 核验并写 artifacts/reviewed_strategy_handoff.json。ready 文件必须包含 kind=fpa.reviewed-strategy-handoff、scope_id/cycle_id/forecast_role、相同的 strategy_version 与 reviewed_strategy_version、工具返回的 proposal/review fingerprint、独立审核身份、review_opinion、条件、剩余风险和 next_graph=fpa-forecast-freeze;失败时写 blocked 结果且不得覆盖已有 ready 文件。最终只输出 fpa.graph-handoff JSON。Graph 到此结束,由主 Agent 依次发布 period-review 与 next-strategy 模块并等待用户决策。",
|
|
155
|
+
"skills": ["fpa-apply-core-rules", "fpa-review-strategy"],
|
|
156
|
+
"tools": ["read", "write", "fpa_json_fingerprint"]
|
|
157
|
+
}
|
|
158
|
+
]
|
|
159
|
+
}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@viccydev/pi-fpa",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.9.0",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"description": "Full-cycle FP&A planning, strategy, forecast, and review prompts, skills, and data tools for Pi",
|
|
6
6
|
"license": "UNLICENSED",
|
|
@@ -31,7 +31,7 @@
|
|
|
31
31
|
"fpa-dashboard-worker": "./bin/fpa-dashboard-worker.mjs"
|
|
32
32
|
},
|
|
33
33
|
"scripts": {
|
|
34
|
-
"test": "node tests/package-structure.test.mjs && node tests/workflow-routing.test.mjs && node --test tests/workflow-routing-guard.test.mjs tests/graph-contract.test.mjs && node tests/extension-unit.test.mjs && node --test tests/catalog-timeout.test.mjs tests/artifact-store.test.mjs tests/artifact-ledger.test.mjs tests/artifact-handoff.test.mjs tests/forecast-compose.test.mjs tests/dashboard-actuals.test.mjs tests/dashboard-projector.test.mjs tests/dashboard-module-publisher.test.mjs tests/dashboard-stage-projector.test.mjs tests/strategy-decision.test.mjs tests/cycle-operating-projection.test.mjs tests/forward-outlook.test.mjs tests/forecast-accuracy.test.mjs tests/dashboard-publisher.test.mjs tests/dashboard-provenance.test.mjs tests/dashboard-coordinator.test.mjs && node tests/pi-loader-smoke.mjs && node tests/worker-loader-smoke.mjs && node tests/publish-workflow.test.mjs",
|
|
34
|
+
"test": "node tests/package-structure.test.mjs && node tests/workflow-routing.test.mjs && node --test tests/workflow-routing-guard.test.mjs tests/graph-contract.test.mjs tests/graph-installer.test.mjs && node tests/extension-unit.test.mjs && node --test tests/catalog-timeout.test.mjs tests/artifact-store.test.mjs tests/artifact-ledger.test.mjs tests/artifact-handoff.test.mjs tests/forecast-compose.test.mjs tests/dashboard-actuals.test.mjs tests/dashboard-projector.test.mjs tests/dashboard-module-publisher.test.mjs tests/dashboard-stage-projector.test.mjs tests/strategy-decision.test.mjs tests/cycle-operating-projection.test.mjs tests/forward-outlook.test.mjs tests/forecast-accuracy.test.mjs tests/dashboard-publisher.test.mjs tests/dashboard-provenance.test.mjs tests/dashboard-coordinator.test.mjs && node tests/pi-loader-smoke.mjs && node tests/worker-loader-smoke.mjs && node tests/publish-workflow.test.mjs",
|
|
35
35
|
"test:structure": "node tests/package-structure.test.mjs",
|
|
36
36
|
"test:unit": "node tests/extension-unit.test.mjs && node --test tests/catalog-timeout.test.mjs tests/artifact-store.test.mjs tests/artifact-ledger.test.mjs tests/artifact-handoff.test.mjs tests/forecast-compose.test.mjs tests/dashboard-actuals.test.mjs tests/dashboard-projector.test.mjs tests/dashboard-module-publisher.test.mjs tests/dashboard-stage-projector.test.mjs tests/strategy-decision.test.mjs tests/cycle-operating-projection.test.mjs tests/forward-outlook.test.mjs tests/forecast-accuracy.test.mjs tests/dashboard-publisher.test.mjs tests/dashboard-provenance.test.mjs tests/dashboard-coordinator.test.mjs",
|
|
37
37
|
"test:loader": "node tests/pi-loader-smoke.mjs && node tests/worker-loader-smoke.mjs",
|
|
@@ -17,19 +17,19 @@ argument-hint: "<project-root> <cycle-id> [instructions]"
|
|
|
17
17
|
## 强制 Graph 路由
|
|
18
18
|
|
|
19
19
|
先读取 `fpa-apply-core-rules`。如果当前 Agent 提供 `graph_list` 和
|
|
20
|
-
`graph_run`,必须先调用 `graph_list`,确认 `fpa-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
`
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
`
|
|
29
|
-
|
|
20
|
+
`graph_run`,必须先调用 `graph_list`,确认 `fpa-strategy-planning` 后按以下边界执行:
|
|
21
|
+
|
|
22
|
+
1. 以完整用户目标运行一个组合式 `fpa-strategy-planning`。`graph_run.context`
|
|
23
|
+
的所有值必须是字符串,并明确提供 `scope_id`、`cycle_id`、
|
|
24
|
+
`forecast_role`;对象、数组、数字和其他结构化要求全部留在 `goal`。
|
|
25
|
+
2. Graph 返回 `driver_analysis.json`、`strategy_proposal.json`、
|
|
26
|
+
`strategy_review.json` 与 `reviewed_strategy_handoff.json` 后,父 Agent 先调用
|
|
27
|
+
`fpa_dashboard_publish_review` preview/publish,取得最新 revision;再调用
|
|
28
|
+
`fpa_dashboard_publish_strategy`,传入 proposal/review/handoff 三个路径及精确
|
|
29
|
+
`scope_id`、`cycle_id`、`forecast_role` 做 preview/publish,发布
|
|
30
30
|
`next-strategy` 并等待仪表盘决策。
|
|
31
31
|
|
|
32
|
-
|
|
32
|
+
Graph 不得拥有或调用任何 `fpa_dashboard_*` 工具。发布是父 Agent
|
|
33
33
|
在 Graph 返回后的职责;父 Agent不得自行模拟 Graph 内的业务阶段。
|
|
34
34
|
|
|
35
35
|
如果匹配 Graph 不在 catalog 中或无法加载,列出缺口并保持 `blocked`;不得把
|
|
@@ -39,7 +39,7 @@ Graph 返回业务阻塞同样不构成降级理由。所需上下文缺失时
|
|
|
39
39
|
## 不可跳过的停点
|
|
40
40
|
|
|
41
41
|
- 策略推荐者不得批准或独立复核自己的提案。若宿主不能证明复核上下文与提案作者独立,复核阶段必须报告 `blocked`。
|
|
42
|
-
- 独立复核完成后,`fpa-strategy-
|
|
42
|
+
- 独立复核完成后,`fpa-strategy-planning` 必须生成精确绑定提案与复核版本的 `reviewed_strategy_handoff`,然后停止。
|
|
43
43
|
- 聊天中的认可、模型自我确认或 Forecast 授权都不等于策略执行授权。
|
|
44
44
|
- 仪表盘响应回到原主会话后,先由主 Agent 调用
|
|
45
45
|
`fpa_strategy_decision_commit`。只有 `confirm` 成功才可在后续运行
|
|
@@ -20,18 +20,18 @@ writing artifacts. It applies only when the current agent exposes both
|
|
|
20
20
|
|
|
21
21
|
| Eligible request and evidence | Required Graph |
|
|
22
22
|
| --- | --- |
|
|
23
|
-
| New or changed objective requiring planning, Actuals diagnosis,
|
|
24
|
-
| Completed `driver_analysis` requiring scenarios, recommendation, and independent review | `fpa-strategy-recommendation` |
|
|
23
|
+
| New or changed objective requiring planning, Actuals diagnosis, driver analysis, scenarios, recommendation, and independent review | `fpa-strategy-planning` |
|
|
25
24
|
| Ready `reviewed_strategy_handoff` plus an exact confirmed `strategy_decision` and a request for an official forecast | `fpa-forecast-freeze` |
|
|
26
25
|
| Exact committed approved Forecast ref plus an authorized execution request | `fpa-strategy-execution` |
|
|
27
26
|
| Exact Forecast and Execution refs plus newly arrived comparable Actuals | `fpa-cycle-review` |
|
|
28
27
|
|
|
29
|
-
3. Call `graph_run` with the user's complete goal
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
28
|
+
3. Call `graph_run` with the user's complete goal. Every `context` value must
|
|
29
|
+
be a string; provide exact `scope_id`, `cycle_id`, and `forecast_role`, and
|
|
30
|
+
keep structured planning details in `goal`. The parent agent must not
|
|
31
|
+
reproduce Graph nodes or pre-run their `fpa_*` calls. After the combined
|
|
32
|
+
planning Graph succeeds, the main Agent publishes `period-review` and then
|
|
33
|
+
`next-strategy` with their matching `fpa_dashboard_publish_*` tools. Graph
|
|
34
|
+
nodes must never receive dashboard publication tools.
|
|
35
35
|
4. If required context is missing or ambiguous, return `blocked` and request
|
|
36
36
|
the exact identity or ref. Do not fall back to direct phase execution.
|
|
37
37
|
|
|
@@ -2,20 +2,18 @@
|
|
|
2
2
|
|
|
3
3
|
## 1. Workflow and artifacts
|
|
4
4
|
|
|
5
|
-
|
|
5
|
+
Combined strategy-planning workflow (`fpa-strategy-planning`):
|
|
6
6
|
|
|
7
|
-
`planning_brief ->
|
|
7
|
+
`planning_brief -> parallel(actuals audit, driver audit) -> driver_analysis -> parallel(efficiency, growth, risk) -> strategy_scenarios -> strategy_proposal -> strategy_review -> reviewed_strategy_handoff`
|
|
8
8
|
|
|
9
|
-
The
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
`driver_analysis -> strategy_scenarios -> strategy_proposal -> strategy_review -> reviewed_strategy_handoff`
|
|
13
|
-
|
|
14
|
-
Each Graph stops at its named handoff. Neither Graph may publish dashboard
|
|
15
|
-
content. The strategy Graph does not
|
|
9
|
+
The Graph stops at the reviewed strategy handoff and may not publish dashboard
|
|
10
|
+
content. Parallel children are independent and read-only; sequential reducer
|
|
11
|
+
nodes alone write the canonical artifacts. The strategy Graph does not
|
|
16
12
|
approve the strategy, create an official forecast, or execute the allocation.
|
|
17
13
|
|
|
18
|
-
The calling main Agent publishes the exact
|
|
14
|
+
The calling main Agent first publishes the exact `driver_analysis` through
|
|
15
|
+
`fpa_dashboard_publish_review`, then publishes the exact proposal, independent
|
|
16
|
+
review, ready handoff, and immutable scope/cycle/role through
|
|
19
17
|
`fpa_dashboard_publish_strategy`, waits for the dashboard response in the
|
|
20
18
|
originating main session, and commits it with `fpa_strategy_decision_commit`.
|
|
21
19
|
Dashboard publishing and decision commit tools are forbidden from every Graph
|
|
@@ -27,9 +25,9 @@ ready handoff plus the exact confirmed strategy-decision fingerprint:
|
|
|
27
25
|
`reviewed_strategy_handoff + strategy_decision -> forecast_plan -> approved_cycle_forecast`
|
|
28
26
|
|
|
29
27
|
The main Agent owns approval recording; the forecast Graph owns deterministic
|
|
30
|
-
composition and artifact freezing. A rejected approval
|
|
31
|
-
`fpa-strategy-planning`
|
|
32
|
-
place.
|
|
28
|
+
composition and artifact freezing. A rejected approval reruns
|
|
29
|
+
`fpa-strategy-planning` with the exact feedback and produces a new version
|
|
30
|
+
rather than modifying the reviewed proposal in place.
|
|
33
31
|
|
|
34
32
|
Execution is a separate `fpa-strategy-execution` workflow:
|
|
35
33
|
|
|
@@ -84,11 +84,23 @@ tool. `complete_with_limits` remains publishable when its limitations are
|
|
|
84
84
|
explicit, while `blocked` is not. Do not hide a real defect to get through the
|
|
85
85
|
gate.
|
|
86
86
|
|
|
87
|
+
Upstream identity or coverage defects are non-blocking data limits. Preserve
|
|
88
|
+
the full approved allocation, leave affected revenue and ROAS values `NULL`,
|
|
89
|
+
and let `fpa_forecast_compose` emit `data_quality`, a coverage-labelled partial
|
|
90
|
+
`conclusion`, and actionable repair items. Never delete a bad slice, turn it
|
|
91
|
+
into zero spend, or renormalize the remaining allocation. The affected slice
|
|
92
|
+
remains ineligible for Actuals comparison and execution until its mapping is
|
|
93
|
+
fixed. Approval mismatch, duplicate or negative allocation, budget mismatch,
|
|
94
|
+
invalid period/currency/role, and unauthorized execution remain blocking
|
|
95
|
+
governance failures.
|
|
96
|
+
|
|
87
97
|
## Boundaries
|
|
88
98
|
|
|
89
99
|
- Do not optimize, revise, or substitute the approved strategy while forecasting.
|
|
90
100
|
- A required change invalidates the current approval and routes back to recommendation and review.
|
|
91
101
|
- Unsupported KPIs remain `NULL` with a reason.
|
|
102
|
+
- A partial conclusion must say it covers only calculable slices and must show
|
|
103
|
+
`calculable_spend_pct`; it must never be labelled portfolio ROAS.
|
|
92
104
|
- Do not execute the strategy and do not start continuous monitoring.
|
|
93
105
|
|
|
94
106
|
## Completion
|
|
@@ -41,6 +41,28 @@ calibration_policy:
|
|
|
41
41
|
policy_version: string
|
|
42
42
|
unsupported_metrics: []
|
|
43
43
|
reconciliation_checks: []
|
|
44
|
+
data_quality:
|
|
45
|
+
status: complete | partial | unavailable
|
|
46
|
+
planned_spend: number
|
|
47
|
+
calculable_spend: number
|
|
48
|
+
calculable_spend_pct: number # 0..1; never renormalized
|
|
49
|
+
excluded_spend: number
|
|
50
|
+
issue_count: number
|
|
51
|
+
issues:
|
|
52
|
+
- issue_id: string
|
|
53
|
+
code: slice_key_not_in_actuals
|
|
54
|
+
severity: warning
|
|
55
|
+
slice: {app_id: string, store: string, channel_group: string}
|
|
56
|
+
affected_metrics: [actuals_comparison, revenue, roas, execution]
|
|
57
|
+
disposition: excluded_from_calculation
|
|
58
|
+
evidence: []
|
|
59
|
+
remediation: string
|
|
60
|
+
owner_role: data_steward
|
|
61
|
+
conclusion:
|
|
62
|
+
status: available | available_with_limits | unavailable
|
|
63
|
+
scope: portfolio | calculable_slices | none
|
|
64
|
+
metrics: {spend: scenario_metric, revenue: scenario_metric, roas: scenario_metric}
|
|
65
|
+
warning: string | null
|
|
44
66
|
frozen_at: timestamp
|
|
45
67
|
```
|
|
46
68
|
|
|
@@ -97,7 +119,10 @@ Rules the plan has to respect, because compose enforces them:
|
|
|
97
119
|
|
|
98
120
|
- **Spend is a decision, not a prediction.** It is identical in all three scenarios, so a slice carries one `approved_spend`. Only revenue moves, through `roas`.
|
|
99
121
|
- **A stopped slice has no ROAS.** `approved_spend: 0` means revenue 0 and `roas` null in all three scenarios — the contract derives ROAS as revenue/spend and calls a zero denominator null.
|
|
100
|
-
- **Slice keys
|
|
122
|
+
- **Slice keys are checked as real triples.** `app_code`, `platform`, and `media_source` must occur together in `ua_spend`; validating three independent value lists is insufficient. A mismatch is isolated as a data-quality limit: approved spend remains in the allocation and consolidated spend, while affected revenue/ROAS are `NULL`. The single-placeholder App axis for a scoped-out portfolio remains permitted.
|
|
123
|
+
- **Do not hide partiality.** Compose reports planned, calculable, and excluded spend. Its partial conclusion covers only calculable slices; remaining spend is never scaled to 100%, and partial ROAS is never labelled portfolio ROAS.
|
|
124
|
+
- **Data quality does not weaken governance.** Missing/mismatched approval, duplicate or negative allocation, invalid period/currency/forecast role, and budget reconciliation failures still block.
|
|
125
|
+
- **Describe other upstream limits actionably.** For non-identity defects, each `unsupported_metrics` item should name the affected metric/scope, evidence, remediation, and data owner. Dashboard publication keeps these items visible even when `data_quality.status` is otherwise complete.
|
|
101
126
|
- **`status` and `unsupported_metrics` must agree.** `complete` requires an empty list; `complete_with_limits` requires a non-empty one. Scope excluded upstream is neither.
|
|
102
127
|
- **Do not hand-compute anything derived.** A ROAS rounded to four decimals misses the commit tolerance and costs a re-draft.
|
|
103
128
|
|
|
@@ -12,7 +12,7 @@ Load `$fpa-apply-core-rules` first. Recommend one plan while keeping alternative
|
|
|
12
12
|
1. Consume `planning_brief`, `driver_analysis`, and `strategy_scenarios`.
|
|
13
13
|
2. Remove scenarios that breach hard constraints.
|
|
14
14
|
3. Rank remaining scenarios using the objective priorities and declared trade-off rule.
|
|
15
|
-
4. Select one recommendation and specify exact allocation, changes from baseline, expected ranges, assumptions, and risks.
|
|
15
|
+
4. Select one recommendation and specify exact allocation, an explicit `grow | hold | cut | stop` action for every App/store/channel row, changes from baseline, expected ranges, assumptions, and risks.
|
|
16
16
|
5. State why rejected alternatives were not chosen.
|
|
17
17
|
6. Define next-cycle evaluation thresholds; do not create a real-time monitoring obligation.
|
|
18
18
|
7. Write `strategy_proposal` using [artifact-contract.md](references/artifact-contract.md).
|
|
@@ -12,6 +12,7 @@ allocation:
|
|
|
12
12
|
- app_id: string
|
|
13
13
|
store: string
|
|
14
14
|
channel_group: string
|
|
15
|
+
action: grow | hold | cut | stop
|
|
15
16
|
spend: number
|
|
16
17
|
change_from_baseline: number
|
|
17
18
|
expected_outcomes:
|
|
@@ -27,4 +28,4 @@ next_cycle_evaluation_thresholds: []
|
|
|
27
28
|
required_human_decisions: []
|
|
28
29
|
```
|
|
29
30
|
|
|
30
|
-
The total allocation must reconcile to the proposed total budget, and every allocation row must map to a simulated scenario row.
|
|
31
|
+
The total allocation must reconcile to the proposed total budget, and every allocation row must map to a simulated scenario row. `action` is explicit and mandatory: use `grow` for a budget increase, `hold` for an unchanged allocation, `cut` for a non-zero reduction, and `stop` when the slice is removed or held at zero under a stop-loss decision.
|
|
@@ -22,10 +22,13 @@ preserve every other module revision.
|
|
|
22
22
|
|
|
23
23
|
1. After the analysis Graph returns `driver_analysis`, preview then publish
|
|
24
24
|
`period-review` with `fpa_dashboard_publish_review`.
|
|
25
|
-
2. After the strategy Graph returns the exact `strategy_proposal
|
|
26
|
-
`reviewed_strategy_handoff`, preview then publish
|
|
27
|
-
`fpa_dashboard_publish_strategy`.
|
|
28
|
-
the
|
|
25
|
+
2. After the strategy Graph returns the exact `strategy_proposal`, independent
|
|
26
|
+
`strategy_review`, and `reviewed_strategy_handoff`, preview then publish
|
|
27
|
+
`next-strategy` with `fpa_dashboard_publish_strategy`. Supply all three paths
|
|
28
|
+
and the exact `scope_id`, `cycle_id`, and `forecast_role`; the tool verifies
|
|
29
|
+
fingerprints, review independence, opinion, conditions, and next-stage
|
|
30
|
+
binding. Publication binds its decision action to the current main session;
|
|
31
|
+
never copy or expose a session id in dashboard data.
|
|
29
32
|
3. Stop and wait for the dashboard action. The Web host sends a canonical
|
|
30
33
|
decision message back to the bound original session. In that session call
|
|
31
34
|
`fpa_strategy_decision_commit` with the exact `action_id`.
|
|
@@ -23,3 +23,25 @@ reviewed_at: timestamp
|
|
|
23
23
|
```
|
|
24
24
|
|
|
25
25
|
Set `independence_confirmed: false` and `status: blocked` if the reviewer also authored the proposal. Any unresolved critical finding requires `reject`.
|
|
26
|
+
|
|
27
|
+
# `reviewed_strategy_handoff` contract
|
|
28
|
+
|
|
29
|
+
```yaml
|
|
30
|
+
kind: fpa.reviewed-strategy-handoff
|
|
31
|
+
status: ready | blocked
|
|
32
|
+
scope_id: string
|
|
33
|
+
cycle_id: string
|
|
34
|
+
forecast_role: string
|
|
35
|
+
strategy_version: string
|
|
36
|
+
reviewed_strategy_version: string
|
|
37
|
+
proposal_fingerprint: sha256
|
|
38
|
+
review_fingerprint: sha256
|
|
39
|
+
reviewer_identity: string
|
|
40
|
+
independence_confirmed: true
|
|
41
|
+
review_opinion: support | support_with_conditions
|
|
42
|
+
review_conditions: []
|
|
43
|
+
review_residual_risks: []
|
|
44
|
+
next_graph: fpa-forecast-freeze
|
|
45
|
+
```
|
|
46
|
+
|
|
47
|
+
`strategy_version` and `reviewed_strategy_version` must be identical and must bind the exact proposal reviewed. A rejected or non-independent review cannot produce a ready handoff.
|
|
@@ -1,10 +0,0 @@
|
|
|
1
|
-
{
|
|
2
|
-
"name": "fpa-period-analysis",
|
|
3
|
-
"version": "1.0.0",
|
|
4
|
-
"start": "plan_cycle",
|
|
5
|
-
"nodes": [
|
|
6
|
-
{ "id": "plan_cycle", "type": "subagent", "agentName": "plan_cycle", "next": "diagnose_actuals", "skills": ["fpa-plan-cycle"], "tools": ["read", "write", "fpa_data_catalog"], "prompt": "规划精确周期、范围、指标与边界;不得推荐策略或调用仪表盘工具。" },
|
|
7
|
-
{ "id": "diagnose_actuals", "type": "subagent", "agentName": "diagnose_actuals", "next": "analyze_drivers", "skills": ["fpa-diagnose-actuals"], "tools": ["read", "write", "fpa_data_catalog", "fpa_query"], "prompt": "诊断 Actuals 完整性并写入工件;不得调用仪表盘工具。" },
|
|
8
|
-
{ "id": "analyze_drivers", "type": "subagent", "agentName": "analyze_drivers", "skills": ["fpa-analyze-drivers"], "tools": ["read", "write", "fpa_query", "fpa_calc"], "prompt": "分析上周期驱动因素并写 artifacts/driver_analysis.json;不得推荐策略或调用仪表盘工具。" }
|
|
9
|
-
]
|
|
10
|
-
}
|
|
@@ -1,11 +0,0 @@
|
|
|
1
|
-
{
|
|
2
|
-
"name": "fpa-strategy-recommendation",
|
|
3
|
-
"version": "1.0.0",
|
|
4
|
-
"start": "simulate_strategies",
|
|
5
|
-
"nodes": [
|
|
6
|
-
{ "id": "simulate_strategies", "type": "subagent", "agentName": "simulate_strategies", "next": "recommend_strategy", "skills": ["fpa-simulate-strategies"], "tools": ["read", "write", "fpa_query", "fpa_calc"], "prompt": "根据分析工件试算候选策略;不得批准、预测或发布仪表盘。" },
|
|
7
|
-
{ "id": "recommend_strategy", "type": "subagent", "agentName": "recommend_strategy", "next": "review_strategy", "skills": ["fpa-recommend-strategy"], "tools": ["read", "write"], "prompt": "形成完整策略提案;不得自我批准或发布仪表盘。" },
|
|
8
|
-
{ "id": "review_strategy", "type": "subagent", "agentName": "review_strategy", "next": "prepare_handoff", "skills": ["fpa-review-strategy"], "tools": ["read", "write", "fpa_calc"], "prompt": "独立复核策略并写审核工件;不得批准或发布仪表盘。" },
|
|
9
|
-
{ "id": "prepare_handoff", "type": "subagent", "agentName": "prepare_handoff", "tools": ["read", "write"], "prompt": "仅在审核通过时形成 reviewed_strategy_handoff;停止,不批准、不预测、不发布仪表盘。" }
|
|
10
|
-
]
|
|
11
|
-
}
|