20 — LangGraph Nodes, Edges and Routing¶
Understand how LangGraph nodes, edges, conditional routing, and control-flow patterns are used to build explicit, predictable, and production-ready AI workflows and Agents.
📖 Overview¶
LangGraph applications are built around a simple but powerful execution model:
A node performs work.
An edge determines what happens next.
A routing decision determines which path should be followed when execution is dynamic.
This provides an explicit execution model for systems containing:
Sequential Processing
Conditional Branching
Loops
Parallel Execution
Tool Calling
Validation
Human Approval
Fallbacks
Retries
Agent Reasoning
A production graph can therefore be represented as:
┌──────────────┐
│ START │
└──────┬───────┘
↓
┌──────────────┐
│ Validate │
└──────┬───────┘
↓
┌──────────────┐
│ Analyze │
└──────┬───────┘
↓
┌────────────┐
│ Route │
└───┬────┬───┘
│ │
RAG│ │Tool
↓ ↓
RAG Tool
│ │
└─┬──┘
↓
┌──────────────┐
│ Validate │
└──────┬───────┘
↓
END
The goal is not simply to create graphs.
The goal is to create clear, testable, observable, and controlled execution paths.
🎯 Learning Objectives¶
After completing this chapter, you will be able to:
- Understand LangGraph nodes
- Understand LangGraph edges
- Design sequential graph execution
- Implement conditional routing
- Design routing functions
- Understand static and dynamic transitions
- Build loops
- Build fallback paths
- Design retry routing
- Implement parallel branches conceptually
- Understand state-aware routing
- Separate routing from business logic
- Design production routing strategies
- Test graph paths
- Identify common routing anti-patterns
- Design reliable agent execution paths
1. Nodes and Edges¶
The fundamental LangGraph model is:
A node performs work:
An edge determines what happens next:
Together:
2. What Is a Node?¶
A node is a unit of computation within the graph.
Examples:
validate_request
classify_request
retrieve_documents
generate_response
call_tool
validate_result
human_review
A node typically:
3. Basic Node Example¶
from typing import TypedDict
class State(TypedDict):
message: str
def process_message(state: State):
return {
"message": state["message"].upper()
}
The node receives:
and returns:
4. Node Registration¶
Conceptually:
The graph now knows that:
is an executable node.
5. Node Naming¶
Use meaningful node names.
Good:
Avoid:
Meaningful names improve:
6. Node Responsibility¶
A node should have a focused responsibility.
Good:
Bad:
Prefer:
over:
7. Node Granularity¶
Nodes should not be too large or too small.
Too Large¶
Problems:
Too Small¶
Problems:
Use meaningful capability boundaries.
8. Node Contracts¶
A production node should have a clear contract:
Example:
Document these contracts.
9. Node Purity¶
Where possible, keep simple transformation nodes deterministic.
Example:
This makes the node:
10. Nodes With Side Effects¶
Some nodes interact with external systems:
These nodes need stronger reliability controls.
11. Node Failure¶
A node may fail because of:
Timeout
Network Failure
Rate Limit
Validation Error
Provider Error
Business Error
Dependency Failure
The graph should determine whether to:
12. What Is an Edge?¶
An edge defines a transition between graph nodes.
Example:
Edges:
13. Static Edges¶
A static edge always follows the same path.
Example:
Whenever:
completes:
is the next destination.
14. Sequential Graph¶
flowchart TD
A[START] --> B[Validate]
B --> C[Retrieve]
C --> D[Generate]
D --> E[END]
This is the simplest graph pattern.
15. Sequential Execution¶
A sequential graph executes:
Use this when the execution path is known.
Examples:
or:
16. Conditional Routing¶
Real applications frequently need decisions.
Example:
The next node depends on state.
17. Conditional Edge¶
Conceptually:
Then the graph maps the routing result to a destination.
The exact API should be verified against the LangGraph version used by the project.
18. Conditional Graph¶
flowchart TD
A[Classify] --> B{Intent}
B -->|Knowledge| C[RAG]
B -->|Action| D[Tool]
C --> E[END]
D --> E
19. Routing Function¶
A routing function should ideally answer one question:
Example:
def route(state):
if state["status"] == "complete":
return "finish"
if state["needs_tool"]:
return "tool"
return "reason"
Avoid putting large business processes inside the routing function.
20. Routing vs Business Logic¶
Poor:
Better:
Routing should primarily make the transition decision.
21. Routing Based on State¶
State can determine the next transition.
Example:
Architecture:
22. Routing Based on Intent¶
Example:
Possible intents:
Then:
Intent
├── knowledge → RAG
├── customer → Customer Tool
├── transaction → Transaction Tool
├── support → Ticket Tool
└── unknown → Human
23. Intent Router¶
flowchart TD
A[User Request] --> B[Intent Classification]
B --> C{Intent}
C -->|Knowledge| D[RAG]
C -->|Customer| E[Customer API]
C -->|Transaction| F[Transaction Tool]
C -->|Support| G[Ticket Tool]
C -->|Unknown| H[Human Review]
24. Routing Based on Confidence¶
An LLM or classifier may return:
Routing can use a threshold:
Example:
The threshold should be determined through evaluation rather than chosen arbitrarily.
25. Confidence Routing¶
flowchart TD
A[Classifier] --> B{Confidence}
B -->|High| C[Automatic Processing]
B -->|Low| D[Human Review]
C --> E[END]
D --> E
26. Routing Based on Risk¶
Agent systems should route based on action risk.
Example:
while:
27. Risk Router¶
flowchart TD
A[Agent Decision] --> B[Risk Classification]
B --> C{Risk Level}
C -->|Low| D[Execute]
C -->|Medium| E[Additional Validation]
C -->|High| F[Human Approval]
D --> G[END]
E --> G
F --> G
28. Routing Based on Tool Availability¶
An agent may require a capability that is temporarily unavailable.
Example:
This prevents blind execution against unavailable dependencies.
29. Availability Routing¶
flowchart TD
A[Tool Required] --> B{Available?}
B -->|Yes| C[Execute Tool]
B -->|No| D[Fallback]
C --> E[END]
D --> E
30. Routing Based on Validation¶
Example:
31. Validation Router¶
flowchart TD
A[Generate] --> B[Validate]
B --> C{Valid?}
C -->|Yes| D[END]
C -->|No| E[Correct]
E --> A
This creates a loop.
32. Loops¶
Loops are useful for:
Example:
33. Bounded Loop¶
Never assume an agent will naturally stop.
Use:
Example:
def route_after_validation(state):
if state["valid"]:
return "finish"
if state["attempts"] >= 3:
return "fallback"
return "correct"
34. Bounded Loop Diagram¶
flowchart TD
A[Generate] --> B[Validate]
B --> C{Valid?}
C -->|Yes| D[END]
C -->|No| E{Attempts < 3?}
E -->|Yes| F[Correct]
F --> A
E -->|No| G[Fallback]
G --> D
35. Retry Routing¶
Retries should distinguish between:
and:
Examples:
Retryable¶
Non-Retryable¶
36. Retry Router¶
flowchart TD
A[Node Failure] --> B{Retryable?}
B -->|Yes| C{Attempts Remaining?}
C -->|Yes| D[Retry]
C -->|No| E[Fallback]
B -->|No| F[Fail / Escalate]
D --> A
37. Backoff¶
Repeated retries can overload dependencies.
Prefer:
Conceptually:
Use appropriate exponential backoff and jitter where supported.
38. Error Routing¶
Different failures may require different destinations.
Failure
├── Timeout → Retry
├── Unauthorized → Reject
├── Validation → Correct
├── Business Error → Fallback
└── Unknown → Escalate
39. Error Router¶
flowchart TD
A[Failure] --> B{Error Type}
B -->|Timeout| C[Retry]
B -->|Unauthorized| D[Reject]
B -->|Validation| E[Correct]
B -->|Business| F[Fallback]
B -->|Unknown| G[Escalate]
40. Fan-Out¶
Some tasks can be executed independently.
Example:
These branches can conceptually execute independently.
41. Fan-Out Architecture¶
flowchart TD
A[Start] --> B[Parallel Routing]
B --> C[Document Search]
B --> D[Customer Search]
B --> E[External Search]
C --> F[Merge]
D --> F
E --> F
F --> G[Reason]
42. Fan-In¶
Fan-in combines results from multiple branches.
The state merge semantics must be clearly defined.
43. Parallel State Updates¶
Example:
Then:
44. Reducers and Fan-In¶
Reducers can be useful when multiple branches update the same state field.
Conceptually:
The merge strategy should be explicitly defined.
45. Sequential vs Parallel¶
Sequential¶
Advantages:
Parallel¶
Advantages:
Trade-offs:
46. Dynamic Routing¶
Dynamic routing means:
Example:
This is particularly useful for:
47. Static vs Dynamic Routing¶
| Routing | Description | Example |
|---|---|---|
| Static | Fixed transition | A → B |
| Conditional | Based on state | A → B/C |
| Dynamic | Runtime destination | A → selected capability |
| Loop | Returns to previous node | A → B → A |
| Fan-out | Multiple branches | A → B/C/D |
| Fan-in | Merge branches | B/C/D → E |
48. Router Node Pattern¶
A useful architecture is:
The router should determine:
while the destination node performs:
49. Router Architecture¶
flowchart TB
A[Request] --> B[Router]
B --> C[RAG]
B --> D[Tool]
B --> E[Workflow]
B --> F[Human Review]
C --> G[Response]
D --> G
E --> G
F --> G
50. LLM-Based Routing¶
An LLM can help determine the route.
Example:
Example output:
The graph should validate the route before executing it.
51. Structured Routing¶
Prefer structured routing output:
over unrestricted natural-language routing.
Example:
Then:
52. LLM Router Security¶
Do not allow an LLM to dynamically select arbitrary executable code.
Bad:
Better:
53. Route Allowlist¶
Example:
Then:
This creates a deterministic boundary around model-generated decisions.
54. Routing and Authorization¶
Routing does not equal authorization.
Example:
does not mean:
Instead:
55. Routing + Policy¶
flowchart TD
A[LLM Router] --> B[Route Validation]
B --> C[Authorization]
C --> D{Allowed?}
D -->|Yes| E[Target Node]
D -->|No| F[Reject]
E --> G[END]
F --> G
56. Routing and Risk¶
The route can influence risk.
Example:
while:
The graph can therefore route high-risk actions through additional controls.
57. Risk-Aware Routing¶
This is preferable to allowing:
58. Nested Routing¶
Complex graphs may route multiple times.
Example:
Architecture:
flowchart TD
A[Main Router] --> B[Agent]
B --> C[Tool Router]
C --> D[Search]
C --> E[Customer API]
C --> F[Ticket API]
Avoid excessive routing layers.
59. Routing Depth¶
Too many routing layers can produce:
Problems:
Prefer clear hierarchical routing.
60. Hierarchical Routing¶
A cleaner model:
Application Router
├── Knowledge
├── Support
└── Operations
Operations Router
├── Customer
├── Transaction
└── Ticket
This creates bounded routing domains.
61. Routing and Subgraphs¶
Subgraphs can encapsulate routing complexity.
This improves modularity.
62. Routing Contract¶
Every route should have:
Example:
Route:
transaction
Destination:
transaction_workflow
Requires:
transaction_id
authorization
Failure:
human_review
63. Routing Observability¶
Track:
Example:
64. Routing Metrics¶
Useful metrics:
Route Selection Accuracy
Route Frequency
Route Failure Rate
Fallback Rate
Human Escalation Rate
Routing Latency
Invalid Route Rate
65. Routing Evaluation¶
For LLM-based routers, create a test set:
Example:
| Query | Expected | Actual | Result |
|---|---|---|---|
| Policy question | RAG | RAG | ✅ |
| Customer lookup | Customer | Customer | ✅ |
| Refund request | Transaction | Transaction | ✅ |
| Unknown request | Human | RAG | ❌ |
66. Route Regression Testing¶
When changing:
rerun the routing dataset.
Do not assume routing behavior remains unchanged.
67. Routing Failures¶
Common routing failures:
A robust system should have:
for unresolved decisions.
68. Fallback Routing¶
flowchart TD
A[Router] --> B{Valid Route?}
B -->|Yes| C[Target Node]
B -->|No| D[Fallback]
D --> E[Human / Safe Response]
C --> F[END]
E --> F
69. Safe Default¶
When routing is uncertain:
Do not automatically select:
as the default.
70. Routing Timeouts¶
A router itself may call:
Therefore routing may require:
Example:
71. Routing Cost¶
LLM-based routing adds:
For simple routing, deterministic logic may be preferable.
Example:
or:
Use LLM routing when its flexibility provides meaningful value.
72. Deterministic vs LLM Router¶
Deterministic¶
LLM-Based¶
A hybrid approach is often effective:
73. Hybrid Router¶
flowchart TD
A[Request] --> B{Simple Rule?}
B -->|Yes| C[Deterministic Route]
B -->|No| D[LLM Router]
D --> E[Route Validation]
C --> F[Target]
E --> F
74. Routing with RAG¶
A production AI application may route:
75. RAG Router¶
flowchart TD
A[Query] --> B[Router]
B --> C[Internal RAG]
B --> D[External Search]
B --> E[Tool]
C --> F[Generate]
D --> F
E --> F
F --> G[Validate]
G --> H[END]
76. Routing with Human Review¶
A safe architecture:
This is especially useful for:
77. Production Routing Architecture¶
flowchart TB
A[User Request] --> B[Input Validation]
B --> C[Router]
C --> D{Route}
D -->|Knowledge| E[RAG]
D -->|Support| F[Support Workflow]
D -->|Operation| G[Operations Subgraph]
G --> H[Risk Check]
H --> I{Risk}
I -->|Low| J[Tool Gateway]
I -->|High| K[Human Approval]
K --> J
E --> L[Response Validation]
F --> L
J --> L
L --> M[END]
78. Routing in Agent Systems¶
An agent can use routing at multiple levels:
The architecture should keep each routing responsibility explicit.
79. Routing as a State Machine¶
A graph can be viewed as a state machine:
Example:
or:
80. State Machine Example¶
stateDiagram-v2
[*] --> REQUESTED
REQUESTED --> ANALYZING
ANALYZING --> EXECUTING
EXECUTING --> VALIDATING
VALIDATING --> COMPLETED
VALIDATING --> RETRYING
RETRYING --> EXECUTING
RETRYING --> FAILED
COMPLETED --> [*]
FAILED --> [*]
81. Explicit Status Fields¶
For complex workflows, state may contain:
Possible values:
Status should be controlled and validated.
82. Routing by Status¶
def route_status(state):
status = state["status"]
routes = {
"requested": "analyze",
"executing": "execute",
"validating": "validate",
"waiting_for_approval": "approval"
}
return routes.get(
status,
"fallback"
)
Use explicit allowlists.
83. State Machine + Agent¶
This provides:
84. Production Design Principle¶
A good production architecture often looks like:
rather than:
85. Routing Anti-Pattern — Business Logic in Router¶
Avoid:
def route(state):
customer = get_customer()
balance = calculate_balance(customer)
send_notification()
return "..."
Prefer:
86. Routing Anti-Pattern — Arbitrary Destinations¶
Avoid:
Prefer:
87. Routing Anti-Pattern — No Fallback¶
Avoid:
Prefer:
88. Routing Anti-Pattern — Unbounded Loops¶
Avoid:
Use:
89. Routing Anti-Pattern — Too Many Routers¶
Avoid:
Prefer:
90. Routing Anti-Pattern — No Evaluation¶
Do not assume:
Measure:
91. Production Routing Checklist¶
Nodes¶
- [ ] Meaningful names
- [ ] Clear responsibilities
- [ ] Small contracts
- [ ] Testable logic
- [ ] Explicit side effects
Edges¶
- [ ] Explicit transitions
- [ ] Clear termination
- [ ] Conditional routing
- [ ] Fallback paths
- [ ] Bounded loops
Routing¶
- [ ] Route allowlist
- [ ] Validation
- [ ] Authorization
- [ ] Confidence handling
- [ ] Safe fallback
- [ ] Timeout
- [ ] Evaluation
Reliability¶
- [ ] Retry policy
- [ ] Backoff
- [ ] Idempotency
- [ ] Failure routing
- [ ] Circuit breaking
Operations¶
- [ ] Route metrics
- [ ] Route tracing
- [ ] Execution logs
- [ ] Graph versioning
- [ ] Regression tests
92. Key Takeaways¶
- Nodes represent meaningful units of computation.
- Edges define execution transitions.
- Static edges represent deterministic flow.
- Conditional edges enable state-aware routing.
- Routing functions should primarily determine the next destination.
- Business logic should remain inside dedicated nodes.
- Routing can be based on intent, confidence, risk, availability, validation, or execution status.
- Loops are useful but must always be bounded.
- Retry routing should distinguish transient failures from permanent failures.
- Fan-out enables independent parallel work.
- Fan-in combines results from multiple branches.
- Reducers can define how shared state is merged.
- LLM-based routing should use structured outputs and allowlists.
- Routing is not authorization.
- High-risk routes should pass through deterministic policy controls.
- Safe fallbacks are essential for ambiguous or invalid routing.
- Routing logic should be evaluated with representative datasets.
- Graph routing should remain observable and versioned.
- Hierarchical routing can reduce complexity in large systems.
- Subgraphs can encapsulate bounded routing domains.
- Deterministic routing is often preferable when the rules are known.
- LLM routing is valuable when semantic flexibility is required.
- A hybrid deterministic + LLM routing architecture can provide both flexibility and control.
📝 Quick Revision Notes¶
Node¶
Static Edge¶
Conditional Edge¶
Loop¶
Fan-Out¶
Fan-In¶
Production Router¶
Agent Routing¶
❓ Interview Questions¶
Beginner¶
- What is a LangGraph node?
- What is a LangGraph edge?
- What is the difference between a static and conditional edge?
- What is a routing function?
- Why should nodes have clear responsibilities?
- What is conditional routing?
- What is a loop in LangGraph?
- What is fan-out?
- What is fan-in?
- Why is a fallback route important?
Intermediate¶
- How would you design a routing function?
- How would you route based on state?
- How would you route based on intent?
- How would you route based on confidence?
- How would you implement bounded retries?
- How would you distinguish retryable and non-retryable failures?
- How would you implement fan-out and fan-in?
- How would reducers help with parallel execution?
- How would you implement an LLM-based router?
- How would you validate an LLM-generated route?
- How would you secure dynamic routing?
- How would you test all graph paths?
- How would you monitor routing decisions?
- How would you combine deterministic and LLM-based routing?
Advanced¶
- Design a production routing architecture for an enterprise AI platform.
- How would you design hierarchical routing?
- How would you prevent arbitrary LLM-generated routes?
- How would you implement risk-aware routing?
- How would you design routing for 100+ enterprise tools?
- How would you evaluate an LLM router?
- How would you prevent routing regressions after a model upgrade?
- How would you design safe fallback behavior?
- How would you handle concurrent fan-out branches?
- How would you design state merging for parallel execution?
- How would you prevent infinite graph loops?
- How would you combine routing with authorization?
- How would you design routing across LangGraph and LlamaIndex?
- How would you structure routing using subgraphs?
- How would you monitor route selection accuracy in production?
- When should you avoid LLM-based routing entirely?
🛠️ Practical Exercise¶
Build a customer-support router.
The system should support:
Architecture:
flowchart TD
A[START] --> B[Validate]
B --> C[Classify]
C --> D{Intent}
D -->|Knowledge| E[RAG]
D -->|Customer| F[Customer API]
D -->|Transaction| G[Transaction Workflow]
D -->|Support| H[Ticket Workflow]
D -->|Unknown| I[Human Review]
E --> J[Validate Response]
F --> J
G --> J
H --> J
I --> J
J --> K[END]
Add:
🧪 Routing Evaluation Exercise¶
Create:
For each query define:
Run the router and measure:
Create a report:
🚀 Failure Routing Exercise¶
Build a graph that handles:
Expected behavior:
Timeout
↓
Retry
Rate Limit
↓
Backoff
↓
Retry
Unauthorized
↓
Reject
Validation
↓
Correct
Business Error
↓
Fallback
Unknown
↓
Escalate
🏢 Enterprise Architecture Challenge¶
Design a routing platform supporting:
100+ Tools
10+ AI Capabilities
Multiple RAG Systems
Multiple LLM Providers
Human Approval
Multi-Tenancy
Use:
Ensure:
🧠 Final Architecture Challenge¶
Design an enterprise AI router:
flowchart TB
A[User Request] --> B[Input Validation]
B --> C[Deterministic Rules]
C --> D{Known Pattern?}
D -->|Yes| E[Known Route]
D -->|No| F[LLM Router]
F --> G[Structured Route]
G --> H[Route Allowlist]
H --> I[Authorization]
I --> J[Risk Policy]
J --> K{Risk}
K -->|Low| L[Target Node]
K -->|High| M[Human Approval]
M --> L
L --> N[Execution]
N --> O[Validation]
O --> P[END]
Answer:
Which routes are deterministic?
Which decisions require the LLM?
Where is authorization enforced?
Where is risk evaluated?
What happens when routing fails?
How do you prevent arbitrary tool execution?
How do you evaluate route accuracy?
How do you monitor routing drift?
How do you version routing logic?
📚 References & Further Reading¶
Recommended areas for further study:
- LangGraph Nodes
- LangGraph Edges
- Conditional Routing
- Dynamic Routing
- Graph State
- Reducers
- Parallel Execution
- Fan-Out / Fan-In
- Agent Routing
- LLM-Based Routing
- Tool Routing
- Workflow Routing
- Human-in-the-Loop
- Agent Guardrails
- Agent Authorization
- Graph Observability
- Agent Evaluation
- Durable Execution
- Enterprise Workflow Architecture
- State Machine Design
LangGraph's graph construction and routing APIs evolve over time. Verify the exact node, edge, conditional-routing, state, reducer, and execution APIs against the official documentation for the LangGraph version used in your project.
🧭 Chapter Navigation¶
⬅️ Previous: 19. LangGraph State and Checkpointing
📚 Part VIII Index: AI Engineering Frameworks & Tooling
➡️ Next: 21. LangGraph Human In The Loop
Enterprise AI Engineering Handbook
Building Production-Grade Enterprise AI Systems — One Chapter at a Time.