PlantUML Diagram Generator
Generate professional PlantUML diagrams from natural language descriptions. This skill handles
the full pipeline: requirement analysis → PlantUML code generation → image rendering.
Trigger Phrases
Use this skill when the user asks to:
- "Generate/draw/create a PlantUML diagram for..."
- "Create a sequence/class/activity/... diagram showing..."
- "Visualize this flow/architecture/process as..."
- "Turn this description into a UML diagram"
- "Make a flowchart / ERD / Gantt chart from..."
- Any request involving diagram generation from text descriptions
Mandatory Style Requirements
ALL diagrams generated by this skill MUST adhere to the uml-diagrams.org reference style —
strict OMG UML 2.x rendered with Visio UML 2.x stencils (black-and-white, no decoration).
This is the canonical style used throughout https://www.uml-diagrams.org and serves as the
authoritative visual reference for every diagram this skill produces.
No exceptions unless the user explicitly requests otherwise.
- Black and white only: Pure black lines (
#000000) on a pure white background (#FFFFFF). No colors, no grayscale fills, no gradients, no themed accents. - Thin uniform line weight: All borders, arrows and connectors use the default hair-line stroke (≈0.75pt). Never thicken or stylize lines.
- No circle visibility icons: Class attributes MUST NOT show colored circle icons (● public / ◐ protected / ○ private). Enforced via
skinparam classAttributeIconSize 0. Use+ - # ~text markers only. - No circle stereotype icons: Class and interface headers MUST NOT show circle-with-letter icons (Ⓒ / Ⓘ / Ⓐ / Ⓔ).
skinparam style strictumlenforces text stereotypes («interface»,«abstract»,«enumeration»). Always declare interfaces/abstract classes viaclass <<interface>>orclass <<abstract>>— never use theinterfaceorabstract classkeywords. - Abstract classifiers in italics: Per UML 2.5 §9 and uml-diagrams.org "Name of an abstract classifier is shown in italics" — using the
<<abstract>>text stereotype withstrictumlproduces the correct italic rendering automatically. - No 3D effects: Drop shadows MUST be disabled (
skinparam shadowing false). - Clean typography: Sans-serif font (Helvetica, equivalent to the Arial used by Visio stencils on uml-diagrams.org), 12pt default. No colored or bold text except diagram titles.
- Standard UML shapes:
- Actors are stick figures (never Visio icons or images).
- Classes / components / nodes are plain rectangles; activities are round-cornered rectangles with the activity name in the upper-left.
- Dependencies and realizations use dashed lines; lifelines use dashed vertical lines (uml-diagrams.org explicitly: "a rectangle forming its head followed by a vertical line (which may be dashed) that represents the lifetime of the participant").
- Notes are white folded-corner rectangles; no shading.
- Sequence diagram specifics (matching uml-diagrams.org figures exactly):
- Lifeline head is a white rectangle; the vertical lifeline is a dashed black line.
- Execution specification / activation bar is a "thin grey or white rectangle on the lifeline" — this skill renders it as a thin white rectangle with a black border (no yellow PlantUML default).
- Destruction occurrence is shown as an
Xat the bottom of the lifeline (PlantUML<participant> !syntax). - Synchronous messages use a filled solid triangle arrowhead on a solid line.
- Asynchronous messages use an open stick arrowhead on a solid line.
- Reply / return messages use an open stick arrowhead on a dashed line.
- Activity diagram specifics: round-cornered action rectangles, solid arrows with open arrowheads for control flow, diamond decisions/merges, thick horizontal/vertical bar for forks/joins, filled black dot for initial node, bull's-eye for activity final.
- Use case diagram specifics: stick-figure actor on the left, ellipses for use cases inside a rectangle subject boundary,
«include»/«extend»as dashed open arrows. - Class diagram specifics: associations are plain solid lines, aggregation = hollow diamond, composition = filled diamond, generalization = hollow triangle arrowhead on solid line, realization = hollow triangle arrowhead on dashed line, dependency = open arrow on dashed line.
Every .puml file MUST include the mandatory uml-diagrams.org-style preamble as its first lines after @startuml (see Style Configuration).
Workflow
Step 1: Parse and Confirm Requirements
Extract from the user's description:
- Diagram type — which PlantUML diagram fits best
- Actors/participants — who/what is involved
- Relationships/flows — how they interact
- Constraints/rules — conditions, ordering, cardinality
- Output format — svg (default), png, pdf, or txt (ASCII art)
If the diagram type is not explicitly stated, infer it from the description:
| Description signals | Recommended diagram |
|---|---|
| "A sends X to B", "request/response", "handshake" | Sequence |
| "inherits from", "has many", "belongs to", entities & fields | Class |
| "if/then", "approve/reject", workflow, pipeline | Activity |
| "user can", "admin manages", roles & permissions | Use Case |
| "depends on", "connects to", services & interfaces | Component |
| "deployed on", "hosted on", nodes & servers | Deployment |
| "transitions from", "changes state", lifecycle | State |
| timeline, milestones, phases, schedule | Gantt |
| hierarchy, brainstorming, tree structure | Mind Map |
If ambiguous, ask the user to clarify the diagram type before proceeding.
Step 2: Generate PlantUML Code
Write the PlantUML source following these rules:
- Start EVERY file with one of the two mandatory uml-diagrams.org-style preambles
immediately after@startuml:
- Default: theskinparampreamble — see OMG-UML / uml-diagrams.org Style Configuration.
Maximum backward compatibility, used by every example except #07.
- Backup option: the CSS-style<style>preamble — see Alternative — CSS-style Preamble.
Recommended on PlantUML ≥ 1.2019.9 whereskinparamis being phased out.
Pick ONE per file — never mix both inside the same.puml. - Use
@startuml/@endumldelimiters - Include a descriptive
title - Use proper PlantUML syntax for the chosen diagram type (see Reference below)
- Keep the diagram focused — don't add unnecessary elements
- NEVER add color, themed backgrounds, or decorative styling — strict black and white
Save the PlantUML source to a .puml file in the working directory.
Step 3: Render to Image
Use the bundled conversion script. Pick the variant that matches the current OS / shell:
Linux, macOS, or Windows with a POSIX shell (Git Bash, MSYS2, WSL, Cygwin):
bash .opencode/skills/plantuml/scripts/generate-plantuml.sh <input.puml> <output_dir> --format <svg|png|pdf|txt>
Windows native PowerShell (no bash required):
powershell -ExecutionPolicy Bypass -File .opencode\skills\plantuml\scripts\generate-plantuml.ps1 <input.puml> <output_dir> -Format <svg|png|pdf|txt>
Both scripts accept the same arguments and try three backends in strict priority order.
The PlantUML public server is the preferred / default path; Docker and the local JAR
are only used as fallbacks when the server is unreachable:
- PlantUML public server (https://www.plantuml.com/plantuml) — preferred, requires internet
- Docker (requires
docker pull plantuml/plantuml:latest) — fallback - Local
plantuml.jar(requires Java) — last-resort offline fallback
After rendering, show the user the output. If SVG is generated, read and display it inline.
If PNG/PDF is generated, tell the user where the file is saved.
Step 4: Iterate on Feedback
If the user requests changes:
1. Modify the .puml file
2. Re-run the conversion script
3. Show the updated result
PlantUML Syntax Reference
> Note: All examples below omit the mandatory monochrome preamble for brevity.
> In actual generated code, EVERY file MUST include the OMG-UML style preamble immediately after @startuml.
> The class diagram example shows the full preamble inline as a reference.
Sequence Diagram
@startuml
title Authentication Flow
actor User
participant "Web App" as App
participant "Auth Service" as Auth
database "User DB" as DB
User -> App: Login (email, password)
App -> Auth: POST /auth/login
Auth -> DB: SELECT user WHERE email
DB --> Auth: user record
Auth -> Auth: Verify password hash
alt Success
Auth --> App: JWT token
App --> User: Dashboard
else Failure
Auth --> App: 401 Unauthorized
App --> User: Error message
end
@enduml
Key syntax: -> sync message, --> async/return, ->> async, alt/else/end branching,
loop/end loops, opt/end optional, activate/deactivate lifeline, note left/right
Class Diagram
@startuml
' OMG-UML Monochrome Style
skinparam style strictuml
skinparam monochrome true
skinparam backgroundColor white
skinparam defaultFontName Helvetica
skinparam shadowing false
skinparam classAttributeIconSize 0
skinparam sequenceMessageAlign center
skinparam ActorBackgroundColor white
skinparam ParticipantBackgroundColor white
skinparam NoteBackgroundColor white
skinparam SequenceGroupBackgroundColor white
skinparam PackageBackgroundColor white
skinparam ClassBackgroundColor white
title Payment System
class User {
+id: UUID
+email: String
+name: String
+register()
}
class Order {
+id: UUID
+total: Decimal
+status: OrderStatus
+calculateTotal()
}
class PaymentProcessor <<interface>> {
+processPayment(amount: Decimal): Boolean
+refund(transactionId: UUID): Boolean
}
class NotificationService <<abstract>> {
#enabled: Boolean
+{abstract} send(to: String, body: String)
}
enum OrderStatus {
PENDING
CONFIRMED
SHIPPED
DELIVERED
}
User "1" -- "*" Order : places
Order ..|> PaymentProcessor
NotificationService <|-- EmailNotifier
@enduml
Key syntax: + public, - private, # protected, {abstract} abstract method,
class Foo <<interface>> (interface via text stereotype — NOT interface Foo),
class Bar <<abstract>> (abstract class — NOT abstract class Bar),
enum, relationships: -- association, *-- composition, o-- aggregation,
<|-- inheritance, ..|> realization
Activity Diagram
@startuml
title Order Processing
start
:Receive Order;
if (Payment Valid?) then (yes)
:Reserve Inventory;
if (Inventory Available?) then (yes)
:Confirm Order;
:Ship Order;
stop
else (no)
:Notify Customer;
:Cancel Order;
stop
endif
else (no)
:Reject Order;
stop
endif
@enduml
Key syntax: start/stop/end, if/then/else/endif, repeat/repeat while,
fork/fork again/end fork (parallel), split/split again/end split,
partition "name" { ... } (swimlane), :Text; action
Use Case Diagram
@startuml
title E-Commerce System
left to right direction
actor Customer
actor Admin
rectangle "E-Commerce" {
usecase "Browse Products" as UC1
usecase "Place Order" as UC2
usecase "Manage Inventory" as UC3
usecase "Process Returns" as UC4
}
Customer --> UC1
Customer --> UC2
Admin --> UC3
Admin --> UC4
UC2 ..> UC1 : <<include>>
@enduml
Key syntax: actor, usecase, rectangle/package for system boundary,
--> association, ..> dependency, <<include>> / <<extend>> stereotypes
Component Diagram
@startuml
title Microservice Architecture
package "Frontend" {
[Web App]
[Mobile App]
}
package "API Gateway" {
[Gateway]
}
package "Services" {
[User Service]
[Order Service]
[Payment Service]
}
database "PostgreSQL" as DB
cloud "Message Queue" as MQ
[Web App] --> [Gateway]
[Mobile App] --> [Gateway]
[Gateway] --> [User Service]
[Gateway] --> [Order Service]
[Order Service] --> [Payment Service]
[User Service] --> DB
[Order Service] --> DB
[Order Service] --> MQ
@enduml
Key syntax: [Component], package "name" { }, database, cloud, node,
frame, interface, ()-- required interface, --() provided interface
Deployment Diagram
@startuml
title Production Deployment
node "AWS us-east-1" {
node "VPC" {
node "Public Subnet" {
[Load Balancer]
[Bastion Host]
}
node "Private Subnet" {
node "App Server 1" {
[Application]
}
node "App Server 2" {
[Application]
}
database "RDS Primary"
}
}
cloud "CDN"
}
@enduml
Key syntax: node "name" { }, nested node, database, cloud, actor
State Diagram
@startuml
title Order Lifecycle
[*] --> Draft
Draft --> Submitted : submit()
Submitted --> Paid : processPayment()
Submitted --> Cancelled : cancel()
Paid --> Shipped : ship()
Shipped --> Delivered : confirmDelivery()
Delivered --> [*]
Cancelled --> [*]
state Paid {
[*] --> Authorizing
Authorizing --> Captured : success
Authorizing --> Failed : decline
Captured --> [*]
}
@enduml
Key syntax: [*] start/end, --> transition with optional : label,
state Name { } composite state, state "Name" as Alias
Gantt Chart
@startuml
title Project Roadmap
project starts 2025-01-06
[Design] lasts 10 days
[Development] lasts 20 days
[Development] starts at [Design]'s end
[Testing] lasts 10 days
[Testing] starts at [Development]'s end
[Deployment] lasts 3 days
[Deployment] starts at [Testing]'s end
[Frontend] lasts 12 days
[Frontend] starts at [Design]'s end
[Backend] lasts 15 days
[Backend] starts at [Design]'s end
@enduml
Key syntax: project starts YYYY-MM-DD, [Task] lasts N days,
[Task] starts at [Other]'s end, -- separator for dependency,
printscale weekly/monthly, @dailymail, @weeklymail
Mind Map
@startmindmap
title System Architecture
* Root Node
** Level 1 A
*** Level 2 A1
*** Level 2 A2
** Level 1 B
*** Level 2 B1
**** Level 3 B1a
**** Level 3 B1b
** Level 1 C
@endmindmap
Key syntax: * root, ** level 1, *** level 2, etc.
Use @startmindmap / @endmindmap (not @startuml).
Affix _ to markdown-style side notation, e.g., ***_ Right side node.
Colors: <style> * { BackgroundColor lightblue } </style>
OMG-UML / uml-diagrams.org Style Configuration (MANDATORY)
Every generated .puml file MUST include this preamble immediately after @startuml.
It locks PlantUML's rendering to the uml-diagrams.org reference style (strict OMG UML 2.x,
black-and-white Visio stencils):
' uml-diagrams.org reference style — strict OMG UML 2.x, monochrome
skinparam monochrome true
skinparam backgroundColor #FFFFFF
skinparam defaultFontName Helvetica
skinparam defaultFontSize 12
skinparam shadowing false
skinparam style strictuml
skinparam classAttributeIconSize 0
skinparam sequenceMessageAlign center
skinparam roundCorner 0
' Force every fill to white so monochrome never falls back to grey
skinparam ActorBackgroundColor #FFFFFF
skinparam ParticipantBackgroundColor #FFFFFF
skinparam NoteBackgroundColor #FFFFFF
skinparam SequenceGroupBackgroundColor #FFFFFF
skinparam PackageBackgroundColor #FFFFFF
skinparam ClassBackgroundColor #FFFFFF
skinparam ObjectBackgroundColor #FFFFFF
skinparam StateBackgroundColor #FFFFFF
skinparam UsecaseBackgroundColor #FFFFFF
skinparam ComponentBackgroundColor #FFFFFF
skinparam ActivityBackgroundColor #FFFFFF
skinparam NodeBackgroundColor #FFFFFF
skinparam DatabaseBackgroundColor #FFFFFF
skinparam StereotypeCBackgroundColor #FFFFFF
skinparam StereotypeIBackgroundColor #FFFFFF
skinparam StereotypeABackgroundColor #FFFFFF
skinparam StereotypeEBackgroundColor #FFFFFF
' Sequence diagrams — match the lifeline / activation look on uml-diagrams.org:
' * lifeline = dashed black vertical line
' * activation bar = thin WHITE rectangle with black border (NOT yellow)
skinparam SequenceLifeLineBorderColor #000000
skinparam SequenceLifeLineBackgroundColor #FFFFFF
skinparam SequenceLifeLineBorderThickness 0.75
skinparam SequenceActivationBackgroundColor #FFFFFF
skinparam SequenceActivationBorderColor #000000
skinparam SequenceArrowColor #000000
skinparam SequenceArrowThickness 0.75
skinparam SequenceBoxBackgroundColor #FFFFFF
' Default arrow / border colour everywhere
skinparam ArrowColor #000000
skinparam ArrowThickness 0.75
skinparam DefaultTextColor #000000
What each directive does (mapped to uml-diagrams.org figures):
| Directive | Effect / uml-diagrams.org reference |
|---|---|
skinparam monochrome true |
Strips all PlantUML colour themes. Matches the Visio UML 2.x stencil look used across uml-diagrams.org. |
skinparam backgroundColor #FFFFFF |
Pure white canvas — same as every figure on uml-diagrams.org. |
skinparam *BackgroundColor #FFFFFF (all element kinds) |
Forces every classifier / actor / note / package / lifeline / state / use case / component / activity / node / database fill to pure white. Eliminates the grey fills monochrome would otherwise leave. |
skinparam defaultFontName Helvetica + size 12 |
Sans-serif typography equivalent to Arial used by Visio stencils on uml-diagrams.org. |
skinparam shadowing false |
Disables drop shadows — uml-diagrams.org figures never have shadows. |
skinparam style strictuml |
Critical. Enforces text stereotypes («interface», «abstract», «enumeration») and removes the Ⓒ/Ⓘ/Ⓐ/Ⓔ circle adornments. Abstract classifier names render in italics, matching uml-diagrams.org §"Classifier". |
skinparam classAttributeIconSize 0 |
Removes the coloured visibility dots (●/◐/○). uml-diagrams.org uses +/-/#/~ text markers only. |
skinparam roundCorner 0 |
Square corners on rectangles (matches Visio stencils). Activity diagrams override locally for round-cornered actions. |
skinparam SequenceLifeLineBorderStyle (implicit dashed via strictuml) + SequenceLifeLineBorderColor #000000 |
Lifelines render as dashed black lines — exactly the lifeline notation shown on uml-diagrams.org/sequence-diagrams.html. |
skinparam SequenceActivationBackgroundColor #FFFFFF + SequenceActivationBorderColor #000000 |
Activation bar (execution specification) is a thin white rectangle with black border, per the uml-diagrams.org definition: "Execution is represented as a thin grey or white rectangle on the lifeline". |
skinparam ArrowColor #000000 + ArrowThickness 0.75 |
All arrows are thin black — matches Visio stencil hair-line strokes. |
NEVER apply colored themes (!theme blueprint, !theme cerulean, etc.), custom colors,
gradients, shadows, or decorative styling — doing so breaks compliance with the
uml-diagrams.org reference style. If a user explicitly and unambiguously requests colour,
add it on top of this preamble rather than removing the preamble.
Alternative — CSS-style Preamble (modern, backup option)
Since PlantUML 1.2019.9 the project officially recommends the CSS-like <style> block
(plantuml.com/style-evolution) as the preferred
styling mechanism — "skinparam is being phased out … users should migrate to style".
This skill ships a second, visually equivalent preamble based on <style>. Both
preambles produce the same uml-diagrams.org reference look; choose one according to the
PlantUML version available at render time:
Use the skinparam preamble (default) when… |
Use the <style> preamble (alternative) when… |
|---|---|
| You need maximum backward compatibility (PlantUML < 1.2019.9) | You are on a modern PlantUML version and want forward-looking syntax |
You want a single flat block of skinparam lines that's easy to grep |
You want CSS-style nested scoping (sequenceDiagram { lifeLine { … } }) |
You need fine-grained per-element-type *BackgroundColor knobs |
You want fewer lines and per-diagram-type cascading rules |
Do NOT mix both inside the same .puml file. Pick one preamble per diagram.
@startuml
<style>
root {
FontName Helvetica
FontSize 12
FontColor #000000
BackGroundColor #FFFFFF
LineColor #000000
LineThickness 0.75
RoundCorner 0
Shadowing 0
}
title {
FontSize 14
FontStyle bold
FontColor #000000
BackGroundColor transparent
LineColor transparent
LineThickness 0
}
note {
BackGroundColor #FFFFFF
LineColor #000000
FontColor #000000
}
sequenceDiagram {
actor { BackGroundColor #FFFFFF; LineColor #000000; FontColor #000000 }
participant { BackGroundColor #FFFFFF; LineColor #000000; FontColor #000000 }
lifeLine { BackGroundColor #FFFFFF; LineColor #000000; LineStyle 5-5; LineThickness 0.75 }
reference { BackGroundColor #FFFFFF; LineColor #000000 }
group { BackGroundColor #FFFFFF; LineColor #000000 }
arrow { LineColor #000000; LineThickness 0.75; FontColor #000000 }
}
classDiagram {
class { BackGroundColor #FFFFFF; LineColor #000000; FontColor #000000 }
arrow { LineColor #000000; LineThickness 0.75 }
}
activityDiagram {
activity { BackGroundColor #FFFFFF; LineColor #000000; FontColor #000000; RoundCorner 10 }
arrow { LineColor #000000; LineThickness 0.75 }
diamond { BackGroundColor #FFFFFF; LineColor #000000 }
}
useCaseDiagram {
actor { BackGroundColor #FFFFFF; LineColor #000000 }
usecase { BackGroundColor #FFFFFF; LineColor #000000 }
rectangle { BackGroundColor #FFFFFF; LineColor #000000 }
}
componentDiagram {
component { BackGroundColor #FFFFFF; LineColor #000000 }
package { BackGroundColor #FFFFFF; LineColor #000000 }
}
stateDiagram {
state { BackGroundColor #FFFFFF; LineColor #000000; FontColor #000000 }
arrow { LineColor #000000 }
}
</style>
' Two settings still have NO CSS equivalent yet — keep them as skinparams:
skinparam style strictuml
skinparam classAttributeIconSize 0
Notes on the CSS preamble:
LineStyle 5-5is the CSS equivalent ofskinparam *LineStyle dashed— gives the
uml-diagrams.org dashed lifeline.Shadowing 0replacesskinparam shadowing false.RoundCorner 0atrootkeeps every rectangle square;activityDiagram.activity
overrides it to10for the round-cornered action shape used on uml-diagrams.org.strictuml(removes circle stereotype icons) andclassAttributeIconSize 0(removes
attribute visibility dots) have no CSS equivalent yet as of PlantUML 1.2026.x —
keep them asskinparamlines beside the<style>block. This is the only place where
the two systems must coexist.- One example file ships with the CSS preamble:
examples/07_sequence_oauth2_css_style.puml.
All other example files keep theskinparampreamble for backward compatibility.
Error Recovery
If the PlantUML server returns an error:
1. Check for syntax errors in the .puml file
2. Validate that @startuml / @enduml are properly paired
3. Ensure diagram-type-specific syntax is correct (e.g., @startmindmap for mind maps)
4. Try the Docker fallback: docker pull plantuml/plantuml:latest && bash generate-plantuml.sh ...
5. If all else fails, offer to install Java + plantuml.jar
Output Expectations
After successful generation:
1. Show the generated PlantUML source (collapsed if long)
2. Show the rendered output (SVG inline if possible)
3. Report the saved file paths for both .puml and the rendered image
4. Offer to make adjustments