State Enforcement (v2.0):
- .state file as single source of truth for task phase
- Approval gates for research, decomposition, design, test_design
- status.py --transition refuses illegal phase transitions
- status.py --validate-folder detects out-of-order artifacts
- status.py --audit checks all tasks for violations
- status.py --create-task is the only valid way to create tasks
- Pre-v2.0 tasks without .state are UNTRACKED -- all commands refuse them
- New --upgrade command bootstraps .state files for existing tasks
Project Scoping:
- --project flag added to all status.py commands across 16+ files
- _find_project_dir errors instead of silently falling back to ~/.automaton/
- --scope-check marks framework files OUT_OF_SCOPE when working on a project
- Dashboard handlers use stored project_root instead of re-detecting from CWD
- Prompts reference ~/.automaton/scripts/vram_detect.py (not {project}/.automaton/)
Harness Integration:
- status.py --can-edit now supports project-level checks (no --task required)
- --can-edit --file checks file scope without --task
- --json output for machine-readable harness integration
- opencode plugin (plugins/automaton-guard/plugin.ts) intercepts edit/write
- Git pre-commit hook (scripts/git-hooks/pre-commit) blocks commits without task
- Formal integration contract (contracts/harness-integration.md)
Other:
- upgrade.sh delegates to status.py --upgrade instead of manual heuristics
- Phase prompts reference --project {project} for multi-project scoping
- 200 tests passing (14 new)
This commit is contained in:
@@ -0,0 +1,71 @@
|
||||
# Add Decomposition Content to Dashboard Data Model
|
||||
|
||||
## Goal
|
||||
|
||||
Add missing content fields to the `Task` model so the dashboard can display wave structure from `DECOMPOSITION.md`, parent task context from `PARENT_SPEC.md`, and VRAM constraints from `VRAM_CONFIG.md`.
|
||||
|
||||
## Requirements
|
||||
|
||||
### R1. Add `decomposition_content` to Task model
|
||||
|
||||
`automaton/dashboard/core/task.py`: The `Task` dataclass has six content fields (`spec_content`, `verdict_content`, `bug_report_content`, `adversarial_bug_report_content`, `doc_review_content`, `design_content`) but no `decomposition_content`. This is the root cause of the dashboard's inability to parse wave structure from `DECOMPOSITION.md`.
|
||||
|
||||
**Fix**:
|
||||
- Add `decomposition_content: Optional[str] = None` field to the `Task` dataclass (`task.py:77-90`)
|
||||
- In `discover_tasks()` (`task.py:243-286`), load `DECOMPOSITION.md` content similar to how other artifacts are loaded
|
||||
- Add `"decomposition_content"` to the `/api/tasks` response in `ui/app.py` `_serve_tasks()` and `_serve_task()`
|
||||
|
||||
### R2. Parse wave structure from DECOMPOSITION.md content
|
||||
|
||||
Currently `dashboard.js:278-285` splits sub-tasks into waves using a 50/50 heuristic (`half = Math.ceil(task.sub_tasks.length / 2)`), completely ignoring the actual wave definitions in `DECOMPOSITION.md`.
|
||||
|
||||
**Fix**:
|
||||
- Parse wave headers from `decomposition_content` (Python side): extract `### Wave 1:` and `### Wave 2:` sections and their sub-task lists
|
||||
- Store parsed wave data as `waves: list[WaveGroup]` on the `Task` model or as structured data in the API response
|
||||
- Each wave group contains: wave number, label, sub-task names
|
||||
- In `dashboard.js`, use parsed wave data instead of 50/50 heuristic for wave statistics
|
||||
- Fall back to 50/50 heuristic only when `decomposition_content` is unavailable
|
||||
|
||||
### R3. Add `parent_spec_content` and `vram_config_content` to Task model
|
||||
|
||||
Sub-tasks have `PARENT_SPEC.md` and `VRAM_CONFIG.md` but these are not in the `ARTIFACTS` dict and not visible in the API response or detail panel. The detail panel cannot show parent context or VRAM constraints.
|
||||
|
||||
**Fix**:
|
||||
- Add `parent_spec_content: Optional[str] = None` and `vram_config_content: Optional[str] = None` to `Task`
|
||||
- Load these in `discover_tasks()` if the files exist
|
||||
- Include in the API response
|
||||
- Display in the detail panel when present (e.g., "Parent Context" and "VRAM Configuration" sections)
|
||||
|
||||
### R4. Add `WaveGroup` dataclass
|
||||
|
||||
Add a simple dataclass for wave metadata:
|
||||
```python
|
||||
@dataclass
|
||||
class WaveGroup:
|
||||
wave_number: int
|
||||
label: str
|
||||
sub_task_names: list[str]
|
||||
```
|
||||
|
||||
### R5. Parse DECOMPOSITION.md wave sections
|
||||
|
||||
Add a `parse_waves(content: str) -> list[WaveGroup]` function that extracts wave definitions from `DECOMPOSITION.md` content. Pattern: `### Wave N: label` followed by lines starting with `- subtask-name`.
|
||||
|
||||
## Acceptance Criteria
|
||||
|
||||
- [ ] `Task` model has `decomposition_content`, `parent_spec_content`, `vram_config_content` fields
|
||||
- [ ] `/api/tasks` response includes `decomposition_content` when present
|
||||
- [ ] `/api/tasks` response includes `parent_spec_content` and `vram_config_content` when present
|
||||
- [ ] `parse_waves()` correctly extracts wave structure from the template `DECOMPOSITION.md` in `templates/tasks/subtask-parent/`
|
||||
- [ ] Dashboard JS uses parsed wave data for Wave 1/Wave 2 statistics instead of 50/50 split
|
||||
- [ ] Detail panel shows "Parent Context" section when `parent_spec_content` exists
|
||||
- [ ] Detail panel shows "VRAM Configuration" section when `vram_config_content` exists
|
||||
- [ ] Existing tests pass
|
||||
- [ ] New test: `parse_waves` with real DECOMPOSITION.md content
|
||||
- [ ] New test: task with PARENT_SPEC.md and VRAM_CONFIG.md has content fields populated
|
||||
|
||||
## Non-Goals
|
||||
|
||||
- Not changing the DECOMPOSITION.md format
|
||||
- Not applying VRAM constraints — display only
|
||||
- Not modifying how sub-tasks are created or executed
|
||||
Reference in New Issue
Block a user