Feat v0.8.5 extension composability (#72)
All checks were successful
CI/CD / detect-changes (push) Successful in 4s
CI/CD / test-runners (push) Has been skipped
CI/CD / e2e-smoke (push) Has been skipped
CI/CD / test-frontend (push) Successful in 6s
CI/CD / test-go-pg (push) Successful in 2m44s
CI/CD / test-sqlite (push) Successful in 2m54s
CI/CD / build-and-deploy (push) Successful in 52s
All checks were successful
CI/CD / detect-changes (push) Successful in 4s
CI/CD / test-runners (push) Has been skipped
CI/CD / e2e-smoke (push) Has been skipped
CI/CD / test-frontend (push) Successful in 6s
CI/CD / test-go-pg (push) Successful in 2m44s
CI/CD / test-sqlite (push) Successful in 2m54s
CI/CD / build-and-deploy (push) Successful in 52s
Co-authored-by: Jeffrey Smith <jasafpro@gmail.com> Co-committed-by: Jeffrey Smith <jasafpro@gmail.com>
This commit was merged in pull request #72.
This commit is contained in:
126
docs/DESIGN-workflow-redesign.md
Normal file
126
docs/DESIGN-workflow-redesign.md
Normal file
@@ -0,0 +1,126 @@
|
||||
# DESIGN — Workflow System Redesign (0.9.x)
|
||||
|
||||
**Version:** v0.9.0
|
||||
**Status:** Draft
|
||||
**Author:** Jeff / Claude session 2026-04-03
|
||||
|
||||
---
|
||||
|
||||
## Problem
|
||||
|
||||
The workflow system spans ~7,600 lines across 25+ files and was built
|
||||
incrementally from v0.3.x through v0.7.10. It works, but several
|
||||
concepts are redundant, primitives are buried, and the Starlark module
|
||||
is read-only. Before shipping reference extensions (v0.10.x) that
|
||||
build on workflows, the system needs cleanup and promotion of reusable
|
||||
primitives.
|
||||
|
||||
## Audit Summary
|
||||
|
||||
Full audit in `/config/Downloads/AUDIT-workflow-0.9.md`. Classification:
|
||||
|
||||
### KEEP — Core primitives that survive
|
||||
|
||||
| Component | File(s) | Lines | Rationale |
|
||||
|-----------|---------|-------|-----------|
|
||||
| Engine core | `workflow/engine.go` | ~400 | Stateless state machine — Start, Advance, Cancel, version-pinned execution |
|
||||
| Conditional routing | `workflow/routing.go` | ~500 | Pure functions, 8 operators, well-tested (497 lines of tests) |
|
||||
| Automated processing | `workflow/automated.go` | ~300 | Starlark hook execution, cycle guard (max 10) |
|
||||
| Scanner | `workflow/scanner.go` | ~200 | Background SLA + staleness checks, 5-minute interval |
|
||||
| Signoff system | engine.go + handlers | ~400 | Multi-party approve/reject with quorum, role-gated |
|
||||
| Assignment queue | handlers | ~300 | Claim/unclaim/complete/cancel lifecycle |
|
||||
| Version snapshots | store + models | ~200 | Immutable snapshots, version-pinned instances |
|
||||
| Typed form system | `models/workflow.go` | ~300 | 8 field types, fieldsets, conditional visibility |
|
||||
| Store interface | `store/workflow_iface.go` | 61 methods | Complete lifecycle coverage |
|
||||
|
||||
### OBE — Superseded by new design
|
||||
|
||||
| Concept | Superseded by |
|
||||
|---------|---------------|
|
||||
| Per-stage `audience` field | Multi-page packages with mixed access declarations |
|
||||
| `entry_mode` (public_link/team_only) | Package-level `scope: adoptable` + per-page access |
|
||||
| `stage_mode` proliferation (4 values) | Collapse to 3: form / delegated / automated |
|
||||
| `stage_type` (simple/dynamic/automated) | Redundant with `starlark_hook` presence check |
|
||||
| `AdoptTeamWorkflow` clone | Package adoption model |
|
||||
| `ExportWorkflowPackage` endpoint | Standard package export |
|
||||
|
||||
### PROMOTE — Buried features to expose as kernel primitives
|
||||
|
||||
1. **Roles → kernel primitive**: `team_user_roles` table, manifest `requires_roles`,
|
||||
team admin UI, kernel middleware, Starlark SDK
|
||||
2. **Typed forms → SDK primitive**: Move from workflow models to `forms` package,
|
||||
FE SDK `sw.forms.render()` / `sw.forms.validate()`
|
||||
3. **Conditional routing → SDK primitive**: Starlark `routing.evaluate(rules, data)`
|
||||
4. **Workflow Starlark module → full read/write**: `workflow.start()`, `.advance()`,
|
||||
`.cancel()`, `.submit_signoff()`
|
||||
|
||||
---
|
||||
|
||||
## Technical Debt
|
||||
|
||||
### Starlark Converter Duplication
|
||||
|
||||
Three files contain nearly identical Go↔Starlark conversion functions:
|
||||
|
||||
| File | Functions |
|
||||
|------|-----------|
|
||||
| `workflow/automated.go` | `goToStarlark`, `starlarkDictToMap`, `starlarkToGo` |
|
||||
| `handlers/workflow_hooks.go` | `starlarkDictToMap`, `starlarkToGo`, `jsonToStarlark` |
|
||||
| `sandbox/workflow_module.go` | `goValToStarlark` |
|
||||
|
||||
**Fix:** Consolidate into `sandbox/convert.go`.
|
||||
|
||||
### Snapshot Format Inconsistency
|
||||
|
||||
Two formats exist (wrapped `{stages, workflow}` vs legacy flat array).
|
||||
Three copies of the parser across engine, instance handlers, and
|
||||
assignment handlers.
|
||||
|
||||
**Fix:** Consolidate into one exported function. Standardize on wrapped format.
|
||||
|
||||
---
|
||||
|
||||
## Sequencing
|
||||
|
||||
| Version | Feature | Dependencies |
|
||||
|---------|---------|-------------|
|
||||
| **v0.9.0** | Starlark converter consolidation + snapshot format cleanup | None |
|
||||
| **v0.9.1** | `team_user_roles` table + management API + admin UI | None |
|
||||
| **v0.9.2** | `scope: adoptable` manifest field + adoption flow with role auto-populate | v0.9.1 |
|
||||
| **v0.9.3** | Promote typed forms to SDK primitive (`sw.forms`) | None |
|
||||
| **v0.9.4** | Deprecate `stage_type`, collapse `stage_mode` to 3 values | None |
|
||||
| **v0.9.5** | Full read/write workflow Starlark module | v0.9.0 |
|
||||
| **v0.9.6** | Conditional routing as SDK primitive | v0.9.5 |
|
||||
| **v0.9.7** | Multi-surface manifest + kernel route resolution | None |
|
||||
| **v0.9.8** | Wire roles into surface access (`access: role:X`) + kernel middleware | v0.9.1, v0.9.7 |
|
||||
|
||||
Each step is CI-green independently. The first four are the high-value items.
|
||||
|
||||
---
|
||||
|
||||
## Files Affected (by component)
|
||||
|
||||
### Converter Consolidation (v0.9.0)
|
||||
- New: `sandbox/convert.go`
|
||||
- Modified: `workflow/automated.go`, `handlers/workflow_hooks.go`, `sandbox/workflow_module.go`
|
||||
|
||||
### Team Roles (v0.9.1)
|
||||
- New: migration (PG + SQLite), `store/team_roles.go`, `handlers/team_roles.go`
|
||||
- Modified: manifest validation, adoption flow, team admin UI
|
||||
|
||||
### Typed Forms (v0.9.3)
|
||||
- New: `forms/` package (extracted from `models/workflow.go`)
|
||||
- New: `sw.forms` SDK module
|
||||
- Modified: workflow engine to import from `forms/` instead of inline
|
||||
|
||||
### Workflow Starlark Module (v0.9.5)
|
||||
- Modified: `sandbox/workflow_module.go` — add start/advance/cancel/signoff
|
||||
- Modified: `workflow/engine.go` — extract interface to break circular import
|
||||
|
||||
---
|
||||
|
||||
## Non-Goals
|
||||
|
||||
- Rewriting the workflow engine. The state machine is correct and stays.
|
||||
- Adding a visual workflow builder. That's an extension concern, not kernel.
|
||||
- Multi-tenancy changes. Team scoping works as designed.
|
||||
Reference in New Issue
Block a user