> ## Documentation Index
> Fetch the complete documentation index at: https://docs.agentium.in/llms.txt
> Use this file to discover all available pages before exploring further.

# Schedule dependency graphs and repeats

> Declare Workflow control and data dependencies, isolate node inputs, join owned patches, and bound repeated graph episodes.

Use a Workflow graph when stages have dependencies but independent stages should start as soon as their prerequisites settle. Nodes contain ordinary Agent, function, condition, parallel, graph or repeat steps. A single Agent remains useful for exploratory reasoning and tool use; graph nodes can contain that existing loop.

## Run independent reads before a join

This complete example uses no provider or external service. Save it as `calculation.ts`, install matching core packages using [installation](/learn/installation), then run `npx tsx calculation.ts`.

```typescript theme={null}
import { Workflow, type GraphStep } from "@agentium/core";

type State = { left: number; right: number; total: number };
const graph: GraphStep<State> = {
  name: "calculate",
  maxConcurrency: 2,
  graph: [
    { id: "left", step: { name: "read-left", run: async () => ({ left: 2 }) } },
    { id: "right", step: { name: "read-right", run: async () => ({ right: 3 }) } },
    { id: "sum", inputsFrom: ["left", "right"],
      step: { name: "sum", run: async (state) => ({ total: state.left + state.right }) } },
  ],
};
const calculation = new Workflow<State>({
  name: "calculation", register: false,
  initialState: { left: 0, right: 0, total: 0 }, steps: [graph],
});
const result = await calculation.run();
console.log(result.status, result.state.total); // completed 5
await calculation.close();
```

`inputsFrom` supplies patches from transitive data ancestors and gates readiness. Each node receives its own structured clone of entry state plus those ancestor patches. Control predecessors and unrelated completed siblings do not silently supply state. Graph input and returned patches must be structured-cloneable.

## Distinguish control from data

| Edge | Required predecessor outcome | Input state |
| - | - | - |
| `dependsOn` | Done or skipped | No predecessor patch supplied merely by this edge |
| `inputsFrom` | Done | Includes transitive data-ancestor patches |

Failed or blocked predecessors block their consumers. A skipped condition can release a control join but cannot provide data. Blocked nodes appear as skipped with `workflow_dependency_blocked` and make the graph fail. Complete episodes are checked before their effects: unique IDs, valid steps, references, duplicate edges, cycles in both edge types and limits. Dynamic factories are checked at entry.

Ready nodes start incrementally. `maxConcurrency` defaults to five nodes and `maxNodes` to 100 per episode; values must be positive safe integers. A nested Agent or parallel group may start its own work, so this local node ceiling does not cap aggregate provider/tool concurrency. Use [recoverable graph root admission](/harness/execution-graphs#bound-all-controlled-work-at-the-root) when you need one shared leaf-work ceiling.

## Join owned patches predictably

Results and final joins use stable topological order with declaration-order ties. Completion timing does not choose the winning writer. Graph `merge` defaults to `"error"`: incomparable nodes writing the same key conflict even when values match. Descendants may intentionally overwrite ancestor keys. `"declaration_order"` uses the stable topological order to choose the later writer. Existing parallel groups retain their declaration-order default.

An ordinary node failure discards its patch, retains child diagnostics and blocks dependent work; successful independent nodes may still contribute patches. Definition, conflict and cancellation failures reject the boundary, drain already-started work and prevent downstream Workflow steps/checkpoints. Applied external effects remain applied.

Structured cloning protects state data. It does not sandbox callbacks, isolate captured resources or prove that independent nodes may safely mutate the same browser, file, database object or account. The host supplies resource ordering or locks.

## Repeat complete episodes within a cap

```typescript theme={null}
import { Workflow } from "@agentium/core";

const repair = new Workflow({
  name: "bounded-repair", register: false,
  initialState: { attempts: 0, verified: false },
  steps: [{
    name: "repair", maxIterations: 2,
    while: (state) => !state.verified,
    repeat: [{ name: "episode", graph: (state) => [{
      id: state.attempts === 0 ? "first-try" : "repair-try",
      step: { name: "check", run: async (input) => ({
        attempts: input.attempts + 1, verified: input.attempts === 1,
      }) },
    }] }],
  }],
});
console.log((await repair.run()).state); // { attempts: 2, verified: true }
await repair.close();
```

The predicate is pre-tested with the zero-based number of completed iterations. A false predicate after the final allowed body succeeds; a true predicate returns `workflow_iteration_limit`. Body errors stop repetition. The cap is captured before callbacks execute. A graph factory runs once at episode entry, after previous work settles.

Factories and predicates are trusted host callbacks. Replanning here selects a complete new episode; it does not modify running nodes or execute arbitrary generated code. Per-episode and repeat limits multiply under nesting. Scoped composition has a depth limit of 64, while shared harness model/tool/token budgets bound the run. This ordinary path has no separate lifetime expansion allowance.

## Grant scoped effects and handle cancellation

Graph nodes and repeat iterations appear in `StepResult.executionPath`, events, child session IDs and `metadata.workflowExecutionPath`. Segments use `encodeURIComponent`. A function's controlled effect name is `workflow:<executionPath>`, such as `workflow:calculate/left/read-left`; grant that exact name under a harness. Outside scoped graph/repeat steps, legacy `workflow:<step.name>` names stay valid. Paths are diagnostic identity and are not remote idempotency keys.

Agent output keys remain `<step.name>_output`. Give independent Agent nodes distinct names or an explicit ordering/merge choice. Shared budget admission winners can depend on timing. Cancellation stops new admission, propagates to children, drains started callbacks and discards late patches; uncooperative callbacks can delay settlement. Repeats can deliberately issue effects again. Controlled Workflow does not automatically retry a rejected effect acknowledgment.

## Save completed boundaries

Graph and repeat are complete top-level checkpoint boundaries. [Validated continuation](/workflows/time-travel) skips a saved completed boundary, but an unsaved graph's effects may repeat after a crash, cancellation or failed save. Callable/factory/environment changes require a new definition version.

Use [ExecutionGraphRuntime](/harness/execution-graphs) for recorded Agent decisions, per-node recovery, persisted root allowances and effect reconciliation. The ordinary Workflow harness driver advertises `durable: false`. See the [workflow API reference](/api-reference/core/workflow) for exact graph/repeat types.


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.