# Build Generation Workflow
This document describes the internal workflow the agent follows when generating a build. It sits between:
- **User layer** ([interaction.md](./interaction.md)) - how users provide input and receive output
- **PoB layer** ([pob-integration.md](./pob-integration.md)) - how builds are constructed and validated
## 1. Invariant Extraction
The first step transforms a user's freeform prompt into structured constraints (class, ascendancy, damage type, goals, etc.) with provenance tracking (explicit, inferred, default).
Single-shot extraction — the LLM parses the prompt and outputs structured invariants in one pass, flagging at most one critical ambiguity. See [prompts/invariant-extraction.md](./prompts/invariant-extraction.md) for the full prompt template and examples.
---
## 2. Modes
The workflow operates in different modes depending on context. Mode determines entry point and exploration budget.
| **Initial** | New build request | decompose | Minimal — use defaults, validate quickly |
| **Refinement** | User asks to improve specific aspect | explore (targeted sub-problems) | Focused — compare 2-4 realistic options |
| **Strategic** | User asks for fundamental change | decompose (rethink intent) | Deep — may rebuild significant portions |
See [exploration-model.md](./exploration-model.md) for detailed mode behavior and guidelines on when to experiment vs decide directly.
---
## 3. BuildState
The agent maintains a `BuildState` structure during generation. This is internal working state, distinct from:
- **Invariants** - user-facing constraints that persist across refinements
- **PoB XML** - the final build output
The structure tracks **7 sub-problems** (questions to answer), where each sub-problem's answer draws from multiple **solution spaces** (mechanisms). See [sub-problems/index.md](./sub-problems/index.md) for the framework.
### Status Values
| `pending` | Not yet addressed |
| `exploring` | Generating candidates |
| `decided` | Solution chosen (may not be validated yet) |
| `blocked` | Waiting on dependency or conflict resolution |
### Status Transitions
```
+----------------------------------+
| |
v |
pending --> exploring --> decided ------+
| (conflict invalidates)
|
v
blocked
|
| (deps resolved)
v
exploring
```
- `pending -> exploring`: Sub-problem work begins
- `exploring -> decided`: Solution chosen
- `exploring -> blocked`: Dependencies not yet satisfied
- `blocked -> exploring`: Dependencies resolved
- `decided -> exploring`: Conflict requires re-evaluation (iteration)
### Phase Transitions
```
+------------------------------------------------+
| |
START --> decompose --> explore --> construct --> validate --> complete
^ |
| | (conflicts found)
| v
+-------------------- iterate
```
**decompose:** Parse invariants, identify which sub-problems are pre-decided (e.g., ascendancy from user prompt), set dependencies.
**explore:** For each sub-problem (respecting dependencies), generate candidates and make intent-level decisions. Phase ends when all sub-problems have `decided` status. This phase uses domain knowledge and static data — it does not build anything in PoB.
**construct:** Translate intent into a concrete build in PoB. Allocate passives, equip gear, socket gems. Where decisions can't be validated without simulation (e.g., passive tree pathing), run experiments to compare options. See [exploration-model.md](./exploration-model.md) for experiment patterns and iterative deepening.
**validate:** Run quality checks against the constructed build. Rule-based checks (res capped, enough life, DPS thresholds) plus LLM assessment (content fit, overall coherence). Transitions to `complete` (no conflicts) or `iterate` (conflicts found).
**iterate:** Analyze conflicts, adjust decisions, mark affected sub-problems as `exploring` again. Returns to `explore`.
**complete:** Build is valid. State can be presented to user.
### PoB's Dual Role
PoB participates in two phases for different purposes:
| **construct** | Simulator | Build the thing, run experiments, compare options |
| **validate** | Validator | Check the result against quality bars and invariants |
During **construct**, PoB is an exploration tool — the agent proposes changes, observes results, and makes evidence-based decisions. During **validate**, PoB is a gatekeeper — the agent checks whether the final build meets requirements.
For the full `BuildState` YAML structure and evolution examples, see [state-examples.md](./state-examples.md).
---
## 4. Reasoning Step Prompts
Four phases drive build generation: **decompose**, **explore**, **construct**, and **validate**. Each has distinct responsibilities and prompt structures.
### Design Principles
1. **Domain injection** - Prompts reference `{domain:file}` placeholders filled at runtime from `docs/domain/`
2. **Structured output** - YAML responses matching `BuildState` schema
3. **Explicit unknowns** - Where domain knowledge is incomplete, prompts note "best effort" behavior
### Prompt Templates
Each phase has its own prompt file:
| Decompose | [prompts/decompose.md](./prompts/decompose.md) | Initialize BuildState from invariants |
| Explore (generic) | [prompts/explore.md](./prompts/explore.md) | Generate candidates, select best option (intent) |
| Explore (per sub-problem) | [prompts/explore-{name}.md](./prompts/) | Sub-problem-specific context and queries |
| Construct | [exploration-model.md](./exploration-model.md) | Build in PoB, run experiments for unclear decisions |
| Validate | [prompts/validate.md](./prompts/validate.md) | Rule-based + LLM checks, conflict detection |
| Iterate | [prompts/iterate.md](./prompts/iterate.md) | Conflict resolution, sub-problem re-opening |
### Prompt Chaining Summary
```
Invariant Extraction (§1)
|
v
+---------+
|Decompose| --- sets up BuildState
+----+----+
|
v
+---------------------------------------------+
| Explore Loop (intent) |
| for each ready sub-problem: |
| 1. Pre-gather data -> discoveries |
| 2. Run explore prompt (LLM reasons) |
| 3. Record intent decision + alternatives |
+----+-----------------------------------------+
| (all decided)
v
+---------------------------------------------+
| Construct (PoB) |
| Translate intent into concrete build: |
| 1. Apply decisions to PoB |
| 2. Where unclear → run experiments |
| 3. Interpret results → refine decisions |
| See exploration-model.md for details |
+----+-----------------------------------------+
|
v
+---------+
|Validate | --- rule checks + LLM assessment
+----+----+
|
conflicts? --yes--> Iterate: mark stale discoveries,
| re-open affected sub-problems
| +---> back to Explore
no
v
Complete --> Present to user
```
### Domain Injection Points
The prompts reference domain knowledge via `{domain:filename}` placeholders. Current state:
| `scaling.md` | Exists | damage_delivery, supports, tree, gear |
| `defenses.md` | Exists | survivability, tree, gear, validate |
| `skills.md` | TODO | damage_delivery, supports |
| `classes.md` | TODO | ascendancy, tree |
| `uniques.md` | TODO | gear |
| `runes.md` | TODO | gear, stat_requirements |
| `solution-budgets.md` | TODO | all sub-problems (quick reference) |
| `dependency_rules.md` | TODO | decompose (conditional dependencies) |
**Fallback behavior:** When a domain file doesn't exist, the prompt proceeds without it. The LLM uses general knowledge (which may be outdated or PoE1-based). Flag in output: `domain_gaps: [missing files]`.
For solution space budgets, see [sub-problems/index.md](./sub-problems/index.md#solution-space-budgets).
---
## 5. Conflict Detection
Conflicts surface at two points, each with different detection mechanics.
### Construct-Time Detection
Experiments during construct may reveal that intent doesn't translate to reality. The agent's response depends on severity:
- **Core assumption invalidated** (skill doesn't function as intended, ascendancy node unavailable) → halt construct, create blocking conflict, iterate immediately
- **Gap another sub-problem may cover** (tree pathing tight but gear not finalized, resist short but flask slots open) → note as provisional conflict, continue constructing
- **Shortfall within tolerances** (ES 10% below target, one resist slightly short) → note, validate will catch if unresolved
Provisional conflicts carry forward to validate. If the completed build resolves them (other sub-problems compensated), they're dropped.
### Validate-Time Detection
Systematic checks on the fully constructed build:
- **Rule-based** — quantitative thresholds per sub-problem (DPS, EHP, resists, mana sustain, Spirit balance, attribute requirements, etc.)
- **Qualitative** — LLM assessment of goal alignment, internal consistency, practical concerns
See [prompts/validate.md](./prompts/validate.md) for check tables, conflict types, and severity definitions.
### Cross-Sub-Problem Budget Checks
Per-sub-problem checks can all pass individually while the aggregate fails. Budget checks detect conflicts that only emerge when solutions are combined:
| Tree point overflow | Allocated points > 123 | damage_delivery, survivability |
| Gear slot contention | Incompatible mod requirements on same slot | competing sub-problems |
| Attribute squeeze | Support color total > attribute/5 | stat_requirements, damage_delivery |
| Spirit overflow | Total reservations > Spirit pool | spirit_allocation |
These run during validate alongside per-sub-problem checks.
### Conflict Dependency Analysis
Before entering resolution, the agent identifies root causes vs symptoms:
1. **Map chains** — if stat_requirement failure prevents equipping a weapon, that causes a downstream damage_gap. Root: stat_requirements.
2. **Group shared-root conflicts** — multiple conflicts caused by the same decision get resolved together.
3. **Tag** each conflict as `root` or `symptom`. Symptoms don't get independent resolution attempts — they're expected to resolve when their root is fixed.
This analysis feeds directly into resolution priority ordering (§6).
---
## 6. Conflict Resolution
When blocking conflicts exist, the iterate phase resolves them. Full resolution logic and prompt template in [prompts/iterate.md](./prompts/iterate.md).
### Priority Ordering
Multiple conflicts are resolved in this order:
1. **Blocking before warning** — warnings don't trigger iteration
2. **Root before symptom** — from dependency analysis (§5). Symptoms may resolve automatically
3. **Shared-root grouping** — same root cause → single resolution pass
4. **Fewer affected sub-problems first** — cheaper resolutions yield faster progress and may simplify remaining conflicts
### Resolution Flow
For each conflict (or conflict group):
1. Select strategy from `suggested_solutions` (least-disruptive first)
2. Re-open only the affected sub-problems (status → `exploring`)
3. Inject conflict context as constraints on re-exploration
4. Preserve prior attempt so explore avoids the same solution
5. Mark dependent discoveries stale
### Limits and Escalation
| Per-conflict attempts | 3 | Try next `suggested_solution`; if exhausted, escalate |
| Global iterations | 5 | Present best attempt with caveats |
| Emergency stop | Blocking count ↑ from previous iteration | Backtrack to snapshot |
When limits are reached, present the build with unresolved conflicts, what was tried, and suggested manual adjustments. See [interaction.md](./interaction.md) for intermediate presentation.
---
## 7. Example Walkthrough
See [walkthrough-cold-dot.md](./walkthrough-cold-dot.md) for a complete end-to-end trace of **"cold DoT occultist for bossing"** through every phase: invariant extraction → decompose → explore → construct → validate → iterate (mana conflict) → re-validate → complete.
---
## Related Documents
- [interaction.md](./interaction.md) - User interaction model
- [reasoning-model.md](./reasoning-model.md) - High-level reasoning loop
- [sub-problems/index.md](./sub-problems/index.md) - Build sub-problems
- [exploration-model.md](./exploration-model.md) - Construct phase: PoB simulation, experiments, iterative deepening
- [state-examples.md](./state-examples.md) - BuildState YAML examples and evolution
- [walkthrough-cold-dot.md](./walkthrough-cold-dot.md) - Complete example walkthrough
## Related Systems
- [Learning System](../../.project/systems/learning-system.md) - How the agent persists knowledge (scored lists, soft invariants, eliminations)
- [Skill System](../../.project/systems/skill-system.md) - Agent capabilities and opportunity cost reasoning
- [Architecture](../../.project/systems/architecture.md) - Port/adapter patterns for persistence