Design to production via agentic workflows

A complex, custom Claude workflow to build production software from design and documentation

Project Date: September 2026

Team

Self

Role

Founder

Platform

Web

Outcome

Cross-platform web platform

Setup

Ontrack is tool I've wanted developed for a long time, you can read about my thought process here. The goal was to let an AI agent do most of the end-to-end production without giving it authority over anything that matters. Three ideas carry the whole workflow.

  1. AI is a tool for output. AI should work off human decisions and thought processes. It mustn't come up with it's own ideas about how to handle something and run off explicit instructions.

  2. The repo is the memory. Chat sessions are disposable, so new sessions are always driven off briefs, decision records, specs and review reports in docs/ to carry the context between them.

  3. The thing that writes code holds nothing worth stealing. The agent works in an isolated machine with no GitHub login and no production secrets.


Workloop

Every unit of work follows the same loop, defined in docs/workflow.md. Figma is the source of truth for design, so the loop starts there. Claude never writes to Figma, so if design looks wrong, Claude proposes a note and the owner changes Figma.

Orange steps are agent work, blue are human driven work, green is the one step that changes main.


What a proposal contains

A plan is a briefing, not a step list, stating what is proposed and why, the relevant context, how it works in plain terms, the options considered and what the owner (me) needs to answer. The same rule covers docs changes, new dependencies and system changes - Approval is always first, then the action.


Piece by piece

The agent builds one component, screen or flow per approved unit and is told not to scaffold the whole app in one pass. Where Figma is silent, Claude has permission to interpret its own UI/UX and logs it in an interpretation register, each marked Figma-sourced or interpreted and to be replaced when design catches up.


Context & Design

Sessions get cut off and restarted, so a session must be able to start cold from a few small reads. The docs are layered so the agent loads only what it needs. This helps keep context low per session to prevent hallucinations and excess token spend. Although auto-compact is a feature in Claude, I preferred to keep things systematic.


Artifact

Holds

Scale in this project (as of writing)

Task brief

Goal, acceptance, state, one handoff note (overwritten, never appended)

40+ briefs, finished ones moved to done/

Decision log

Dated decisions that override the product doc

67 entries

ADRs

Stack, persistence, boundaries, sync protocol, hosting, Go layout, secretless dev

7 records

Figma specs

Each frame distilled once, so later sessions do not refetch Figma

8 spec files

Review reports

Blind-review findings and how each ended

18 reports

Release notes

Commit, image digest, migrations, checks per release

2 so far


Docs are version-controlled and “living”: any task may amend them as part of its work, with the owner’s review. The source product doc and the archive are never rewritten. Changes go in the decision log instead.


Design to code

Figma holds the design and the agent reads it through the Figma MCP server. The rule is that code is never written from memory of a design.

How it worked in practice

  • Tokens are generated. A snapshot of Figma’s colour variables and text styles is turned into CSS custom properties named after the Figma variable.

  • Specs record the drift. The task-row spec splits “Figma-sourced” from “Interpreted” and ends with a table of drifts between Figma and the code. Each row says what the code does, what Figma says and the action: follow Figma, keep (user instruction) or propose a Figma note.

  • Deliberate deviations are named. Live testing found the Figma type scale “too cramped and zoomed in”. Rather than editing generated tokens, we added a separate density layer that overrides them, with the Figma values kept as fallbacks. A proposed Figma note exists now to adopt it or replace it with another system.


Worktrees

Branch policy

main only ever holds approved work. Each task gets one short-lived branch named <type>/<T-NNN>-<slug> and there is no long-lived dev branch because the team is one person. A tracked pre-commit hook blocks direct commits to main except for docs.

Parallel work with worktrees

A worktree is a second working copy of the repo on its own branch. It let several agent sessions work at once without touching each other’s files. Each brief declares which files it owns, and no two open briefs may own the same file. Shared interfaces (domain types, tokens, store API) get their own brief and merge first. Docs are edited in the main checkout only, so worktrees carry code.


Blind Opinion

An author reviewing its own work shares its own blind spots. I added a second check before I'm briefed on anything significant like new modules, shared interfaces, the domain, any sync or backend code, and any sensitive path.

Examples of what it caught

The Account page (password sign-in, JSON import and export) took three blind rounds.

Round 1 found that “Replace” could destroy data account-wide if the backup download was dismissed, and that the sign-in form revealed whether an email had an account.

Round 2 found an IndexedDB upgrade that hung while an older tab was open, and a restore copy that was not tied to an account.

Round 3 approved with only low findings, each written down.

Known limit. Same-model reviewers share blind spots. The workflow allows a different model for risky work on request, and /code-review ultra exists as a separate cloud review the owner triggers.

Model use is also a decision - stronger models for backend, sync, auth, deployment and review, lighter models for UI, specs and mechanical work.


Security

An agent runs shell commands, installs packages and edits any file. If something it reads tricks it, it can do whatever it is allowed to do.

The design limits what it is allowed to do. Agent-accessible identities and environments cannot read production credentials, change who can read them, or deploy code into a workload that holds them.

Safety nets, each with a stated limit

Net

Catches

Does not catch

Agent permission rules in user settings (not the repo)

Reads of ~/.ssh, ~/.fly, .env, backups; fly and gh admin commands

Anything not blocked by name. A fence, not a wall

gitleaks on commit, in CI and on the Mac

Keys, passwords, connection strings in new commits

Secrets that don’t look like secrets

Bundle check

sb_secret_, service_role, DB URLs, odd VITE_ names in the built web app

Secrets in the server image

Environment rule (Go)

Settings read outside the one reviewed config package

Misconfigured values that pass the checks

.dockerignore

Keys, dumps, .env in the image

Files outside the ignore list

Sensitive-path list + CODEOWNERS

Forces human review of CI, Dockerfiles, fly.toml, scripts/, auth, config, migrations, lockfiles

Not enforced by GitHub on this plan; the owner is the enforcement

Dependency scripts blocked (allowBuilds empty)

Install-time code from packages

Malicious code that runs at build or test time

Proving it works

Accepted limits, stated plainly. The machine has open outbound internet, so a tricked agent could send source code out (no secrets are inside). All OrbStack machines share one Linux kernel. Page JavaScript from the machine’s app runs in the Mac’s browser, reduced by using a separate browser profile. One early test showed that connecting the desktop app to the machine brought the owner’s login, connectors and browser tools with it, so that route was rejected and the CLI inside the machine is used instead.


Result

The current build is open at https://ontrack.gestaltapps.com. Although currently a closed-off build, local use does work but account creation is blocked until UI flows are implemented and security tests are finalised with regards to general practices including input validation or rate limiting.

Dilan Omer © 2026. I had no idea what to include in the footer

Dilan Omer

Dilan Omer