alphacouncil-agent 1.0.3 → 1.0.13

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.
Files changed (81) hide show
  1. package/.claude/agents/alphacouncil-insider_sec.md +19 -0
  2. package/.claude/commands/alpha.md +48 -19
  3. package/.claude-plugin/marketplace.json +2 -2
  4. package/.claude-plugin/plugin.json +1 -1
  5. package/.codex-plugin/plugin.json +1 -1
  6. package/.grok/agents/alphacouncil-insider_sec.md +19 -0
  7. package/.grok/commands/alpha.md +48 -19
  8. package/.opencode/agent/alphacouncil-insider_sec.md +19 -0
  9. package/.opencode/command/alpha.md +48 -19
  10. package/CHANGELOG.md +307 -0
  11. package/CLAUDE.md +55 -13
  12. package/README.ja.md +42 -16
  13. package/README.md +70 -27
  14. package/README.zh-CN.md +53 -20
  15. package/SECURITY.md +11 -1
  16. package/commands/alpha.md +48 -19
  17. package/data/build-profile.v1.json +1 -1
  18. package/docs/INSTALL.md +9 -6
  19. package/docs/examples/final_report.SOX.zh.md +442 -0
  20. package/docs/report-contract.md +27 -3
  21. package/knowledge/ai-assisted-solo/experiments/runs/a.json +4 -4
  22. package/knowledge/ai-assisted-solo/experiments/runs/b.json +2 -2
  23. package/knowledge/ai-assisted-solo/experiments/runs/c.json +2 -2
  24. package/knowledge/ai-assisted-solo/experiments/runs/d13.json +16 -16
  25. package/knowledge/ai-assisted-solo/experiments/runs/d26.json +30 -30
  26. package/knowledge/ai-assisted-solo/experiments/runs/e-d13.json +19 -19
  27. package/knowledge/ai-assisted-solo/experiments/runs/e-d26.json +33 -33
  28. package/knowledge/ai-assisted-solo/experiments/runs/h_ai_reference.json +34 -34
  29. package/knowledge/ai-assisted-solo/experiments/simulation-input.json +84 -84
  30. package/knowledge/ai-assisted-solo/experiments/simulation-manifest.json +19 -19
  31. package/knowledge/solo-test/masters/master_ackman/manifest.json +8 -8
  32. package/knowledge/solo-test/masters/master_aschenbrenner/manifest.json +8 -8
  33. package/knowledge/solo-test/masters/master_asness/manifest.json +8 -8
  34. package/knowledge/solo-test/masters/master_bogle/manifest.json +8 -8
  35. package/knowledge/solo-test/masters/master_buffett/manifest.json +8 -8
  36. package/knowledge/solo-test/masters/master_burry/manifest.json +8 -8
  37. package/knowledge/solo-test/masters/master_cathie_wood/manifest.json +8 -8
  38. package/knowledge/solo-test/masters/master_dalio/manifest.json +8 -8
  39. package/knowledge/solo-test/masters/master_damodaran/manifest.json +8 -8
  40. package/knowledge/solo-test/masters/master_druckenmiller/manifest.json +8 -8
  41. package/knowledge/solo-test/masters/master_duan_yongping/manifest.json +8 -8
  42. package/knowledge/solo-test/masters/master_fisher/manifest.json +8 -8
  43. package/knowledge/solo-test/masters/master_forensic_short/manifest.json +8 -8
  44. package/knowledge/solo-test/masters/master_graham/manifest.json +8 -8
  45. package/knowledge/solo-test/masters/master_jhunjhunwala/manifest.json +8 -8
  46. package/knowledge/solo-test/masters/master_klarman/manifest.json +8 -8
  47. package/knowledge/solo-test/masters/master_li_lu/manifest.json +8 -8
  48. package/knowledge/solo-test/masters/master_lynch/manifest.json +8 -8
  49. package/knowledge/solo-test/masters/master_marks/manifest.json +8 -8
  50. package/knowledge/solo-test/masters/master_munger/manifest.json +8 -8
  51. package/knowledge/solo-test/masters/master_natenberg/manifest.json +8 -8
  52. package/knowledge/solo-test/masters/master_pabrai/manifest.json +8 -8
  53. package/knowledge/solo-test/masters/master_simons/manifest.json +8 -8
  54. package/knowledge/solo-test/masters/master_sinclair/manifest.json +8 -8
  55. package/knowledge/solo-test/masters/master_soros/manifest.json +8 -8
  56. package/knowledge/solo-test/masters/master_taleb/manifest.json +8 -8
  57. package/knowledge/solo-test/masters/master_thorp/manifest.json +8 -8
  58. package/mcp/lib/constants.mjs +82 -4
  59. package/mcp/lib/council-options.mjs +8 -4
  60. package/mcp/lib/council-selection.mjs +79 -1
  61. package/mcp/lib/fundamentals.mjs +50 -10
  62. package/mcp/lib/gates.mjs +42 -0
  63. package/mcp/lib/grounding.mjs +27 -1
  64. package/mcp/lib/industry.mjs +9 -1
  65. package/mcp/lib/markdown.mjs +25 -1
  66. package/mcp/lib/orchestrator.mjs +187 -24
  67. package/mcp/lib/personas/engine.mjs +57 -12
  68. package/mcp/lib/personas-v3/runtime.mjs +28 -0
  69. package/mcp/lib/prompts.mjs +72 -3
  70. package/mcp/lib/rpc.mjs +93 -7
  71. package/mcp/lib/run-store.mjs +3 -0
  72. package/mcp/lib/screen.mjs +46 -46
  73. package/mcp/lib/sec.mjs +25 -10
  74. package/mcp/lib/voice-from-decision.mjs +13 -5
  75. package/mcp/lib/weights.mjs +9 -2
  76. package/mcp/lib/xbrl-series.mjs +31 -5
  77. package/package.json +2 -1
  78. package/personas/analysts/insider_sec.md +38 -0
  79. package/scripts/lib/persona-v3-solo-test-packs.mjs +14 -8
  80. package/scripts/review-persona-v3-solo-formulas.mjs +5 -3
  81. package/skills/alphacouncil-agent/SKILL.md +80 -19
@@ -55,6 +55,25 @@
55
55
  四、**股权稀释**
56
56
  在外流通股数的多年变化。持续稀释会让每股口径的所有增长打折,而这一点在讨论增长时常被忽略。
57
57
 
58
+ ## 怎么取到原文(EDGAR 会限流,这一节决定这个席位有没有真凭据)
59
+
60
+ EDGAR 对没有描述性 User-Agent 的客户端返回 **HTTP 429**,而且 `www.sec.gov` 比 `data.sec.gov` 限得更狠。**连续换 URL 猛试只会让限流变严**——一次真实运行里连试 8 个不同 URL 全部 429,最后一份原文都没读到。
61
+
62
+ 按这个顺序取,取到就停:
63
+
64
+ 1. `https://data.sec.gov/submissions/CIK##########.json`(10 位补零)—— 申报索引,JSON API 最宽容,一次拿到全部表单类型、accession 与 filed date。
65
+ 2. `https://data.sec.gov/api/xbrl/companyfacts/CIK##########.json` —— 股数、股东权益这类 XBRL 数字。
66
+ 3. `https://www.sec.gov/Archives/edgar/data/<无前导零CIK>/<去横线accession>/<主文档>` —— 具体那一份 Form 4 / 8-K 原文。
67
+ 4. EDGAR 全文检索与 `cgi-bin/browse-edgar` **放到最后**:它们最容易被限流,且能给的信息前三步都能给。
68
+
69
+ 遇到 429:**停下来等几秒再重试同一个 URL**,不要立刻换别的 URL。同一份文档最多重试三次;三次都 429 就记为取回失败,进入下面的降级纪律。
70
+
71
+ **降级纪律(必须照做,不许含糊)**:一份原文都没读到时,
72
+ - `summary` 第一句就写明「本包未直读任何 EDGAR 原文,全部内容经二级来源交叉核实」;
73
+ - `confidence` 最高只能是 `low`;
74
+ - 在 `open_questions` 里逐条列出失败的 URL 与状态码;
75
+ - 每条来自镜像/聚合站的内容都标注它是二手,**绝不能把镜像内容写成「已按申报原文核实」**。
76
+
58
77
  ## 硬纪律
59
78
 
60
79
  - **每条必须带申报链接和申报日期**(filed date,不是期间结束日)。
@@ -87,6 +106,25 @@ Key items: 1.01 material agreement, 2.02 results, 4.01 auditor change, 4.02 prio
87
106
  4. **Dilution**
88
107
  Shares outstanding across several years. Persistent dilution discounts every per-share growth figure, and that is routinely ignored in growth discussions.
89
108
 
109
+ ## How to actually retrieve the filings (EDGAR throttles; this section decides whether this seat has primary evidence at all)
110
+
111
+ EDGAR answers **HTTP 429** to a client without a descriptive User-Agent, and `www.sec.gov` is throttled harder than `data.sec.gov`. **Rapidly trying different URLs makes the throttling worse, not better** -- on one real run eight different URLs were tried in a row, all returned 429, and not a single filing was read.
112
+
113
+ Retrieve in this order and stop as soon as you have what you need:
114
+
115
+ 1. `https://data.sec.gov/submissions/CIK##########.json` (CIK zero-padded to ten digits) -- the filing index. The most tolerant endpoint, and one call returns every form type, accession number and filed date.
116
+ 2. `https://data.sec.gov/api/xbrl/companyfacts/CIK##########.json` -- XBRL numbers such as share count and stockholders' equity.
117
+ 3. `https://www.sec.gov/Archives/edgar/data/<CIK without leading zeros>/<accession without dashes>/<primary document>` -- the specific Form 4 or 8-K text.
118
+ 4. EDGAR full-text search and `cgi-bin/browse-edgar` **last**: they are throttled the hardest and tell you nothing the first three cannot.
119
+
120
+ On a 429: **wait a few seconds and retry the same URL** rather than immediately switching to a different one. Retry one document at most three times; if all three are limited, record the retrieval as failed and follow the degradation rule below.
121
+
122
+ **Degradation rule (mandatory, and not to be softened)** -- when no filing was read directly:
123
+ - the first sentence of `summary` must state that no EDGAR original was read and that everything was cross-checked through secondary sources instead;
124
+ - `confidence` is capped at `low`;
125
+ - `open_questions` lists each failed URL with its status code;
126
+ - every item taken from a mirror or aggregator is labelled second-hand. **Never write mirror content as "verified against the filing".**
127
+
90
128
  ## Hard rules
91
129
 
92
130
  - **Every item carries the filing link and the filed date** -- the filed date, not the period end.
@@ -501,21 +501,27 @@ function buildDocuments({ seat, blueprint, rawTools, packVersion, formulaManifes
501
501
  ja: `${publicTitle.en} 単独テスト`,
502
502
  ko: `${publicTitle.en} 단독 테스트`,
503
503
  },
504
+ // The owner reviewed and accepted these method attributions, so the catalog title no
505
+ // longer repeats a review-status warning next to every name. The machine-verified
506
+ // admission level is unchanged and still published; the label is just the method's name.
504
507
  operator_label: {
505
- en: `${publicTitle.en} Provisional Operator Lens`,
506
- zh: `${publicTitle.zh}临时操作视角`,
507
- ja: `${publicTitle.en} 暫定オペレーター・レンズ`,
508
- ko: `${publicTitle.en} 임시 오퍼레이터 렌즈`,
508
+ en: publicTitle.en,
509
+ zh: publicTitle.zh,
510
+ ja: `${publicTitle.en}・メソッドレンズ`,
511
+ ko: `${publicTitle.en} 방법론 렌즈`,
509
512
  },
510
513
  maturity: "operator_lens",
511
514
  source_cutoff: SOURCE_DATE,
512
515
  },
513
516
  selection: {
517
+ // What a seat IS, not its review history. "Not the person's own words" stays because it
518
+ // guards against impersonation; the review-status clause is gone because the owner signed
519
+ // off on these attributions and a warning repeated 27 times stops being a warning.
514
520
  identity: {
515
- en: `${publicTitle.en}; project-derived and not human reviewed`,
516
- zh: `${publicTitle.zh};项目派生、未经人工审定`,
517
- ja: `${publicTitle.en}。プロジェクト派生で、方法帰属について人による審査を受けていない暫定オペレーター・レンズ。本人の発言や現在の見解ではない。`,
518
- ko: `${publicTitle.en}. 프로젝트에서 파생되었고 방법 귀속에 대한 인적 심사를 거치지 않은 임시 오퍼레이터 렌즈다. 본인의 발언이나 현재 견해가 아니다.`,
521
+ en: `${publicTitle.en}; a method model, not the person's own words`,
522
+ zh: `${publicTitle.zh};方法模型,非本人言论`,
523
+ ja: `${publicTitle.en}。メソッドモデルであり、本人の発言や現在の見解ではない。`,
524
+ ko: `${publicTitle.en}. 방법론 모델이며, 본인의 발언이나 현재 견해가 아니다.`,
519
525
  },
520
526
  method: {
521
527
  en: seat.method_scope.planning_hypothesis,
@@ -46,8 +46,8 @@ export function usage() {
46
46
  return [
47
47
  "Usage: node scripts/review-persona-v3-solo-formulas.mjs [--check|--plan|--write] [--json]",
48
48
  "",
49
- "--plan recompute 52 machine review records without reading the review tree",
50
- "--write write 52 reviews plus the manifest below isolated staging",
49
+ "--plan recompute the planned machine review records without reading the review tree",
50
+ "--write write every planned review plus the manifest below isolated staging",
51
51
  "--check require exact physical files and byte-stable recomputation (default)",
52
52
  "--formula-root override the physical solo-test formula tree",
53
53
  "--review-root override the isolated AI review tree",
@@ -93,7 +93,9 @@ export function main(argv = process.argv.slice(2)) {
93
93
  if (args.json) process.stdout.write(`${JSON.stringify(result, null, 2)}\n`);
94
94
  else process.stdout.write(compact(result));
95
95
  const okay = result.review_count === PLANNED_TOOL_COUNT
96
- && result.role_count === 156
96
+ // Derived, not hardcoded: the literal 156 (26 seats x 2 tools x 3 roles) survived the
97
+ // twenty-seventh seat and failed a review tree its own output line printed as 162/162.
98
+ && result.role_count === PLANNED_TOOL_COUNT * INDEPENDENT_ROLES_PER_REVIEW
97
99
  && result.mechanical_pass_count === PLANNED_TOOL_COUNT
98
100
  && result.disagreement_count === 0
99
101
  && result.semantic_unknown_count === PLANNED_TOOL_COUNT
@@ -27,8 +27,9 @@ after Stage 0.
27
27
  explicitly adds optional analyst seats, every added seat is equally mandatory. A mandatory
28
28
  evidence failure is a fail-fast barrier: persist the failure and final diagnostic artifacts,
29
29
  skip masters/debate/PM model calls, and terminate `incomplete`; do not synthesize around it.
30
- Headless full has a hard 1800000 ms queue-to-terminal-persistence ceiling. It fails closed
31
- at expiry and does not promise all-seat success when external services deteriorate.
30
+ Headless full runs at one of three depth tiers set by `council_pace`: `fast` 900000 ms,
31
+ `normal` (default) 1800000 ms, `slow` 3600000 ms, queue-to-terminal-persistence. It fails
32
+ closed at expiry and does not promise all-seat success when external services deteriorate.
32
33
  - **Quick council (`quick_v1`)**: only the plugin-managed headless `analyze_symbol` path may
33
34
  execute it. It runs the four fixed evidence roles in parallel, 1-4 selected methods in
34
35
  parallel, one parallel bull/bear statement, and one short PM inside the hard 600000 ms
@@ -70,16 +71,44 @@ can do. It does **not** create a selection session, prove that the individual ca
70
71
  displayed, or issue a receipt, so it never substitutes for the steps below.
71
72
 
72
73
  The analysts have a sensible default -- the eight-seat fan-out -- and asking about them every
73
- time is a question with an obvious answer. Master selection is the one configuration decision:
74
+ time is a question with an obvious answer. The gate takes two decisions in ONE interaction:
75
+ which methods sit on the bench, and which depth tier the run uses.
76
+
77
+ **Ask the tier; never make the user type `fast` or `slow`.** `begin_council_selection` returns
78
+ `pace_options`, one row per tier with `expected_minutes`, `hard_ceiling_minutes` and what the
79
+ extra time buys. Show it as a short menu ABOVE the seat catalog, because it is a three-option
80
+ question and the catalog is long. Publish BOTH numbers: the ceiling on its own reads as the
81
+ estimate, and then every fast run looks like it takes fifteen minutes. Render it like this, in
82
+ the run's language:
83
+
84
+ ```
85
+ 本次分析要跑多深?(默认 2)
86
+ 1. 快速 预计 ~12 分钟(上限 15) 每证据席 3.5 分钟,每轮辩论每侧 90 秒
87
+ 2. 标准 预计 ~20 分钟(上限 30) 每证据席 6 分钟,每轮辩论每侧 150 秒 ← 默认
88
+ 3. 深入 预计 ~44 分钟(上限 60) 每证据席 12 分钟,每轮辩论每侧 360 秒
89
+ 三档都是完整评议:同样 8 个证据席、同样三轮辩论、同样 PM。只有每席能想多久不同。
90
+ ```
91
+
92
+ Pass the answer as `council_pace` to `confirm_master_selection`; it binds into the receipt, so an
93
+ execution call may repeat it but never change it. If the request already said a speed, pass it as
94
+ `council_pace` to `begin_council_selection`: that is a PREFILL exactly like a named master --
95
+ highlight the row, still show the menu, still take the answer. No answer means `normal`.
96
+
97
+ Quick returns an empty `pace_options` and rejects the field: it is a smaller contract, not a
98
+ slower one. Say that plainly if a user asks for a fast quick run.
99
+
100
+ Then take this run's method selection:
74
101
 
75
102
  1. Call `begin_council_selection` with `symbol`, the original `prompt`, inferred `language`,
76
103
  the calling `host`, and the intended `council_mode` (`full` by default). If the request
77
104
  explicitly names masters, resolve their stable IDs and pass them as
78
- `preselected_master_ids`; preselection highlights only and never confirms.
79
- 2. Display **every returned master individually in the returned order**. Preserve the stable
80
- number and show `identity`, `method`, `best_for` and `maturity` for every row. A school
81
- summary, preset or seat count does not satisfy this step.
82
- 3. Take one submission. The universal fallback is a numbered text reply: one index in
105
+ `preselected_master_ids`; if it named a speed, pass `council_pace`. Both are prefills that
106
+ highlight only and never confirm.
107
+ 2. Display the `pace_options` menu with both numbers per tier, then **every returned master
108
+ individually in the returned order**. Preserve the stable number and show `identity`,
109
+ `method`, `best_for` and `maturity` for every row. A school summary, preset or seat count
110
+ does not satisfy this step.
111
+ 3. Take one submission covering both decisions. The universal fallback is a numbered text reply: one index in
83
112
  `1..N`, any comma/space-separated combination, ranges such as `1-4` or `1..4`, or stable
84
113
  IDs/names. Full also accepts `all`; quick requires 1-4 distinct methods and rejects `all`.
85
114
  - **Claude Code, Codex, OpenCode and Grok Build** may use a native multi-select when it can
@@ -94,7 +123,8 @@ time is a question with an obvious answer. Master selection is the one configura
94
123
  The obsolete rule **"Skip the question entirely"** is prohibited for council runs: a
95
124
  prefill reduces typing but never replaces this run's displayed catalog and receipt.
96
125
  5. Call `confirm_master_selection` with the exact `selection_id`, `catalog_hash`,
97
- `display_ack: true`, and exactly one of:
126
+ `display_ack: true`, the answered `council_pace` (omit to accept `normal`), and exactly one
127
+ of:
98
128
  - `selected_master_ids: [...]` for a native multi-select;
99
129
  - `select_all: true` for all in full mode only;
100
130
  - `selection: "1,4-6"` (or another supported text selection) for the fallback.
@@ -117,18 +147,44 @@ Use this contract when full runs through headless `analyze_symbol`:
117
147
  - The eight mandatory evidence roles start together. Each has one bounded parse-only repair;
118
148
  repair converts malformed output and does not repeat web research.
119
149
  - After the evidence barrier, every selected physical v3 method executes its deterministic
120
- policy and freezes its stance. Exactly one isolated voice worker is then launched for that
121
- stable ID. It may explain the recorded policy result in the user's language, but cannot
122
- change the stance, invent a typed fact or speak as the real named person. A missing voice
123
- result remains visible and prevents a false complete bench.
150
+ policy and freezes its stance. Each seat that reached a stance then gets exactly one isolated
151
+ voice worker for that stable ID. It may explain the recorded policy result in the user's
152
+ language, but cannot change the stance, invent a typed fact or speak as the real named person.
153
+ A missing voice result remains visible and prevents a false complete bench.
154
+ - A seat frozen `out_of_scope` is settled without a worker. Its deterministic statement names
155
+ the condition that closed its gate and states that an abstention is not a bearish vote, which
156
+ is all an out_of_scope seat is asked to say; `ALPHACOUNCIL_VOICE_ABSTAINING_SEATS=1` restores
157
+ a worker for every seat. Such a seat is still published with a readable statement, and its
158
+ `voice_status` is `deterministic_scope` rather than a claim that a worker ran.
159
+ - Every condition id a seat cites is resolved back to the id its pack declares. The ids are
160
+ hashed before the policy runs so the decision layer cannot recognise the seat, but past the
161
+ freeze the seat is named in the report and in its own worker prompt, so a surviving
162
+ `anon_<hash>` only stopped a seat from telling a reader which condition decided it.
124
163
  - Round 1 Bull/Bear run together; after both pass, Round 2 runs together; after both pass,
125
164
  Round 3 runs together with exact saved-question bindings. The PM starts after both Round-3
126
165
  sides pass.
127
- - The hard ceiling is 1800000 ms from durable queueing through terminal artifact persistence,
128
- including queueing, retries, all workers and deterministic finalization. A caller or
129
- environment may lower it, never raise it. At expiry persist `incomplete` and name every
166
+ - The ceiling is the selected tier's total from durable queueing through terminal artifact
167
+ persistence, including queueing, retries, all workers and deterministic finalization: `fast`
168
+ 900000 ms, `normal` 1800000 ms, `slow` 3600000 ms. A caller or environment may lower the
169
+ selected tier's budget, never raise it. At expiry persist `incomplete` and name every
130
170
  timed-out/failed/skipped role. The deadline guarantees a terminal saved run, not successful
131
171
  completion under provider/search/data degradation.
172
+ - The tier moves every per-stage cap with the total, because those caps are what bound each
173
+ worker: evidence 3.5/6/12 minutes per seat, method 1/2/4 minutes per seat, debate 90/150/360
174
+ seconds per round, PM 2/3/8 minutes. Raising `total_timeout_ms` alone buys idle time rather
175
+ than depth; the tier is what buys depth. All three tiers are `full_v2` — same eight evidence
176
+ seats, same three rounds, same PM — so a tier changes how long each seat may think, never what
177
+ the council is. Quick rejects `council_pace`.
178
+ - The tier also shapes each worker's output, and this is the part that makes `fast` fast rather
179
+ than merely short of time. A cap alone is a timeout, and the same prompt with a shorter fuse
180
+ produces a packet the worker could not finish. Since an LLM call's wall clock is dominated by
181
+ the tokens it generates, `fast` asks for the same information in less prose: at most six
182
+ arguments, one to two sentences each, citing a source ID instead of re-quoting the evidence,
183
+ no opponent recap and no methodology preamble — while every figure, every scoped source ID and
184
+ every required report section stays mandatory, and price levels and invalidation conditions may
185
+ not be compressed. Dropping an argument is acceptable at `fast`; dropping a source ID or
186
+ filling a number from memory never is. `slow` instead asks for the derivation written out step
187
+ by step with explicit falsification conditions. `normal` adds nothing.
132
188
  - The concise handoff lists every selected stable master ID, frozen stance and voice-worker
133
189
  explanation/status; all eight analyst task IDs, statuses and summaries; and a system-owned
134
190
  price snapshot with currency/time/source or an explicit unavailable-data gap.
@@ -265,8 +321,11 @@ Use MCP only when the user explicitly accepts background/headless execution, wan
265
321
  `wait_for_completion=false` when the user wants a long/short or portfolio decision saved
266
322
  under `~/.alphacouncil-agent/runs/`. This returns a small durable accepted response with
267
323
  `run_id`, `status_json`, and `events_jsonl`; acceptance does not mean the report is done.
268
- For quick, do not pass task overrides and do not request `synthesis=false`. For full, the
269
- 1800000 ms global maximum and parallel/barrier topology in the full contract above apply.
324
+ For quick, do not pass task overrides and do not request `synthesis=false`. For full, pass
325
+ `council_pace` when the user asked for a speed (fast 15 min / normal 30 / slow 60); the
326
+ selected tier's global maximum and the parallel/barrier topology in the full contract above
327
+ apply. `total_timeout_ms` above the tier's total is rejected and names the tier that allows
328
+ it.
270
329
  3. Poll `read_run(run_id)` at a bounded interval until `status.status` is terminal:
271
330
  `complete`, `degraded`, `incomplete`, `needs_verification`, `needs_revision`, or `failed`.
272
331
  Surface meaningful phase changes, not every unchanged poll. Poll the same `run_id`; never
@@ -320,6 +379,8 @@ Detect the user's language from their request and propagate it to EVERY subagent
320
379
  ### Stage 0 — Plan (envelope only)
321
380
  Call `plan_visible_run` with `symbol`, `prompt` (original user request), `as_of`, inferred `language`, `council_mode: "full"`, and the Stage 0 `selection_receipt`. It returns `run_id`, the planned evidence agent specs, the selected master specs, the 3 debate agent specs, and artifact paths. This is planning only (SKILL step 9); do not treat it as execution. The tool rejects `council_mode: "quick"`.
322
381
 
382
+ Every planned prompt is written to `<run>/prompts/` and each agent spec carries `prompt_file`. Check `prompts_inline`: when it is `false` the prompt bodies were deliberately left out of the result, because returning them together would exceed what a host accepts, and you must `Read` each `prompt_file` instead of the inline field. What drives that size is the grounding each prompt embeds rather than the seat count, so a run with a full macro series crosses the budget where a sparse one does not. A truncated or rejected plan result is never a reason to write prompts from memory.
383
+
323
384
  ### Stage 1 — Evidence fan-out (one turn, isolated context)
324
385
  In a SINGLE assistant turn, emit one `Task` (subagent_type: general-purpose) call for every evidence role returned by the plan. The default eight are `market_data`, `earnings_deep_dive`, `forward_expectations`, `quant_factor`, `valuation_long_short`, `news_industry_management`, `insider_sec`, and `ib_event_analysis`. Each subagent:
325
386
  - May use ONLY `WebSearch` + `WebFetch`. It must NOT call `@alphacouncil-agent`, `collect_evidence`, `analyze_symbol`, or `read_run` (leaf-worker rule, Boundaries).
@@ -353,7 +414,7 @@ Run the documented rounds, each as a parallel fan-out of `bull_researcher` + `be
353
414
  Persist each round via `record_visible_decision(run_id, role, packet)` so `all_agents.md` accumulates the full trace. DISPUTED/UNVERIFIABLE claims may appear in a thesis only with an explicit caveat.
354
415
 
355
416
  ### Stage 4 — Verdict + synthesize
356
- Run one `portfolio_manager` `Task` fed the verified evidence plus all three debate rounds. Record it via `record_visible_decision(run_id, 'portfolio_manager', packet)`, which writes `decision.json` + `final_report.md` and marks the run complete. A successful PM response has `handoff_contract=inline_user_response_v1` and returns `user_response_markdown`; use that Markdown as the final user-facing response body instead of replacing it with a shorter recap. Its last section is the exact selected-seat count and one readable method statement per seat, including deterministic `out_of_scope` statements. Then link the complete report and audit artifacts in an appendix. The saved full report still contains the Analyst Work Log, Bull/Bear Debate record, verification ledger, all mandated sections, data gaps, horizons and `<task>:<source_id>` source table.
417
+ Run one `portfolio_manager` `Task` fed the verified evidence plus all three debate rounds. Its packet MUST carry `report_markdown` as the complete report body with every authored contract section; the tool rejects a packet that does not, before taking the idempotency lock, and the rejection lists each missing section with the heading to use. Do not send a PM packet without it and expect the report to be assembled from the summary. The master bench and any instrument-structure section are system-appended and are never asked of you. Record it via `record_visible_decision(run_id, 'portfolio_manager', packet)`, which writes `decision.json` + `final_report.md` and marks the run complete. A successful PM response has `handoff_contract=inline_user_response_v1` and returns `user_response_markdown`; use that Markdown as the final user-facing response body instead of replacing it with a shorter recap. Its last section is the exact selected-seat count and one readable method statement per seat, including deterministic `out_of_scope` statements. Then link the complete report and audit artifacts in an appendix. The saved full report still contains the Analyst Work Log, Bull/Bear Debate record, verification ledger, all mandated sections, data gaps, horizons and `<task>:<source_id>` source table.
357
418
 
358
419
  Honest limits: Task fan-out is best-effort, not a guaranteed workflow engine; enforce the barrier by polling artifacts, not by assuming. WebSearch/WebFetch is the only evidence channel (no financial API), so some numeric claims stay "narratively corroborated, not vendor-verified". This is the same auditable contract as the other paths — a stronger runner, not a different audit story.
359
420