Diagram type

PlantUML Activity Diagram Syntax & Examples

Reference for PlantUML activity diagram syntax — start / stop, actions, if-else branches, repeat-while loops, switch-case, and swimlane lanes. Copy-paste examples.

Use this page to connect a high-intent search query to the right problem-solution narrative.

At a glance

A syntax reference for the PlantUML activity-beta grammar — read this when you need to know exactly how a particular construct (decision, loop, lane, fork) is written, then beautify or edit the source in the editor.

What is a PlantUML activity diagramBasic syntax — start, action, stopBranching — if-else and switch-caseLooping — repeat-while and while-doSwimlane lanes — partition responsibility across actorsCommon patterns & gotchas
Rendered proof
A reimbursement approval flow combining swimlane lanes with an if-else decision — the building blocks covered on this page in one diagram.
Theme · Blueprint
Open this diagram in editor
01 Employee 02 Manager 03 Finance yes no 01 · ENTRYStart02 · PROCESSSubmitreimbursement03 · PROCESSReview request04 · DECISIONApproved?05 · PROCESSProcess payment07 · PROCESSNotify employee06 · PROCESSReceive rejection08 · OUTCOMEStop
View PlantUML sourcePlain-text diagram syntax — copy or edit directly.
diagram.puml
1@startuml
2|Employee|
3start
4:Submit reimbursement;
5|Manager|
6:Review request;
7if (Approved?) then (yes)
8 |Finance|
9 :Process payment;
10 :Notify employee;
11else (no)
12 |Employee|
13 :Receive rejection;
14endif
15stop
16@enduml

What is a PlantUML activity diagram

An activity diagram in PlantUML describes a process as an ordered sequence of actions, with branches, loops, and parallel paths along the way. It is the closest PlantUML equivalent to a flowchart — but with a strict grammar (`start` / `:action;` / `stop`) and built-in support for swimlane lanes, which makes it the standard choice for runbooks, approval flows, and process documentation. PlantUML actually ships two activity syntaxes: the legacy one (using `(*)` and arrow notation) and the modern activity-beta (start / action / stop). Everything on this page covers activity-beta, which is what `@startuml` / `@enduml` blocks render by default in current PlantUML releases.

Basic syntax — start, action, stop

Every activity diagram lives inside a `@startuml` / `@enduml` block. The flow begins at `start`, runs through a series of actions written as `:Action text;` (note the trailing semicolon), and ends at `stop` (or `end` for early termination). Actions can be plain strings, multi-line with `\n`, or include inline formatting. Each action becomes one rounded rectangle in the rendered output, and the renderer connects them top-to-bottom by default. This is the minimum viable activity diagram and the building block every other construct extends.

  • `start` and `stop` are required terminals — omit them and the parser falls back to legacy syntax
  • `:Action;` is the basic activity node — text inside the colons, semicolon at the end
  • Multi-line action labels use `\n` inside the colons

Branching — if-else and switch-case

Decisions in PlantUML activity use `if (Condition?) then (yes) ... else (no) ... endif`. The condition is rendered as a diamond, and the `(yes)` / `(no)` labels appear on the outgoing edges. For multi-way decisions, use `switch (Variable?) ... case (A) ... case (B) ... endswitch` — each case becomes a separate path that converges at the end of the switch. Both forms can be nested and combined with loops; the parser handles arbitrarily deep nesting, but practical readability degrades past two levels.

  • `if (Condition?) then (yes) ... else (no) ... endif` — basic two-way decision
  • `if (...) then (yes) ... elseif (...) then (yes) ... else (no) ... endif` — chained decisions
  • `switch (...) case (A) ... case (B) ... endswitch` — multi-way decision with named branches

Looping — repeat-while and while-do

PlantUML activity offers two loop constructs that differ in when the condition is evaluated. `repeat ... repeat while (Condition?) is (yes)` runs the body first, then tests — equivalent to a do-while loop. `while (Condition?) ... endwhile` tests first, then runs the body — equivalent to a standard while loop. The first form is typical for retry patterns (attempt the action, then check whether to retry); the second is typical for queue processing (check whether there's work, then process it). Both forms accept an optional `->no;` or `->yes;` annotation on the exit edge to label what the false condition means in context.

Swimlane lanes — partition responsibility across actors

Swimlane lanes are PlantUML activity's standout feature. Declare a lane with `|Lane Name|` before the first action that belongs in it; subsequent actions belong to the most recently declared lane until another `|Other Lane|` switches context. Optionally tint the lane with `|#Color|Lane Name|` — colors can be named CSS values or hex. The reference renderer stacks lanes vertically as subgraphs, but Beauty Diagram's renderer lays them out as horizontal columns by default once at least two lanes and one cross-lane edge are present. That column layout is what makes the diagram read as a process across actors rather than a vertical sequence with labels.

  • `|Customer|` — plain lane declaration
  • `|#FFB6C1|Monitoring|` — coloured lane declaration with hex tint
  • `|Lane Name|` re-used later switches the active lane without redefining it

Common patterns & gotchas

A few patterns come up repeatedly. Approval flows usually combine swimlanes with `if-else` — the approver lane has the decision, the receiver lane handles each outcome. Retry flows pair `repeat-while` with a status check. Forks and joins for parallel paths use `fork ... fork again ... end fork` — supported but rendered with default layout, not yet beautified. The most common gotcha: forgetting the semicolon on `:Action;` causes the parser to swallow the entire next line silently — if your diagram is missing a node, check the previous line for a missing `;` first.

  • Missing `;` on `:Action;` silently swallows the next line — most common syntax bug
  • Lanes only switch to horizontal columns when ≥ 2 lanes + ≥ 1 cross-lane edge exist
  • `stop` inside a branch terminates only that branch path, not the whole diagram
FAQ

PlantUML Activity Diagram Syntax & Examples — frequently asked questions

What does `start` and `stop` do in a PlantUML activity diagram?

`start` marks the entry point (rendered as a filled black circle) and `stop` marks the exit (a circled black dot). Both are required for the activity-beta syntax; without them, the parser falls back to PlantUML's legacy activity syntax which has different semantics. Use `end` instead of `stop` for an early-termination terminal that visually differs from a normal exit.

How do I write an if-else decision in PlantUML activity syntax?

Use `if (Question?) then (yes) ... else (no) ... endif`. The question becomes a diamond node, and the `(yes)` / `(no)` strings label the outgoing edges. For multi-way decisions, chain with `elseif (Other?) then (yes) ...` or use `switch (Variable?) case (A) ... case (B) ... endswitch`. Both forms render with the same visual conventions.

What's the difference between repeat-while and while-endwhile?

`repeat ... repeat while (Condition?) is (yes)` is a do-while loop — the body runs once before the condition is checked. `while (Condition?) ... endwhile` is a standard while loop — the condition is checked first, and the body may never run. Use repeat-while for retry patterns (always attempt at least once), and while-endwhile for queue processing or polling (check first before doing work).

Can I nest swimlane lanes inside other constructs?

Lanes themselves cannot be nested — there's no `|Outer| |Inner|` syntax. But you can switch lanes inside any other construct: inside an `if-else` branch, inside a `repeat` loop, anywhere an action would be valid. The lane scope follows the source order, so each `|Lane|` declaration switches the active lane until the next one. Beauty Diagram preserves whichever lane is active at each action when laying out horizontal columns.

Why does my activity diagram look vertical instead of horizontal?

Two reasons. First, the default PlantUML renderer always stacks lanes vertically — switch to the Beauty Diagram editor to get the horizontal column layout. Second, even Beauty Diagram only flips to horizontal columns when at least two `|lane|` declarations exist AND at least one edge crosses between lanes — a single-lane diagram or a diagram where all actions stay in one lane stays vertical because there's no swimlane signal to render.