agentic examples

The Plan Diagrammer

The Plan Diagrammer: any orchestrator's graph, emitted as Mermaid - paste it into a README, GitHub renders it, and the diagram can never drift from the plan because it is generated FROM the plan.

Developer Experience Round 5 Xavier Noria exit 0

source on github

bundle exec ruby examples/plan_diagram.rb

a real captured run

```mermaid
graph TD
  T0["research topic"]
  T1["draft outline"]
  T2["verify sources"]
  T3["write draft"]
  T4["publish"]
  T0 --> T1
  T0 --> T2
  T1 -- skeleton --> T3
  T2 -- citations --> T3
  T3 --> T4
```

paste the block above into any GitHub markdown file. the arrows
labeled 'skeleton' and 'citations' are the named dependencies -
the diagram documents not just THAT draft waits, but WHY.

source

# frozen_string_literal: true

# The Plan Diagrammer: any orchestrator's graph, emitted as Mermaid -
# paste it into a README, GitHub renders it, and the diagram can never
# drift from the plan because it is generated FROM the plan.
#
#   bundle exec ruby examples/plan_diagram.rb
#
# Runs offline; prints Mermaid source. Named dependencies become
# labeled edges; plain dependencies become arrows.

require class="s">"bundler/setup"
require class="s">"agentic"

# A representative plan: the editorial pipeline with a named fan-in
orchestrator = Agentic:class="y">:PlanOrchestrator.new

def step(name)
  Agentic:class="y">:Task.new(description: name, agent_spec: {class="s">"name" => name, class="s">"instructions" => class="s">"work"})
end

research = step(class="s">"research topic")
outline = step(class="s">"draft outline")
sources = step(class="s">"verify sources")
draft = step(class="s">"write draft")
publish = step(class="s">"publish")

orchestrator.add_task(research)
orchestrator.add_task(outline, [research])
orchestrator.add_task(sources, [research])
orchestrator.add_task(draft, needs: {skeleton: outline, citations: sources})
orchestrator.add_task(publish, [draft])

# --- the diagrammer: graph in, mermaid out -----------------------------------
# graph[:edges] arrives pre-merged with labels and graph[:order] gives
# stable, topological node numbering - both were this example's asks.
def to_mermaid(graph)
  names = graph[class="y">:tasks].transform_values(&class="y">:description)
  ids = graph[class="y">:order].each_with_index.to_h { |task_id, i| [task_id, class="s">"T#{i}"] }

  lines = [class="s">"graph TD"]
  graph[class="y">:order].each { |task_id| lines << class="s">"  #{ids[task_id]}[\"#{names[task_id]}\class="s">"]" }
  graph[class="y">:edges].each do |edge|
    arrow = edge[class="y">:label] ? class="s">"-- #{edge[class="y">:label]} -->" : class="s">"-->"
    lines << class="s">"  #{ids[edge[class="y">:from]]} #{arrow} #{ids[edge[class="y">:to]]}"
  end
  lines.join(class="s">"\n")
end

mermaid = to_mermaid(orchestrator.graph)

puts class="s">"```mermaid"
puts mermaid
puts class="s">"```"
puts
puts class="s">"paste the block above into any GitHub markdown file. the arrows"
puts class="s">"labeled 'skeleton' and 'citations' are the named dependencies -"
puts class="s">"the diagram documents not just THAT draft waits, but WHY."