Skip to content
Agent Memory
Skill

/workflow-authoring

Reference for writing a Workflow tool script (script API and gotchas, pipeline-vs-barrier rules, quality patterns, worked examples). Load before authoring a script for a workflow the user already opted into; it does not itself authorize running one.

From plugin
letta-code
3.8k26 skills8 hooks

Claude Code

$ npx -y skills add letta-ai/letta-code --skill workflow-authoring --agent claude-code

SKILL.md

workflow-authoring.SKILL.md
name: workflow-authoring
description: Reference for writing a Workflow tool script (script API and gotchas, pipeline-vs-barrier rules, quality patterns, worked examples). Load before authoring a script for a workflow the user already opted into; it does not itself authorize running one.

Workflow authoring reference

A workflow structures work across many subagents — to be comprehensive (decompose and cover in parallel), to be confident (independent perspectives and adversarial checks before committing), or to take on scale one context can't hold (migrations, audits, broad sweeps). The script is where you encode that structure: what fans out, what verifies, what synthesizes.

When you do call the Workflow tool, the right move is often **hybrid**: scout inline first (list the files, scope the diff, find the modules) to discover the work-list, then call Workflow to pipeline over it, passing the list via `args`. You don't need to know the shape before the *task* — only before the *orchestration step*.

Common single-phase workflows you can chain across turns:

  • **Understand** — parallel readers over relevant subsystems → structured map
  • **Design** — judge panel of N independent approaches → scored synthesis
  • **Review** — dimensions → find → adversarially verify
  • **Research** — multi-modal sweep → deep-read → synthesize
  • **Migrate** — discover sites → transform each → verify

For larger work, run several in sequence — read each result before deciding the next phase. You stay in the loop; each workflow is one well-scoped fan-out.

Every script must begin with `export const meta = {...}`:

export const meta = { name: 'find-flaky-tests', // kebab-case, required description: 'Find flaky tests and propose fixes', // required phases: [ // one entry per phase() call { title: 'Scan', detail: 'grep test logs for retries' }, { title: 'Fix', detail: 'one agent per flaky test' }, ], } // script body starts here — use agent()/parallel()/pipeline()/phase()/log()

The `meta` object must be a PURE LITERAL — no variables, function calls, spreads, or template interpolation.

What a subagent is

Every `agent()` call is one agent-free ephemeral conversation linked to the invoking parent agent (`is_subagent: true`, named after the call's `label`). It starts with nothing but its prompt: no memory, no conversation context, no skills. Put ALL context a stage needs in the prompt — file paths, the rule it should apply, what shape to return.

Subagents are told their final text IS the return value (not a human-facing message), so they return raw data. Workers inherit the invoking session's tools and permission mode; use `allowedTools` to restrict a workflow or stage. For stages whose input is entirely in the prompt (synthesis, judging, scoring) pass `allowedTools: []` — a model that can still read files tends to wander, and a subagent that re-issues an identical tool call three times is stopped and rejects with the failure detail.

Their model defaults to the invoking conversation's model. `opts.model` (or the tool's `model` input) accepts any handle or alias listed by `letta model list`; an unknown value rejects that call. Use a cheaper model for mechanical stages only when you know a valid handle.

Use the invoking backend for workflow workers. Local execution requires an Agent SDK and App Server with local conversation support; `decide()` still uses the Cloud decisions service.

Script body hooks

  • `agent(prompt, opts?)` → Promise. Spawn one subagent. Resolves to its final

text, or with `schema` (JSON Schema) to a validated object. Prefer `schema` for shaped results: invalid or missing output is retried, then rejects with validation detail in the error and journal. `json: true` still parses without validating; `schema` wins if both are set. Await each call; failures reject with the cause, `callIndex`, and `conversationId` when available. Catch errors explicitly to recover. Options: `label` (display name), `phase` (progress group — use this inside concurrent stages), `schema`, `json`, `model`, `effort` (`'low'` for mechanical stages, higher for the hardest verify/judge stages), `allowedTools`, `systemPrompt` (extra system prompt for this subagent), `skills` (skill names whose full content is loaded into the subagent's prompt; workers otherwise have no skills), `timeoutMs` (default 10 minutes), `maxToolCalls` (positive safe integer; default 1000 unique tool calls for this subagent), `conversationId` (resume a worker — see "Diagnosing a run").

  • `pipeline(items, stage1, stage2, ...)` → run each item through all stages

independently, NO barrier between stages. Item A can be in stage 3 while item B is still in stage 1. This is the DEFAULT for multi-stage work. Wall-clock = slowest single-item chain, not sum-of-slowest-per-stage. Every stage callback receives `(prevResult, originalItem, index)` — use originalItem/index in later stages to label work without threading context through stage 1's return value. A stage that throws skips that item's remaining stages; siblings finish, then the helper rejects.

  • `parallel(thunks)` → run zero-arg functions concurrently. This is a

BARRIER: it awaits all thunks, then rejects if any threw. For best-effort processing, catch errors inside each thunk and return explicit success/error results. Use ONLY when you genuinely need all results together.

  • `phase(title)` — start a new phase; subsequent agent() calls are grouped

under this title in progress output.

  • `log(message)` — emit a progress message to the user.
  • `budget` — live run cost in USD: `budget.spent`, `budget.limit`, and

`budget.remaining` (limit and remaining are `null` without a `maxCostUsd`; spent and remaining are `null` once any usage had no cost estimate). With a budget, reaching it stops the run: pending and new calls reject with `

Read more
@letta-ai
Ships withletta-code

Letta Code is a stateful agent harness for creating agents that are more like people than tools. Letta Code agents have memory, identity, and a sense of experience over time.

Stars on GitHub

Momentum

stars in total
3.8k
Star history of letta-ai/letta-code on GitHub, a chart by star-history.com

Other skills on letta-code.

acquiring-skills

acquiring-skills

Discover and install skills from Hermes, ClawHub, GitHub, and other registries. Load this skill whenever a user asks for a…

@letta-ai@letta-aiInstall Skill
browser-use

browser-use

Control a real browser to navigate pages, click, type, fill forms, inspect rendered UI, take screenshots, or record video. Load…

@letta-ai@letta-aiInstall Skill
context-doctor

context-doctor

Investigate and repair an agent's context — memory, system prompt, and skills — using observed behavior as evidence. Use when the…

@letta-ai@letta-aiInstall Skill
creating-mods

creating-mods

Creates and edits trusted local Letta Code mods, including tools, slash commands, local-only model providers, lifecycle/turn…

@letta-ai@letta-aiInstall Skill
creating-skills

creating-skills

Guide for creating effective skills. Use when creating a new skill or updating an existing one that extends Letta Code's…

@letta-ai@letta-aiInstall Skill
customizing-commands

customizing-commands

Creates, edits, and enables Letta Code mod-provided slash commands. Use when the user asks to add a custom /command, slash…

@letta-ai@letta-aiInstall Skill

More skills from other plugins.

agent-cost-report

agent-cost-report

Believable agent cost report for any period, default the last 7 full days PT, not counting today. Measured tokens from Claude…

@thedotmack@thedotmackInstall Skill
bot-handoff

bot-handoff

Keep a durable record of work passed between Bots in the shared Hindsight memory bank. Use when handing work to another Bot, when…

@vectorize-io@vectorize-ioInstall Skill
mempalace

mempalace

Install, configure, and operate MemPalace, including a private local palace, a shared-brain hub, or a client joining an existing…

@mempalace@mempalaceInstall Skill
mempalace

mempalace

Install, configure, and operate MemPalace, including a private local palace, a shared-brain hub, or a client joining an existing…

@milla-jovovich@milla-jovovichInstall Skill

Questions about workflow-authoring.

Which coding agents can use workflow-authoring?
workflow-authoring installs in Claude Code, Codex, Cursor, Gemini CLI, GitHub Copilot, OpenCode and Windsurf with the skills CLI, using each agent's flag shown on this page. Flowy's auto-invocation, which fires a skill when your prompt matches, runs in Claude Code only.