Skip to content

Update docs for new Flows transition_to field #44

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Dec 6, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
70 changes: 61 additions & 9 deletions api-reference/utilities/flows/pipecat-flows.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -221,10 +221,8 @@ await flow_manager.set_node("start", create_start_node())

</CodeGroup>

## Function Handlers

<ResponseField name="Node Functions" type="concept">
Functions that execute operations within a state without causing transitions.
Functions that execute operations within a state and optionally transition to a new state.

<CodeBlock>

Expand All @@ -240,19 +238,20 @@ async def process_data(args: FlowArgs) -> FlowResult:
"processed_data": result
}

# Node configuration
# Node configuration with transition
{
"type": "function",
"function": {
"name": "process_data",
"handler": process_data, # Handler required for node functions
"handler": process_data,
"description": "Process user data",
"parameters": {
"type": "object",
"properties": {
"data": {"type": "string"}
}
}
},
"transition_to": "next_node" # Optional: Specify next node
}
}
```
Expand All @@ -262,7 +261,7 @@ async def process_data(args: FlowArgs) -> FlowResult:
</ResponseField>

<ResponseField name="Edge Functions" type="concept">
Functions that create transitions between nodes. No handler needed - the name must match a target node.
Functions that create transitions between nodes. Use transition_to to specify the target node.

<CodeBlock>

Expand All @@ -271,9 +270,10 @@ async def process_data(args: FlowArgs) -> FlowResult:
{
"type": "function",
"function": {
"name": "next_node", # Must match an existing node name
"name": "next_step",
"description": "Transition to next node",
"parameters": {"type": "object", "properties": {}}
"parameters": {"type": "object", "properties": {}},
"transition_to": "target_node" # Required: Specify target node
}
}
```
Expand All @@ -282,6 +282,58 @@ async def process_data(args: FlowArgs) -> FlowResult:

</ResponseField>

### Function Properties

<ResponseField name="handler" type="Optional[Callable]">
Async function that processes data within a node
</ResponseField>

<ResponseField name="transition_to" type="Optional[str]">
Name of the node to transition to after function execution
</ResponseField>

### Transition Types

<CodeGroup>
```python Handler with Transition
# Process data and transition
{
"type": "function",
"function": {
"name": "save_order",
"handler": save_order_handler,
"parameters": {...},
"transition_to": "confirmation"
}
}
```

```python Pure Transition
# Transition only
{
"type": "function",
"function": {
"name": "go_to_checkout",
"parameters": {},
"transition_to": "checkout"
}
}
```

```python Handler Only
# Process without transition
{
"type": "function",
"function": {
"name": "validate_input",
"handler": validate_handler,
"parameters": {...}
}
}
```

</CodeGroup>

### Handler Signatures

<CodeGroup>
Expand Down
155 changes: 78 additions & 77 deletions guides/pipecat-flows.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,58 @@ pip install "pipecat-ai[daily,google,deepgram]" # For Google

# Core Concepts

## Designing Conversation Flows

Functions in Pipecat Flows serve two key purposes: interfacing with external systems and advancing the conversation.

### Function Handlers

When you need to collect data, validate input, or retrieve information, add a handler to your function. These handlers are async functions that execute when the LLM calls the function, allowing you to interact with databases, APIs, or other external services:

```python
# Example function handler
async def check_availability(args: FlowArgs) -> FlowResult:
"""Check restaurant availability for the requested time."""
date = args["date"]
time = args["time"]
party_size = args["party_size"]

# Interface with reservation system
available = await reservation_system.check_availability(date, time, party_size)
return {"status": "success", "available": available}
```

### Transitioning Between Nodes

To advance the conversation, Pipecat Flows offers two approaches based on your flow type:

For static flows, use the `transition_to` property to specify the next node:

```python
{
"type": "function",
"function": {
"name": "confirm_reservation",
"handler": save_reservation, # Process the reservation
"parameters": {...},
"transition_to": "send_confirmation" # Move to confirmation node
}
}
```

For dynamic flows, use a transition callback to determine the next node at runtime:

```python
async def handle_transitions(function_name: str, args: Dict, flow_manager):
if function_name == "check_availability":
if args["available"]:
await flow_manager.set_node("collect_details", create_details_node())
else:
await flow_manager.set_node("suggest_alternatives", create_alternatives_node())
```

You can combine both approaches: use handlers to process data and transitions to advance the conversation, creating flows that are both functional and conversational.

## Node Structure

Each node in your flow represents a conversation state and consists of three main components:
Expand All @@ -82,15 +134,15 @@ Messages set the context for the LLM at each state:

Functions come in two types, each serving a different purpose:

#### Node Functions
#### Node Functions with Transitions

Execute operations within the current state:
Process data and optionally transition to a new state:

```python
from pipecat_flows import FlowArgs, FlowResult

async def select_size(args: FlowArgs) -> FlowResult:
"""Handle pizza size selection."""
"""Handle pizza size selection and transition."""
size = args["size"]
return {
"status": "success",
Expand All @@ -102,14 +154,15 @@ async def select_size(args: FlowArgs) -> FlowResult:
"type": "function",
"function": {
"name": "select_size",
"handler": select_size, # Handler required for node functions
"handler": select_size,
"description": "Select pizza size",
"parameters": {
"type": "object",
"properties": {
"size": {"type": "string", "enum": ["small", "medium", "large"]}
}
}
},
"transition_to": "toppings" # Optional: Specify next node
}
}
```
Expand All @@ -122,9 +175,10 @@ Create transitions between states:
{
"type": "function",
"function": {
"name": "next_node", # Must match a node name
"name": "next_step",
"description": "Move to next state",
"parameters": {"type": "object", "properties": {}}
"parameters": {"type": "object", "properties": {}},
"transition_to": "target_node" # Required: Specify target node
}
}
```
Expand All @@ -148,33 +202,7 @@ Actions execute during state transitions:
]
```

## Function Types

### Type Safety

Pipecat Flows provides type definitions for function handlers:

```python
from pipecat_flows import FlowArgs, FlowResult

async def my_handler(args: FlowArgs) -> FlowResult:
"""Type-safe function handler."""
return {
"status": "success",
"data": process_args(args)
}
```

### Handler Implementation

Function handlers should:

- Be async functions
- Accept FlowArgs (or no args)
- Return FlowResult
- Include status in response

## Provider Support
## LLM Provider Support

Pipecat Flows automatically handles format differences between LLM providers:

Expand Down Expand Up @@ -266,44 +294,41 @@ flow_config = {
{
"type": "function",
"function": {
"name": "choose_pizza", # Edge function
"name": "choose_pizza",
"description": "User wants pizza",
"parameters": {"type": "object", "properties": {}}
"parameters": {"type": "object", "properties": {}},
"transition_to": "pizza_order" # Specify transition
}
},
{
"type": "function",
"function": {
"name": "select_size", # Node function
"name": "select_size",
"handler": select_size,
"description": "Select pizza size",
"parameters": {
"type": "object",
"properties": {
"size": {"type": "string", "enum": ["small", "medium", "large"]}
}
}
},
"transition_to": "toppings" # Optional transition after processing
}
}
],
"pre_actions": [
{
"type": "tts_say",
"text": "Welcome! What would you like to order?"
}
]
}
}
}
```

### Best Practices
### Transition Best Practices

- Define complete conversation paths upfront
- Use clear, descriptive node names
- Keep node messages focused on current state
- Ensure edge functions match valid node names
- Test all paths and transitions
- Use `transition_to` to make state changes explicit
- Combine handlers with transitions when appropriate
- Keep transitions focused on single responsibilities
- Use clear, descriptive names for target nodes
- Validate all transition targets exist
- Test both successful and failed transitions

## Dynamic Flows

Expand Down Expand Up @@ -444,25 +469,7 @@ The Pipecat Flow Editor provides a visual interface for creating and managing co
}
```

### Node Configuration

Each node can be configured with:

- Messages for LLM context
- Available functions
- Pre/post actions
- State transitions

## Best Practices

### Organization

- Arrange nodes in logical flow
- Group related nodes together
- Use consistent spacing
- Make transitions clear

### Naming Conventions
## Naming Conventions

- **Start Node**: Use descriptive names (e.g., "greeting", "welcome")
- **Flow Nodes**: Name based on purpose (e.g., "collect_info", "verify_data")
Expand All @@ -476,9 +483,10 @@ Each node can be configured with:
{
"type": "function",
"function": {
"name": "next_state", # Matches target node name
"name": "next_state",
"description": "Clear transition description",
"parameters": {...}
"transition_to": "target_node_name" # Transition target
}
}

Expand All @@ -494,13 +502,6 @@ Each node can be configured with:
}
```

### Testing Flows

- Verify all paths lead to valid endpoints
- Test node functions with sample data
- Ensure edge functions connect properly
- Validate configuration export

## Using the Editor

### Creating a New Flow
Expand Down