Generate architecture diagrams
Use IBM Bob to analyze the Galaxium Travels codebase and generate Mermaid UML class diagrams, sequence diagrams, and use case diagrams. Learn how to use context mentions in Ask mode to explore code and Agent mode to save the results to your repository.
Architecture diagrams give you a shared visual language for a codebase before you modify it. In this tutorial, you use Bob to read the Galaxium Travels source files and generate three types of UML diagrams: a UML class diagram, a sequence diagram, and a use case diagram. You use Ask mode to safely explore the code and generate the diagram markup, which uses Mermaid . Then you switch to Agent mode to save the diagrams to the project.
GitHub provides native support for Mermaid diagrams in Markdown
files, so you can save the generated diagrams as .md files and view them
rendered on GitHub.
In this tutorial, Bob's output may differ from the examples depending on the current state of the codebase. Use the generated markup as a starting point and refine it as needed.
Key features you learn
- Context mentions: Reference
specific files and folders in your prompts using the
@symbol. Context mentions let Bob know exactly which files to analyze for generating accurate diagrams. - Ask mode: Read and analyze code without Bob making any changes to your files.
- Agent mode: Let Bob write files autonomously to persist generated artifacts to your project.
Prerequisites
To complete this tutorial, you need the following:
- Bob IDE installed.
- Git installed locally so you can clone the Galaxium Travels example repository.
- Familiarity with the basics of using Bob. If you are new to Bob, start with the Quickstart tutorial.
Set up your workspace
Clone the Galaxium Travels repository
In your terminal, run the following command to clone the Galaxium Travels example repository:
git clone https://github.com/ibm/galaxium-travels.gitLaunch IBM Bob
Launch the IBM Bob IDE on your computer.
Open the example project
In the Bob IDE, open the galaxium-travels folder you cloned. If Bob asks "Do
you trust the authors of the files in the folder?", click Yes, I trust the
authors.
Review the README.md file in the root directory to get an overview of the application and its architecture. The Galaxium Travels app simulates a flight booking system with a React frontend, a Python FastAPI backend, and a Java inventory hold service. The codebase is intentionally complex and representative of real-world applications, making it a great candidate for generating architecture diagrams.
Open the Bob chat interface
If the chat interface is not already open, click the Bob icon in the navigation bar or use the shortcut Option + Command + B (Mac) or Ctrl + Alt + B (Windows).
Initialize project context
Bob defaults to Agent mode on startup. If you have changed modes, make sure to switch to Agent mode before running the initialization command. Bob needs to write files to set up the project context.
Enter the /init command in the chat interface input field. If you have
auto-approval disabled, Bob asks your permission to read files and write the
AGENTS.md files.
/initBob reads the relevant files in the project. Bob then generates the main
AGENTS.md file in the root directory. Bob also creates a
.bob folder that contains an AGENTS.md for each mode.
Review the generated AGENTS.md files to understand how Bob has set up the
project context and what capabilities Bob has in each mode.
Switch to Ask mode
Select Ask in the mode selector below the chat input field. You may instead
type /ask in the chat input field to switch modes.
Unlike Agent mode, Ask mode is read-only. Bob can read and analyze files but cannot create or modify anything, making it safe for code exploration.
Generate a UML class diagram
A UML class diagram maps the data model of an application: the entities (classes), their attributes, and the relationships between them. For Galaxium Travels, this covers the Python SQLAlchemy models in the backend and the Java domain classes in the inventory hold service.
Create a prompt to analyze the data models across both services and produce a
Mermaid classDiagram. Use context mentions to specify the relevant files for
Bob to analyze. By default, Bob outputs the Mermaid diagram as a rendered image.
To review the raw Mermaid markup instead, add the instruction "Output only the
Mermaid code block. Do not render the Mermaid diagram." to your prompt.
In Ask mode, enter the following prompt in the chat input field:
Analyze the data models in @booking_system_backend/models.py and the
Java domain classes in @booking_system_inventory_hold_service/src/main/java/com/galaxium/holdservice/domain.
Generate a Mermaid classDiagram that shows all classes, their attributes,
their methods (if any), and the relationships between them.
Include the BookingStatus enum.
Output the Mermaid markup. Do not render the Mermaid diagram.Bob reads both files and produces diagram markup similar to the following:
classDiagram
direction LR
%% ── Python / SQLAlchemy (booking_system_backend/models.py) ──────────
class User {
+int user_id PK
+str name
+str email
}
class Flight {
+int flight_id PK
+str origin
+str destination
+str departure_time
+str arrival_time
+int base_price
+int economy_seats_available
+int business_seats_available
+int galaxium_seats_available
}
class Booking {
+int booking_id PK
+int user_id FK
+int flight_id FK
+str status
+str booking_time
+str seat_class
+int price_paid
}
class BookingStatus {
<<enumeration>>
BOOKED = "booked"
CANCELLED = "cancelled"
CANCELED = "cancelled"
COMPLETED = "completed"
}
%% ── Java / JPA (holdservice/domain) ────────────────────────────────
class Quote {
+String quoteId PK
+Integer flightId
+String seatClass
+Integer quantity
+Integer travelerId
+String travelerName
+Long pricePerSeat
+Long totalPrice
+Instant expiresAt
+QuoteStatus status
+Instant createdAt
#onCreate() void
}
class QuoteStatus {
<<enumeration>>
CREATED
}
class Hold {
+String holdId PK
+String quoteId FK
+HoldStatus status
+Instant reservedUntil
+String externalBookingReference
+String errorMessage
+Instant createdAt
+Instant updatedAt
#onCreate() void
#onUpdate() void
}
class HoldStatus {
<<enumeration>>
HELD
EXPIRED
CONFIRMED
RELEASED
CONFIRMATION_FAILED
}
class AuditEvent {
+String eventId PK
+String entityType
+String entityId
+String eventType
+String details
+Instant createdAt
#onCreate() void
}
%% ── Relationships ───────────────────────────────────────────────────
User "1" --> "0..*" Booking : places
Flight "1" --> "0..*" Booking : booked on
Booking ..> BookingStatus : status
Quote "1" --> "0..*" Hold : generates
Quote ..> QuoteStatus : status
Hold ..> HoldStatus : status
AuditEvent ..> Quote : references entityId
AuditEvent ..> Hold : references entityIdGenerate a sequence diagram
A sequence diagram shows how components interact at runtime in a specific flow, ordered by time. The Galaxium Travels booking flow spans the React frontend, the Python FastAPI backend, and the Java inventory hold service.
Create a prompt to trace the full booking flow and produce a Mermaid
sequenceDiagram. Use context mentions to specify the relevant files for Bob to
analyze. The more specific you are in your prompt about which files to analyze
and what flow you want to diagram, the more accurate the output is.
In Ask mode, enter the following prompt in the chat input field:
Analyze the booking flow across @booking_system_frontend/src/services,
@booking_system_backend/server.py, @booking_system_backend/services/booking.py,
and @booking_system_inventory_hold_service/src/main/java/com/galaxium/holdservice/api.
Generate a Mermaid sequenceDiagram showing the complete flow for a
user booking a flight, including the quote and hold steps with the Java service.
Output the Mermaid markup. Do not render the Mermaid diagram.Bob traces the interaction chain and produces diagram markup similar to the following:
sequenceDiagram
autonumber
participant U as User (Browser)
participant FE as Frontend<br/>(api.ts)
participant PY as Python Backend<br/>(server.py)
participant BS as BookingService<br/>(booking.py)
participant QC as QuoteController<br/>(Java)
participant QS as QuoteService<br/>(Java)
participant HC as HoldController<br/>(Java)
participant HS as HoldService<br/>(Java)
participant DB as Python SQLite
participant JDB as Java SQLite
Note over U,JDB: ── Phase 1: Create Quote ──────────────────────────────────
U->>FE: createQuote({ flightId, seatClass,<br/>quantity, travelerId, travelerName })
FE->>PY: POST /quotes
PY->>QC: POST /api/v1/quotes
QC->>QS: createQuote(request)
QS->>QS: generateQuoteId() → "Q-2025-000001"
QS->>QS: pricingService.calculatePrice(flightId, seatClass)
QS->>JDB: save Quote (status=CREATED, expiresAt=+24h)
QS->>JDB: save AuditEvent (QUOTE / CREATED)
QC-->>PY: 201 Quote
Note right of PY: Returns {"error":"..."} HTTP 200<br/>if Java service unreachable
PY-->>FE: Quote JSON
FE->>FE: assertNotProxyError(response.data)
FE-->>U: quoteId
Note over U,JDB: ── Phase 2: Create Hold ───────────────────────────────────
U->>FE: createHold(quoteId)
FE->>PY: POST /quotes/{quoteId}/holds
PY->>HC: POST /api/v1/quotes/{quoteId}/holds
HC->>HS: createHold(quoteId)
HS->>JDB: findById(quoteId)
JDB-->>HS: Quote
HS->>HS: check quote not expired
HS->>HS: generateHoldId() → "H-2025-000001"
HS->>JDB: save Hold (status=HELD,<br/>reservedUntil=+15min)
HS->>JDB: save AuditEvent (HOLD / CREATED)
HC-->>PY: 201 Hold
PY-->>FE: Hold JSON
FE->>FE: assertNotProxyError(response.data)
FE-->>U: holdId
Note over U,JDB: ── Phase 3: Confirm Hold → Create Booking ─────────────────
U->>FE: confirmHold(holdId)
FE->>PY: POST /holds/{holdId}/confirm
PY->>HC: POST /api/v1/holds/{holdId}/confirm
HC->>HS: confirmHold(holdId)
HS->>JDB: findById(holdId)
JDB-->>HS: Hold
HS->>HS: check status == HELD
HS->>HS: check reservedUntil not passed
HS->>JDB: findById(hold.quoteId)
JDB-->>HS: Quote
HS->>PY: POST /internal/bookings/from-hold<br/>{ travelerId, travelerName, flightId, seatClass }
PY->>BS: book_flight(db, user_id, name,<br/>flight_id, seat_class)
BS->>DB: query Flight (check seats available)
BS->>DB: query User (validate user_id + name match)
BS->>DB: decrement {seat_class}_seats_available
BS->>DB: insert Booking (status="booked")
DB-->>BS: Booking row
BS-->>PY: BookingOut
alt booking succeeded
PY-->>HS: 200 { booking_id, ... }
HS->>JDB: update Hold (status=CONFIRMED,<br/>externalBookingReference=booking_id)
HS->>JDB: save AuditEvent (HOLD / CONFIRMED)
HC-->>PY: 200 Hold (CONFIRMED)
PY-->>FE: Hold JSON
FE->>FE: assertNotProxyError(response.data)
FE-->>U: Booking confirmed ✓
else booking failed (name mismatch / no seats / user not found)
PY-->>HS: 400 { error, error_code, details }
HS->>JDB: update Hold (status=CONFIRMATION_FAILED,<br/>errorMessage=...)
HS->>JDB: save AuditEvent (HOLD / CONFIRMATION_FAILED)
HC-->>PY: 400 Bad Request
PY-->>FE: error response
FE-->>U: Error shown to user ✗
endGenerate a use case diagram
A use case diagram identifies the actors in a system and the capabilities each
actor can exercise. Mermaid does not have a native use case diagram type, so you
represent this with a flowchart LR that groups use cases by actor.
Create a prompt to identify all actors and their use cases across the full application. Actors include user types and external systems. Use context mentions to specify the relevant files for Bob to analyze, including the frontend pages, backend REST endpoints, and MCP tools. The more specific you are in your prompt about which files to analyze, the more accurate the output is. Additionally, instruct Bob to escape curly braces in the Mermaid markup so that the Mermaid renderer does not attempt to interpret the curly braces as template syntax.
In Ask mode, enter the following prompt in the chat input field:
Analyze the full Galaxium Travels application.
Identify all actors (user types or external systems) and the use cases each
actor can perform, based on the frontend pages, backend REST endpoints,
and MCP tools.
Generate a Mermaid flowchart LR that represents this as a use case diagram,
grouping use cases under their respective actors using subgraphs.
Escape curly braces in Mermaid markup so that the Mermaid renderer does not
attempt to interpret the curly braces as template syntax.
Output the Mermaid markup. Do not render the Mermaid diagram.Bob analyzes the application and produces diagram markup similar to the following:
flowchart LR
subgraph Traveller["👤 Traveller (Browser)"]
T1[Browse available flights]
T2[Search flights by origin / destination]
T3[Filter flights by date, price, seat class,\nduration, route category, time period]
T4[Register account]
T5[Sign in with name and email]
T6[Select seat class\neconomy / business / galaxium]
T7[Get price quote]
T8[Place seat hold - 15-minute timer]
T9[Confirm hold and create booking]
T10[Release hold]
T11[View active bookings]
T12[View past bookings]
T13[Cancel booking]
T14[View pending holds with countdown]
T15[Dismiss expired hold]
end
subgraph AIAgent["🤖 AI Agent (MCP Client)"]
A1[list_flights]
A2[register_user]
A3[get_user_id]
A4[book_flight]
A5[get_bookings]
A6[cancel_booking]
end
subgraph JavaService["☕ Java Hold Service\n(Internal System)"]
J1[Confirm hold via POST /internal/bookings/from-hold]
J2[Auto-expire holds after timeout]
end
subgraph RestAPI["🐍 Python REST API\n(External Consumers / Swagger)"]
R1[GET /flights — list and filter flights]
R2[POST /register — register user]
R3[GET /user — look up user by name and email]
R4[POST /book — book a flight]
R5[GET /bookings/{user_id} — get user bookings]
R6[POST /cancel/{booking_id} — cancel booking]
R7[POST /quotes — create quote proxy]
R8[GET /quotes/{id} — get quote proxy]
R9[POST /quotes/{id}/holds — create hold proxy]
R10[GET /holds/{id} — get hold proxy]
R11[POST /holds/{id}/confirm — confirm hold proxy]
R12[POST /holds/{id}/release — release hold proxy]
R13[GET / — health check]
end
Traveller -->|uses frontend which calls| RestAPI
AIAgent -->|MCP over HTTP at /mcp| RestAPI
JavaService -->|calls back via internal endpoint| RestAPISave diagrams to the repository
Switch Bob to Agent mode and ask it to save the diagrams you generated into the
repository. Each diagram is saved as a Markdown file in a new
docs/architecture/ folder.
Switch to Agent mode
Select Agent in the mode selector, or type /agent in the chat input field.
Save all three diagrams
Ask Bob to create the architecture documentation files.
Create a docs/architecture/ folder in the repository root.
Save each of the three diagrams we generated as individual Markdown files:
- class-diagram.md — the UML class diagram
- sequence-diagram.md — the booking flow sequence diagram
- use-case-diagram.md — the use case flowchart
Each file should have a short title heading, the Mermaid code block we
generated, and a brief description of the diagram.Bob creates the three files. Click Approve and Save for each file Bob writes.
Verify the output
Open each file in the Bob file explorer to confirm the Mermaid fenced code blocks are present. You have these options for verifying the diagrams:
-
Ask Bob to show you a preview of the Markdown file.
In the chat input field, enter the following prompt:
Show me a preview of docs/architecture/class-diagram.mdBob renders the Markdown file, including the Mermaid diagram, in the chat interface. Click on the rendered diagram to open it in a larger view.
You can do this for each of the three files to see all the diagrams rendered.
-
Paste the diagram markup into Mermaid Live Editor to preview the rendered diagram.
-
Commit and push the changes to a GitHub repository. Then view the files on GitHub to see the rendered diagrams.
Troubleshooting
Bob generates Mermaid markup that does not compile
Mermaid's parser is strict. Even a single invalid character, an unsupported keyword, or a missing newline can cause a diagram to silently fail or throw a parse error. Use the following approach to diagnose and fix the problem.
Identify the failing line
When Bob produces a parse error, the output includes the line number and a snippet of the offending code.
If Bob doesn't output a parser error, paste the markup into Mermaid Live Editor. The editor highlights the offending line and shows the parser error, which can help you identify the issue.
You can also visually inspect the markup for common issues such as unescaped special characters in labels, unclosed subgraphs, or syntax errors in arrows.
| Symptom | Likely cause | Fix |
|---|---|---|
Parse error near { or } | Curly braces unescaped in flowchart or classDiagram node labels | Replace { with { and } with }, or reword the label |
Parse error near ( or ) | Parentheses in a node ID | Wrap the label in quotes: A["label (note)"] |
Unexpected end or subgraph error | Subgraph not closed | Ensure every subgraph block has a matching end |
| Arrow type not recognized | Wrong arrow syntax for the diagram type | --> is for flowchart; classDiagram uses -->, ..>, --|> etc.; sequenceDiagram uses ->>, -->> |
| Node defined but not connected | Orphan node causes no error but can confuse some renderers | Connect the node or remove it |
| Diagram renders partially then stops | Label contains a bare " character | Escape quotes inside labels: A["it\'s a label"] |
Ask Bob to fix the issue
Give Bob the parser error and the failing line. Then ask Bob to fix specific lines.
For example:
The Mermaid classDiagram fails to parse with this error:
Parse error on line 42: ...unexpected token 'NEWLINE'
Here is the relevant block:
Booking ..> BookingStatus : status (active)
Fix the syntax so it compiles without changing the diagram structure.Bob can target a narrow fix without regenerating content you already reviewed.
Ask Bob to validate before outputting
If you are regenerating a diagram from scratch, add an explicit validation instruction to the prompt:
Before outputting the Mermaid block, mentally parse it and confirm every node ID
is valid, every subgraph is closed, and all special characters in labels are escaped.Narrow the scope when the diagram is large
If a diagram with many nodes keeps producing invalid markup, ask Bob to generate it in sections, such as the Python models first and then the Java models. Afterwards, ask Bob to assemble the blocks. Smaller generations are easier for Bob to validate and easier for you to diff.
Next steps
In this tutorial, you used context mentions and Ask mode to explore the Galaxium Travels codebase and generate three types of architecture diagrams with Bob, then used Agent mode to save them to the repository. Continue with the following resources:
- Explore the Bob get started tutorials to learn more about Bob's capabilities with the Galaxium Travels app.
- Follow the Plan and implement complex features tutorial to use the Plan → Agent mode workflow to add new functionality.
- Read Bob best practices to learn effective prompting strategies for using Bob.
Inspect an unfamiliar codebase
Use IBM Bob to rapidly understand an unfamiliar application, such as its purpose, project structure, architecture, tech stack, key components, test coverage, and deployment model. You can do this without relying on outdated documentation or waiting for teammates.
Audit code and generate reports
Use IBM Bob to create a reusable security audit skill, scan an application against OWASP ASVS requirements, and generate SARIF and OSCAL reports that developers and AI agents can act on.