# YAML to LangGraph Converter
A powerful tool for converting Defy YAML workflow files to LangGraph implementations with comprehensive validation, beautiful CLI output, and professional workflow visualization.
## Features
- ๐ **YAML Schema Validation**: Comprehensive validation of workflow structure
- ๐จ **Rich CLI Interface**: Beautiful command-line interface with Click
- โก **Fast Conversion**: Efficient parsing and code generation
- ๐งช **Comprehensive Testing**: Full test suite with pytest
- ๐ฆ **Modern Packaging**: Standard Python package structure
- ๐ ๏ธ **Extensible**: Easy to customize and extend
- ๐จ **Professional Visualization**: High-quality workflow diagrams using Mermaid + Pyppeteer
- ๐ **Advanced Loop Support**: Proper handling of complex loop structures with break conditions
- ๐ **State Management**: Intelligent variable reference handling and state tracking
- ๐ฏ **Multiple Themes**: Default, dark, forest, and neutral visualization themes
## Installation
### From Source
```bash
git clone https://github.com/example/yaml-to-langgraph.git
cd yaml-to-langgraph
pip install -e .
```
### With Development Dependencies
```bash
pip install -e ".[dev]"
```
### With LangChain Dependencies
```bash
pip install -e ".[langchain]"
```
## Usage
### Command Line Interface
#### Basic Commands
```bash
# Validate YAML workflow file
yaml-to-langgraph validate workflow.yml
# Convert YAML to LangGraph implementation
yaml-to-langgraph convert workflow.yml
# Convert with custom output directory
yaml-to-langgraph convert workflow.yml --output my_workflow
# Convert with verbose output
yaml-to-langgraph convert workflow.yml --verbose
# Skip validation (not recommended)
yaml-to-langgraph convert workflow.yml --skip-validation
# List all nodes in the workflow
yaml-to-langgraph list-nodes workflow.yml
# Dry run to see what would be generated
yaml-to-langgraph dry-run workflow.yml
# Get help for any command
yaml-to-langgraph --help
yaml-to-langgraph convert --help
yaml-to-langgraph validate --help
```
#### ๐จ Workflow Visualization
```bash
# Generate a visual representation of the workflow
yaml-to-langgraph visualize workflow.yml
# Visualize with different themes
yaml-to-langgraph visualize workflow.yml --theme dark
yaml-to-langgraph visualize workflow.yml --theme forest
yaml-to-langgraph visualize workflow.yml --theme neutral
# Customize visualization output
yaml-to-langgraph visualize workflow.yml --output my_workflow.png
yaml-to-langgraph visualize workflow.yml --format svg
yaml-to-langgraph visualize workflow.yml --size 30 20
yaml-to-langgraph visualize workflow.yml --dpi 300
# Generate high-resolution (HD) visualization
yaml-to-langgraph visualize workflow.yml --size 30 20 --dpi 300 --output workflow_hd.png
# Different layout algorithms
yaml-to-langgraph visualize workflow.yml --layout hierarchical
yaml-to-langgraph visualize workflow.yml --layout flowchart
yaml-to-langgraph visualize workflow.yml --layout graph
# Show edge labels (can make complex graphs cluttered)
yaml-to-langgraph visualize workflow.yml --show-edge-labels
# Disable loop grouping
yaml-to-langgraph visualize workflow.yml --no-loops
```
#### Validation Examples
```bash
# Basic validation
yaml-to-langgraph validate workflow.yml
# Strict validation (treats warnings as errors)
yaml-to-langgraph validate workflow.yml --strict
# Validate with detailed output
yaml-to-langgraph validate workflow.yml --verbose
```
#### Conversion Examples
```bash
# Simple conversion (includes automatic visualization)
yaml-to-langgraph convert sample_workflow.yml
# Convert without visualization
yaml-to-langgraph convert sample_workflow.yml --no-visualization
# Convert to specific directory
yaml-to-langgraph convert sample_workflow.yml --output generated_workflow
# Convert with verbose output to see all generated files
yaml-to-langgraph convert sample_workflow.yml --verbose
# Convert multiple workflows
for file in workflows/*.yml; do
yaml-to-langgraph convert "$file" --output "generated_$(basename "$file" .yml)"
done
```
### Python API
#### Basic Usage
```python
from yaml_to_langgraph import YAMLToLangGraphConverter
from yaml_to_langgraph.schema_validator import validate_yaml_workflow
# Validate a workflow
result = validate_yaml_workflow("workflow.yml")
if result.is_valid:
print("Workflow is valid!")
if result.warnings:
print(f"Warnings: {[w.message for w in result.warnings]}")
else:
print(f"Validation failed: {[e.message for e in result.errors]}")
# Convert YAML workflow to LangGraph
converter = YAMLToLangGraphConverter("workflow.yml", "output_dir")
output_path = converter.convert()
print(f"Generated workflow at: {output_path}")
```
#### Advanced Usage
```python
from yaml_to_langgraph import YAMLToLangGraphConverter
from yaml_to_langgraph.yaml_parser import YAMLWorkflowParser
from yaml_to_langgraph.code_generator import LangGraphCodeGenerator
# Parse YAML workflow
parser = YAMLWorkflowParser("workflow.yml")
workflow_data = parser.parse()
# Generate code
generator = LangGraphCodeGenerator(workflow_data)
code_files = generator.generate_code("output_dir")
# Access specific components
print(f"Workflow name: {workflow_data.app.name}")
print(f"Number of nodes: {len(workflow_data.graph.nodes)}")
print(f"Number of edges: {len(workflow_data.graph.edges)}")
# Get LLM nodes
llm_nodes = [node for node in workflow_data.graph.nodes if node.type == "llm"]
print(f"LLM nodes: {[node.id for node in llm_nodes]}")
# Access loop information
for loop in workflow_data.loops:
print(f"Loop {loop.id}: {loop.title}")
print(f" Max iterations: {loop.max_iterations}")
print(f" Break conditions: {loop.break_conditions}")
print(f" Child nodes: {[node.id for node in loop.child_nodes]}")
# Access state variables
for var in workflow_data.state_variables:
print(f"State variable: {var.node_id}.{var.variable_name} ({var.variable_type})")
```
#### ๐จ Visualization API
```python
from yaml_to_langgraph.graph_visualizer import GraphVisualizer, VisualizationConfig
from yaml_to_langgraph.yaml_parser import YAMLWorkflowParser
# Parse workflow
parser = YAMLWorkflowParser("workflow.yml")
workflow_info = parser.parse()
# Create visualization config
config = VisualizationConfig(
output_format="png", # png, svg, pdf
layout_algorithm="hierarchical", # hierarchical, flowchart, graph
figure_size=(24, 16), # width, height in inches
dpi=300, # resolution
theme="default", # default, dark, forest, neutral
show_edge_labels=False, # show edge labels
show_loops=True, # enable loop grouping
loop_grouping=True, # group loop nodes
max_label_length=20 # truncate long labels
)
# Generate visualization
visualizer = GraphVisualizer(config)
output_path = visualizer.visualize_workflow(workflow_info, "workflow_diagram.png")
print(f"Visualization saved to: {output_path}")
# Generate high-resolution (HD) visualization
hd_config = VisualizationConfig(
output_format="png",
layout_algorithm="hierarchical",
figure_size=(30, 20), # Large size for HD
dpi=300, # High resolution
theme="default",
show_edge_labels=False,
show_loops=True,
loop_grouping=True,
max_label_length=20
)
hd_visualizer = GraphVisualizer(hd_config)
hd_output_path = hd_visualizer.visualize_workflow(workflow_info, "workflow_hd.png")
print(f"HD visualization saved to: {hd_output_path}")
```
#### Error Handling
```python
from yaml_to_langgraph import YAMLToLangGraphConverter
from yaml_to_langgraph.schema_validator import ValidationError
try:
converter = YAMLToLangGraphConverter("invalid_workflow.yml", "output")
output_path = converter.convert()
except ValidationError as e:
print(f"Validation error: {e.message}")
print(f"Path: {e.path}")
except FileNotFoundError:
print("YAML file not found")
except Exception as e:
print(f"Unexpected error: {e}")
```
### Generated Code Structure
When you convert a YAML workflow, the following structure is generated:
```
generated_workflow/
โโโ prompts/ # Prompt templates for LLM nodes
โ โโโ node1_prompt.py
โ โโโ node2_prompt.py
โ โโโ ...
โโโ nodes/ # Node implementations
โ โโโ workflow_nodes.py
โ โโโ llm_node.py # Enhanced LLM nodes with state management
โ โโโ custom_nodes.py
โโโ edges/ # Edge definitions and routing logic
โ โโโ routing.py
โ โโโ conditions.py
โโโ workflow_graph.py # Main graph assembly
โโโ loop_aware_graph.py # Advanced loop handling with LangGraph For constructs
โโโ example_usage.py # Usage example
โโโ requirements.txt # Dependencies
โโโ workflow_graph.png # Professional workflow visualization
โโโ README.md # Generated documentation
```
### Using the Generated Workflow
```python
# After conversion, use the generated workflow
from workflow_graph import create_workflow_graph, run_workflow
from langchain_openai import ChatOpenAI
# Initialize your model
model = ChatOpenAI(model="gpt-4", temperature=0.7)
# Create the workflow graph
graph = create_workflow_graph(model)
# Run the workflow
result = run_workflow(
graph=graph,
input_data={"user_input": "Hello, world!"}
)
print(result)
```
### Real-World Examples
#### Example 1: Simple Chat Workflow
```yaml
# simple_chat.yml
app:
name: "simple-chat"
description: "A simple chat workflow"
workflow:
graph:
nodes:
- id: "start"
type: "start"
data:
type: "start"
title: "Start"
- id: "chat"
type: "llm"
data:
type: "llm"
title: "Chat Response"
model:
provider: "openai"
name: "gpt-4"
prompt_template:
- role: "user"
content: "{{user_input}}"
- id: "end"
type: "end"
data:
type: "end"
title: "End"
edges:
- id: "edge1"
source: "start"
target: "chat"
data:
label: "always"
- id: "edge2"
source: "chat"
target: "end"
data:
label: "always"
```
Convert and use:
```bash
yaml-to-langgraph convert simple_chat.yml --output simple_chat_workflow
cd simple_chat_workflow
pip install -r requirements.txt
python example_usage.py
```
#### Example 2: Multi-Step Processing Workflow
```yaml
# processing_workflow.yml
app:
name: "data-processor"
description: "Multi-step data processing workflow"
workflow:
graph:
nodes:
- id: "start"
type: "start"
data:
type: "start"
- id: "analyze"
type: "llm"
data:
type: "llm"
title: "Data Analyzer"
model:
provider: "openai"
name: "gpt-4"
prompt_template:
- role: "system"
content: "Analyze the following data: {{input_data}}"
- id: "process"
type: "llm"
data:
type: "llm"
title: "Data Processor"
model:
provider: "openai"
name: "gpt-4"
prompt_template:
- role: "system"
content: "Process the analyzed data: {{analyze.output}}"
- id: "validate"
type: "llm"
data:
type: "llm"
title: "Data Validator"
model:
provider: "openai"
name: "gpt-4"
prompt_template:
- role: "system"
content: "Validate the processed data: {{process.output}}"
- id: "end"
type: "end"
data:
type: "end"
edges:
- id: "e1"
source: "start"
target: "analyze"
data:
label: "always"
- id: "e2"
source: "analyze"
target: "process"
data:
label: "success"
- id: "e3"
source: "process"
target: "validate"
data:
label: "success"
- id: "e4"
source: "validate"
target: "end"
data:
label: "valid"
```
#### Example 3: Complex Loop Workflow
```yaml
# loop_workflow.yml
app:
name: "iterative-processor"
description: "Workflow with iterative processing loop"
workflow:
graph:
nodes:
- id: "start"
type: "start"
data:
type: "start"
title: "Start Processing"
- id: "main_loop"
type: "loop"
data:
type: "loop"
title: "Main Processing Loop"
loop_config:
max_iterations: 5
break_conditions:
- condition: "{{Objection}} == 'resolved'"
description: "Stop when objection is resolved"
loop_variables:
- name: "iteration_count"
initial_value: 0
- name: "Objection"
initial_value: "pending"
children:
- id: "loop_start"
type: "loop-start"
data:
type: "loop-start"
title: "Loop Start"
- id: "process_item"
type: "llm"
data:
type: "llm"
title: "Process Item"
model:
provider: "openai"
name: "gpt-4"
prompt_template:
- role: "system"
content: "Process item {{iteration_count}}: {{input_data}}"
- id: "check_objection"
type: "llm"
data:
type: "llm"
title: "Check for Objections"
model:
provider: "openai"
name: "gpt-4"
prompt_template:
- role: "system"
content: "Check if there are objections: {{process_item.output}}"
- id: "end"
type: "end"
data:
type: "end"
title: "End"
edges:
- id: "e1"
source: "start"
target: "main_loop"
data:
label: "always"
- id: "e2"
source: "main_loop"
target: "end"
data:
label: "loop_complete"
```
### Using Make Commands
The project includes a comprehensive Makefile for development:
```bash
# Development setup
make dev-setup # Install in development mode
make test # Run all tests
make demo # Convert sample workflow
make validate-demo # Validate sample workflow
# Code quality
make format # Format code
make lint # Run linting
make check # Run all quality checks
# Package management
make build # Build package
make publish-token TOKEN=your-token # Publish to PyPI
make pypi-help # Show PyPI setup instructions
# UV commands
make uv-sync # Sync dependencies
make uv-add PACKAGE=requests # Add new package
make uv-update # Update dependencies
```
## Quick Reference
### Common Commands
| Command | Description |
|---------|-------------|
| `yaml-to-langgraph validate workflow.yml` | Validate YAML workflow |
| `yaml-to-langgraph convert workflow.yml` | Convert to LangGraph |
| `yaml-to-langgraph convert workflow.yml --output my_dir` | Convert to specific directory |
| `yaml-to-langgraph visualize workflow.yml` | Generate workflow diagram |
| `yaml-to-langgraph visualize workflow.yml --theme dark` | Generate dark theme diagram |
| `yaml-to-langgraph visualize workflow.yml --size 30 20 --dpi 300` | Generate HD diagram |
| `yaml-to-langgraph list-nodes workflow.yml` | List all nodes |
| `yaml-to-langgraph dry-run workflow.yml` | Preview what would be generated |
### Visualization Options
| Option | Description | Default |
|--------|-------------|---------|
| `--theme` | Theme: default, dark, forest, neutral | default |
| `--layout` | Layout: hierarchical, flowchart, graph | hierarchical |
| `--format` | Output format: png, svg, pdf | png |
| `--size` | Figure size (width height) | 24 16 |
| `--dpi` | Resolution | 300 |
| `--show-edge-labels` | Show edge labels | false |
| `--no-loops` | Disable loop grouping | false |
### Make Commands
| Command | Description |
|---------|-------------|
| `make help` | Show all available commands |
| `make test` | Run all tests |
| `make demo` | Convert sample workflow |
| `make build` | Build package |
| `make publish-token TOKEN=xxx` | Publish to PyPI |
| `make pypi-help` | Show PyPI setup help |
### YAML Structure
```yaml
app:
name: "workflow-name"
description: "Workflow description"
workflow:
graph:
nodes:
- id: "node_id"
type: "llm|start|end|code|loop|loop-start|assigner"
data:
type: "llm|start|end|code|loop|loop-start|assigner"
title: "Node Title"
# ... node-specific data
edges:
- id: "edge_id"
source: "source_node"
target: "target_node"
data:
label: "condition"
```
### Generated Files
- `workflow_graph.py` - Main graph implementation
- `loop_aware_graph.py` - Advanced loop handling
- `prompts/` - LLM prompt templates
- `nodes/` - Node implementations
- `edges/` - Routing logic
- `example_usage.py` - Usage example
- `requirements.txt` - Dependencies
- `workflow_graph.png` - Professional workflow visualization
## Advanced Features
### ๐ Loop Support
The converter provides advanced loop handling:
- **Hierarchical Loop Structure**: Proper handling of `loop` containers with `loop-start` nodes
- **Break Conditions**: Support for conditional loop exit based on state variables
- **Loop Variables**: Automatic tracking of loop-specific state variables
- **LangGraph Integration**: Generates proper `For` constructs for LangGraph execution
### ๐ State Management
Intelligent state management features:
- **Variable References**: Automatic detection of `{{#node_id.field#}}` patterns in prompts
- **State Variable Tracking**: Comprehensive tracking of all state variables across the workflow
- **Dependency Analysis**: Automatic detection of node dependencies based on variable usage
- **Enhanced LLM Nodes**: LLM nodes automatically update state with multiple output keys
### ๐จ Professional Visualization
High-quality workflow visualization using Mermaid + Pyppeteer:
- **Multiple Themes**: Default, dark, forest, and neutral themes
- **Loop Grouping**: Visual grouping of loop nodes with subgraphs
- **Emoji Icons**: Visual node type identification (๐ Start, ๐ End, ๐ค LLM, etc.)
- **Compact Output**: Small file sizes (90%+ smaller than previous backends)
- **Scalable Quality**: Vector-based rendering maintains perfect quality at any size
## Development
### Setup Development Environment
```bash
# Clone repository
git clone https://github.com/example/yaml-to-langgraph.git
cd yaml-to-langgraph
# Install in development mode
pip install -e ".[dev]"
# Run tests
pytest tests/ -v
# Run with coverage
pytest tests/ --cov=src/yaml_to_langgraph --cov-report=html
```
### Code Quality
```bash
# Format code
black src/ tests/
# Sort imports
isort src/ tests/
# Lint code
ruff check src/ tests/
# Type checking
mypy src/
```
## Project Structure
```
yaml_to_langgraph/
โโโ src/
โ โโโ yaml_to_langgraph/
โ โโโ __init__.py
โ โโโ cli.py # Command-line interface
โ โโโ converter.py # Main converter logic
โ โโโ schema_validator.py # YAML validation
โ โโโ yaml_parser.py # YAML parsing with loop/state support
โ โโโ code_generator.py # Code generation with loop awareness
โ โโโ graph_visualizer.py # Mermaid + Pyppeteer visualization
โโโ tests/
โ โโโ __init__.py
โ โโโ conftest.py
โ โโโ test_sample_workflow.py
โ โโโ test_cli.py
โ โโโ test_converter.py
โ โโโ test_schema_validation.py
โโโ pyproject.toml
โโโ README.md
```
## Testing
The project includes a comprehensive test suite covering:
- **Schema Validation**: YAML structure validation
- **CLI Functionality**: Command-line interface testing
- **Core Converter**: Conversion logic testing
- **Sample Workflow**: Real-world workflow testing
- **Loop Handling**: Complex loop structure testing
- **State Management**: Variable reference and state tracking testing
- **Visualization**: Mermaid diagram generation testing
```bash
# Run all tests
pytest tests/ -v
# Run specific test categories
pytest tests/test_schema_validation.py -v
pytest tests/test_cli.py -v
pytest tests/test_converter.py -v
pytest tests/test_sample_workflow.py -v
```
## Publishing
The package can be published to PyPI using several methods:
### Using UV (Recommended)
```bash
# Build the package
make build
# Publish with environment variables
export UV_PUBLISH_USERNAME=your-username
export UV_PUBLISH_PASSWORD=your-password
make publish
# Or publish with token
make publish-token TOKEN=your-pypi-token
# Publish to Test PyPI first
make publish-test TOKEN=your-testpypi-token
```
### Using Twine (Fallback)
If you prefer to use your existing `~/.pypirc` configuration:
```bash
# Build the package
make build
# Publish using twine (reads ~/.pypirc)
make publish-twine
# Publish to Test PyPI using twine
make publish-test-twine
```
### Manual Publishing
```bash
# Build
uv build
# Publish with uv
uv publish --token your-token
# Or with twine
python -m twine upload dist/*
```
## Contributing
1. Fork the repository
2. Create a feature branch
3. Make your changes
4. Add tests for new functionality
5. Ensure all tests pass
6. Submit a pull request
## License
MIT License - see LICENSE file for details.
## Support
- **Issues**: [GitHub Issues](https://github.com/example/yaml-to-langgraph/issues)
- **Documentation**: [GitHub Wiki](https://github.com/example/yaml-to-langgraph/wiki)
- **Discussions**: [GitHub Discussions](https://github.com/example/yaml-to-langgraph/discussions)
Raw data
{
"_id": null,
"home_page": null,
"name": "yaml-to-langgraph",
"maintainer": null,
"docs_url": null,
"requires_python": ">=3.9",
"maintainer_email": null,
"keywords": "converter, langchain, langgraph, workflow, yaml",
"author": null,
"author_email": "YAML to LangGraph Team <team@example.com>",
"download_url": "https://files.pythonhosted.org/packages/2d/6f/935a7e2f3e73c0dc210eea561cad7a0ff61ab867a7bd97b4b591731530bb/yaml_to_langgraph-1.0.3.tar.gz",
"platform": null,
"description": "# YAML to LangGraph Converter\n\nA powerful tool for converting Defy YAML workflow files to LangGraph implementations with comprehensive validation, beautiful CLI output, and professional workflow visualization.\n\n## Features\n\n- \ud83d\udd0d **YAML Schema Validation**: Comprehensive validation of workflow structure\n- \ud83c\udfa8 **Rich CLI Interface**: Beautiful command-line interface with Click\n- \u26a1 **Fast Conversion**: Efficient parsing and code generation\n- \ud83e\uddea **Comprehensive Testing**: Full test suite with pytest\n- \ud83d\udce6 **Modern Packaging**: Standard Python package structure\n- \ud83d\udee0\ufe0f **Extensible**: Easy to customize and extend\n- \ud83c\udfa8 **Professional Visualization**: High-quality workflow diagrams using Mermaid + Pyppeteer\n- \ud83d\udd04 **Advanced Loop Support**: Proper handling of complex loop structures with break conditions\n- \ud83d\udcca **State Management**: Intelligent variable reference handling and state tracking\n- \ud83c\udfaf **Multiple Themes**: Default, dark, forest, and neutral visualization themes\n\n## Installation\n\n### From Source\n\n```bash\ngit clone https://github.com/example/yaml-to-langgraph.git\ncd yaml-to-langgraph\npip install -e .\n```\n\n### With Development Dependencies\n\n```bash\npip install -e \".[dev]\"\n```\n\n### With LangChain Dependencies\n\n```bash\npip install -e \".[langchain]\"\n```\n\n## Usage\n\n### Command Line Interface\n\n#### Basic Commands\n\n```bash\n# Validate YAML workflow file\nyaml-to-langgraph validate workflow.yml\n\n# Convert YAML to LangGraph implementation\nyaml-to-langgraph convert workflow.yml\n\n# Convert with custom output directory\nyaml-to-langgraph convert workflow.yml --output my_workflow\n\n# Convert with verbose output\nyaml-to-langgraph convert workflow.yml --verbose\n\n# Skip validation (not recommended)\nyaml-to-langgraph convert workflow.yml --skip-validation\n\n# List all nodes in the workflow\nyaml-to-langgraph list-nodes workflow.yml\n\n# Dry run to see what would be generated\nyaml-to-langgraph dry-run workflow.yml\n\n# Get help for any command\nyaml-to-langgraph --help\nyaml-to-langgraph convert --help\nyaml-to-langgraph validate --help\n```\n\n#### \ud83c\udfa8 Workflow Visualization\n\n```bash\n# Generate a visual representation of the workflow\nyaml-to-langgraph visualize workflow.yml\n\n# Visualize with different themes\nyaml-to-langgraph visualize workflow.yml --theme dark\nyaml-to-langgraph visualize workflow.yml --theme forest\nyaml-to-langgraph visualize workflow.yml --theme neutral\n\n# Customize visualization output\nyaml-to-langgraph visualize workflow.yml --output my_workflow.png\nyaml-to-langgraph visualize workflow.yml --format svg\nyaml-to-langgraph visualize workflow.yml --size 30 20\nyaml-to-langgraph visualize workflow.yml --dpi 300\n\n# Generate high-resolution (HD) visualization\nyaml-to-langgraph visualize workflow.yml --size 30 20 --dpi 300 --output workflow_hd.png\n\n# Different layout algorithms\nyaml-to-langgraph visualize workflow.yml --layout hierarchical\nyaml-to-langgraph visualize workflow.yml --layout flowchart\nyaml-to-langgraph visualize workflow.yml --layout graph\n\n# Show edge labels (can make complex graphs cluttered)\nyaml-to-langgraph visualize workflow.yml --show-edge-labels\n\n# Disable loop grouping\nyaml-to-langgraph visualize workflow.yml --no-loops\n```\n\n#### Validation Examples\n\n```bash\n# Basic validation\nyaml-to-langgraph validate workflow.yml\n\n# Strict validation (treats warnings as errors)\nyaml-to-langgraph validate workflow.yml --strict\n\n# Validate with detailed output\nyaml-to-langgraph validate workflow.yml --verbose\n```\n\n#### Conversion Examples\n\n```bash\n# Simple conversion (includes automatic visualization)\nyaml-to-langgraph convert sample_workflow.yml\n\n# Convert without visualization\nyaml-to-langgraph convert sample_workflow.yml --no-visualization\n\n# Convert to specific directory\nyaml-to-langgraph convert sample_workflow.yml --output generated_workflow\n\n# Convert with verbose output to see all generated files\nyaml-to-langgraph convert sample_workflow.yml --verbose\n\n# Convert multiple workflows\nfor file in workflows/*.yml; do\n yaml-to-langgraph convert \"$file\" --output \"generated_$(basename \"$file\" .yml)\"\ndone\n```\n\n### Python API\n\n#### Basic Usage\n\n```python\nfrom yaml_to_langgraph import YAMLToLangGraphConverter\nfrom yaml_to_langgraph.schema_validator import validate_yaml_workflow\n\n# Validate a workflow\nresult = validate_yaml_workflow(\"workflow.yml\")\nif result.is_valid:\n print(\"Workflow is valid!\")\n if result.warnings:\n print(f\"Warnings: {[w.message for w in result.warnings]}\")\nelse:\n print(f\"Validation failed: {[e.message for e in result.errors]}\")\n\n# Convert YAML workflow to LangGraph\nconverter = YAMLToLangGraphConverter(\"workflow.yml\", \"output_dir\")\noutput_path = converter.convert()\nprint(f\"Generated workflow at: {output_path}\")\n```\n\n#### Advanced Usage\n\n```python\nfrom yaml_to_langgraph import YAMLToLangGraphConverter\nfrom yaml_to_langgraph.yaml_parser import YAMLWorkflowParser\nfrom yaml_to_langgraph.code_generator import LangGraphCodeGenerator\n\n# Parse YAML workflow\nparser = YAMLWorkflowParser(\"workflow.yml\")\nworkflow_data = parser.parse()\n\n# Generate code\ngenerator = LangGraphCodeGenerator(workflow_data)\ncode_files = generator.generate_code(\"output_dir\")\n\n# Access specific components\nprint(f\"Workflow name: {workflow_data.app.name}\")\nprint(f\"Number of nodes: {len(workflow_data.graph.nodes)}\")\nprint(f\"Number of edges: {len(workflow_data.graph.edges)}\")\n\n# Get LLM nodes\nllm_nodes = [node for node in workflow_data.graph.nodes if node.type == \"llm\"]\nprint(f\"LLM nodes: {[node.id for node in llm_nodes]}\")\n\n# Access loop information\nfor loop in workflow_data.loops:\n print(f\"Loop {loop.id}: {loop.title}\")\n print(f\" Max iterations: {loop.max_iterations}\")\n print(f\" Break conditions: {loop.break_conditions}\")\n print(f\" Child nodes: {[node.id for node in loop.child_nodes]}\")\n\n# Access state variables\nfor var in workflow_data.state_variables:\n print(f\"State variable: {var.node_id}.{var.variable_name} ({var.variable_type})\")\n```\n\n#### \ud83c\udfa8 Visualization API\n\n```python\nfrom yaml_to_langgraph.graph_visualizer import GraphVisualizer, VisualizationConfig\nfrom yaml_to_langgraph.yaml_parser import YAMLWorkflowParser\n\n# Parse workflow\nparser = YAMLWorkflowParser(\"workflow.yml\")\nworkflow_info = parser.parse()\n\n# Create visualization config\nconfig = VisualizationConfig(\n output_format=\"png\", # png, svg, pdf\n layout_algorithm=\"hierarchical\", # hierarchical, flowchart, graph\n figure_size=(24, 16), # width, height in inches\n dpi=300, # resolution\n theme=\"default\", # default, dark, forest, neutral\n show_edge_labels=False, # show edge labels\n show_loops=True, # enable loop grouping\n loop_grouping=True, # group loop nodes\n max_label_length=20 # truncate long labels\n)\n\n# Generate visualization\nvisualizer = GraphVisualizer(config)\noutput_path = visualizer.visualize_workflow(workflow_info, \"workflow_diagram.png\")\nprint(f\"Visualization saved to: {output_path}\")\n\n# Generate high-resolution (HD) visualization\nhd_config = VisualizationConfig(\n output_format=\"png\",\n layout_algorithm=\"hierarchical\",\n figure_size=(30, 20), # Large size for HD\n dpi=300, # High resolution\n theme=\"default\",\n show_edge_labels=False,\n show_loops=True,\n loop_grouping=True,\n max_label_length=20\n)\n\nhd_visualizer = GraphVisualizer(hd_config)\nhd_output_path = hd_visualizer.visualize_workflow(workflow_info, \"workflow_hd.png\")\nprint(f\"HD visualization saved to: {hd_output_path}\")\n```\n\n#### Error Handling\n\n```python\nfrom yaml_to_langgraph import YAMLToLangGraphConverter\nfrom yaml_to_langgraph.schema_validator import ValidationError\n\ntry:\n converter = YAMLToLangGraphConverter(\"invalid_workflow.yml\", \"output\")\n output_path = converter.convert()\nexcept ValidationError as e:\n print(f\"Validation error: {e.message}\")\n print(f\"Path: {e.path}\")\nexcept FileNotFoundError:\n print(\"YAML file not found\")\nexcept Exception as e:\n print(f\"Unexpected error: {e}\")\n```\n\n### Generated Code Structure\n\nWhen you convert a YAML workflow, the following structure is generated:\n\n```\ngenerated_workflow/\n\u251c\u2500\u2500 prompts/ # Prompt templates for LLM nodes\n\u2502 \u251c\u2500\u2500 node1_prompt.py\n\u2502 \u251c\u2500\u2500 node2_prompt.py\n\u2502 \u2514\u2500\u2500 ...\n\u251c\u2500\u2500 nodes/ # Node implementations\n\u2502 \u251c\u2500\u2500 workflow_nodes.py\n\u2502 \u251c\u2500\u2500 llm_node.py # Enhanced LLM nodes with state management\n\u2502 \u2514\u2500\u2500 custom_nodes.py\n\u251c\u2500\u2500 edges/ # Edge definitions and routing logic\n\u2502 \u251c\u2500\u2500 routing.py\n\u2502 \u2514\u2500\u2500 conditions.py\n\u251c\u2500\u2500 workflow_graph.py # Main graph assembly\n\u251c\u2500\u2500 loop_aware_graph.py # Advanced loop handling with LangGraph For constructs\n\u251c\u2500\u2500 example_usage.py # Usage example\n\u251c\u2500\u2500 requirements.txt # Dependencies\n\u251c\u2500\u2500 workflow_graph.png # Professional workflow visualization\n\u2514\u2500\u2500 README.md # Generated documentation\n```\n\n### Using the Generated Workflow\n\n```python\n# After conversion, use the generated workflow\nfrom workflow_graph import create_workflow_graph, run_workflow\nfrom langchain_openai import ChatOpenAI\n\n# Initialize your model\nmodel = ChatOpenAI(model=\"gpt-4\", temperature=0.7)\n\n# Create the workflow graph\ngraph = create_workflow_graph(model)\n\n# Run the workflow\nresult = run_workflow(\n graph=graph,\n input_data={\"user_input\": \"Hello, world!\"}\n)\n\nprint(result)\n```\n\n### Real-World Examples\n\n#### Example 1: Simple Chat Workflow\n\n```yaml\n# simple_chat.yml\napp:\n name: \"simple-chat\"\n description: \"A simple chat workflow\"\n\nworkflow:\n graph:\n nodes:\n - id: \"start\"\n type: \"start\"\n data:\n type: \"start\"\n title: \"Start\"\n - id: \"chat\"\n type: \"llm\"\n data:\n type: \"llm\"\n title: \"Chat Response\"\n model:\n provider: \"openai\"\n name: \"gpt-4\"\n prompt_template:\n - role: \"user\"\n content: \"{{user_input}}\"\n - id: \"end\"\n type: \"end\"\n data:\n type: \"end\"\n title: \"End\"\n edges:\n - id: \"edge1\"\n source: \"start\"\n target: \"chat\"\n data:\n label: \"always\"\n - id: \"edge2\"\n source: \"chat\"\n target: \"end\"\n data:\n label: \"always\"\n```\n\nConvert and use:\n```bash\nyaml-to-langgraph convert simple_chat.yml --output simple_chat_workflow\ncd simple_chat_workflow\npip install -r requirements.txt\npython example_usage.py\n```\n\n#### Example 2: Multi-Step Processing Workflow\n\n```yaml\n# processing_workflow.yml\napp:\n name: \"data-processor\"\n description: \"Multi-step data processing workflow\"\n\nworkflow:\n graph:\n nodes:\n - id: \"start\"\n type: \"start\"\n data:\n type: \"start\"\n - id: \"analyze\"\n type: \"llm\"\n data:\n type: \"llm\"\n title: \"Data Analyzer\"\n model:\n provider: \"openai\"\n name: \"gpt-4\"\n prompt_template:\n - role: \"system\"\n content: \"Analyze the following data: {{input_data}}\"\n - id: \"process\"\n type: \"llm\"\n data:\n type: \"llm\"\n title: \"Data Processor\"\n model:\n provider: \"openai\"\n name: \"gpt-4\"\n prompt_template:\n - role: \"system\"\n content: \"Process the analyzed data: {{analyze.output}}\"\n - id: \"validate\"\n type: \"llm\"\n data:\n type: \"llm\"\n title: \"Data Validator\"\n model:\n provider: \"openai\"\n name: \"gpt-4\"\n prompt_template:\n - role: \"system\"\n content: \"Validate the processed data: {{process.output}}\"\n - id: \"end\"\n type: \"end\"\n data:\n type: \"end\"\n edges:\n - id: \"e1\"\n source: \"start\"\n target: \"analyze\"\n data:\n label: \"always\"\n - id: \"e2\"\n source: \"analyze\"\n target: \"process\"\n data:\n label: \"success\"\n - id: \"e3\"\n source: \"process\"\n target: \"validate\"\n data:\n label: \"success\"\n - id: \"e4\"\n source: \"validate\"\n target: \"end\"\n data:\n label: \"valid\"\n```\n\n#### Example 3: Complex Loop Workflow\n\n```yaml\n# loop_workflow.yml\napp:\n name: \"iterative-processor\"\n description: \"Workflow with iterative processing loop\"\n\nworkflow:\n graph:\n nodes:\n - id: \"start\"\n type: \"start\"\n data:\n type: \"start\"\n title: \"Start Processing\"\n - id: \"main_loop\"\n type: \"loop\"\n data:\n type: \"loop\"\n title: \"Main Processing Loop\"\n loop_config:\n max_iterations: 5\n break_conditions:\n - condition: \"{{Objection}} == 'resolved'\"\n description: \"Stop when objection is resolved\"\n loop_variables:\n - name: \"iteration_count\"\n initial_value: 0\n - name: \"Objection\"\n initial_value: \"pending\"\n children:\n - id: \"loop_start\"\n type: \"loop-start\"\n data:\n type: \"loop-start\"\n title: \"Loop Start\"\n - id: \"process_item\"\n type: \"llm\"\n data:\n type: \"llm\"\n title: \"Process Item\"\n model:\n provider: \"openai\"\n name: \"gpt-4\"\n prompt_template:\n - role: \"system\"\n content: \"Process item {{iteration_count}}: {{input_data}}\"\n - id: \"check_objection\"\n type: \"llm\"\n data:\n type: \"llm\"\n title: \"Check for Objections\"\n model:\n provider: \"openai\"\n name: \"gpt-4\"\n prompt_template:\n - role: \"system\"\n content: \"Check if there are objections: {{process_item.output}}\"\n - id: \"end\"\n type: \"end\"\n data:\n type: \"end\"\n title: \"End\"\n edges:\n - id: \"e1\"\n source: \"start\"\n target: \"main_loop\"\n data:\n label: \"always\"\n - id: \"e2\"\n source: \"main_loop\"\n target: \"end\"\n data:\n label: \"loop_complete\"\n```\n\n### Using Make Commands\n\nThe project includes a comprehensive Makefile for development:\n\n```bash\n# Development setup\nmake dev-setup # Install in development mode\nmake test # Run all tests\nmake demo # Convert sample workflow\nmake validate-demo # Validate sample workflow\n\n# Code quality\nmake format # Format code\nmake lint # Run linting\nmake check # Run all quality checks\n\n# Package management\nmake build # Build package\nmake publish-token TOKEN=your-token # Publish to PyPI\nmake pypi-help # Show PyPI setup instructions\n\n# UV commands\nmake uv-sync # Sync dependencies\nmake uv-add PACKAGE=requests # Add new package\nmake uv-update # Update dependencies\n```\n\n## Quick Reference\n\n### Common Commands\n\n| Command | Description |\n|---------|-------------|\n| `yaml-to-langgraph validate workflow.yml` | Validate YAML workflow |\n| `yaml-to-langgraph convert workflow.yml` | Convert to LangGraph |\n| `yaml-to-langgraph convert workflow.yml --output my_dir` | Convert to specific directory |\n| `yaml-to-langgraph visualize workflow.yml` | Generate workflow diagram |\n| `yaml-to-langgraph visualize workflow.yml --theme dark` | Generate dark theme diagram |\n| `yaml-to-langgraph visualize workflow.yml --size 30 20 --dpi 300` | Generate HD diagram |\n| `yaml-to-langgraph list-nodes workflow.yml` | List all nodes |\n| `yaml-to-langgraph dry-run workflow.yml` | Preview what would be generated |\n\n### Visualization Options\n\n| Option | Description | Default |\n|--------|-------------|---------|\n| `--theme` | Theme: default, dark, forest, neutral | default |\n| `--layout` | Layout: hierarchical, flowchart, graph | hierarchical |\n| `--format` | Output format: png, svg, pdf | png |\n| `--size` | Figure size (width height) | 24 16 |\n| `--dpi` | Resolution | 300 |\n| `--show-edge-labels` | Show edge labels | false |\n| `--no-loops` | Disable loop grouping | false |\n\n### Make Commands\n\n| Command | Description |\n|---------|-------------|\n| `make help` | Show all available commands |\n| `make test` | Run all tests |\n| `make demo` | Convert sample workflow |\n| `make build` | Build package |\n| `make publish-token TOKEN=xxx` | Publish to PyPI |\n| `make pypi-help` | Show PyPI setup help |\n\n### YAML Structure\n\n```yaml\napp:\n name: \"workflow-name\"\n description: \"Workflow description\"\n\nworkflow:\n graph:\n nodes:\n - id: \"node_id\"\n type: \"llm|start|end|code|loop|loop-start|assigner\"\n data:\n type: \"llm|start|end|code|loop|loop-start|assigner\"\n title: \"Node Title\"\n # ... node-specific data\n edges:\n - id: \"edge_id\"\n source: \"source_node\"\n target: \"target_node\"\n data:\n label: \"condition\"\n```\n\n### Generated Files\n\n- `workflow_graph.py` - Main graph implementation\n- `loop_aware_graph.py` - Advanced loop handling\n- `prompts/` - LLM prompt templates\n- `nodes/` - Node implementations\n- `edges/` - Routing logic\n- `example_usage.py` - Usage example\n- `requirements.txt` - Dependencies\n- `workflow_graph.png` - Professional workflow visualization\n\n## Advanced Features\n\n### \ud83d\udd04 Loop Support\n\nThe converter provides advanced loop handling:\n\n- **Hierarchical Loop Structure**: Proper handling of `loop` containers with `loop-start` nodes\n- **Break Conditions**: Support for conditional loop exit based on state variables\n- **Loop Variables**: Automatic tracking of loop-specific state variables\n- **LangGraph Integration**: Generates proper `For` constructs for LangGraph execution\n\n### \ud83d\udcca State Management\n\nIntelligent state management features:\n\n- **Variable References**: Automatic detection of `{{#node_id.field#}}` patterns in prompts\n- **State Variable Tracking**: Comprehensive tracking of all state variables across the workflow\n- **Dependency Analysis**: Automatic detection of node dependencies based on variable usage\n- **Enhanced LLM Nodes**: LLM nodes automatically update state with multiple output keys\n\n### \ud83c\udfa8 Professional Visualization\n\nHigh-quality workflow visualization using Mermaid + Pyppeteer:\n\n- **Multiple Themes**: Default, dark, forest, and neutral themes\n- **Loop Grouping**: Visual grouping of loop nodes with subgraphs\n- **Emoji Icons**: Visual node type identification (\ud83d\ude80 Start, \ud83c\udfc1 End, \ud83e\udd16 LLM, etc.)\n- **Compact Output**: Small file sizes (90%+ smaller than previous backends)\n- **Scalable Quality**: Vector-based rendering maintains perfect quality at any size\n\n## Development\n\n### Setup Development Environment\n\n```bash\n# Clone repository\ngit clone https://github.com/example/yaml-to-langgraph.git\ncd yaml-to-langgraph\n\n# Install in development mode\npip install -e \".[dev]\"\n\n# Run tests\npytest tests/ -v\n\n# Run with coverage\npytest tests/ --cov=src/yaml_to_langgraph --cov-report=html\n```\n\n### Code Quality\n\n```bash\n# Format code\nblack src/ tests/\n\n# Sort imports\nisort src/ tests/\n\n# Lint code\nruff check src/ tests/\n\n# Type checking\nmypy src/\n```\n\n## Project Structure\n\n```\nyaml_to_langgraph/\n\u251c\u2500\u2500 src/\n\u2502 \u2514\u2500\u2500 yaml_to_langgraph/\n\u2502 \u251c\u2500\u2500 __init__.py\n\u2502 \u251c\u2500\u2500 cli.py # Command-line interface\n\u2502 \u251c\u2500\u2500 converter.py # Main converter logic\n\u2502 \u251c\u2500\u2500 schema_validator.py # YAML validation\n\u2502 \u251c\u2500\u2500 yaml_parser.py # YAML parsing with loop/state support\n\u2502 \u251c\u2500\u2500 code_generator.py # Code generation with loop awareness\n\u2502 \u2514\u2500\u2500 graph_visualizer.py # Mermaid + Pyppeteer visualization\n\u251c\u2500\u2500 tests/\n\u2502 \u251c\u2500\u2500 __init__.py\n\u2502 \u251c\u2500\u2500 conftest.py\n\u2502 \u251c\u2500\u2500 test_sample_workflow.py\n\u2502 \u251c\u2500\u2500 test_cli.py\n\u2502 \u251c\u2500\u2500 test_converter.py\n\u2502 \u2514\u2500\u2500 test_schema_validation.py\n\u251c\u2500\u2500 pyproject.toml\n\u2514\u2500\u2500 README.md\n```\n\n## Testing\n\nThe project includes a comprehensive test suite covering:\n\n- **Schema Validation**: YAML structure validation\n- **CLI Functionality**: Command-line interface testing\n- **Core Converter**: Conversion logic testing\n- **Sample Workflow**: Real-world workflow testing\n- **Loop Handling**: Complex loop structure testing\n- **State Management**: Variable reference and state tracking testing\n- **Visualization**: Mermaid diagram generation testing\n\n```bash\n# Run all tests\npytest tests/ -v\n\n# Run specific test categories\npytest tests/test_schema_validation.py -v\npytest tests/test_cli.py -v\npytest tests/test_converter.py -v\npytest tests/test_sample_workflow.py -v\n```\n\n## Publishing\n\nThe package can be published to PyPI using several methods:\n\n### Using UV (Recommended)\n```bash\n# Build the package\nmake build\n\n# Publish with environment variables\nexport UV_PUBLISH_USERNAME=your-username\nexport UV_PUBLISH_PASSWORD=your-password\nmake publish\n\n# Or publish with token\nmake publish-token TOKEN=your-pypi-token\n\n# Publish to Test PyPI first\nmake publish-test TOKEN=your-testpypi-token\n```\n\n### Using Twine (Fallback)\nIf you prefer to use your existing `~/.pypirc` configuration:\n\n```bash\n# Build the package\nmake build\n\n# Publish using twine (reads ~/.pypirc)\nmake publish-twine\n\n# Publish to Test PyPI using twine\nmake publish-test-twine\n```\n\n### Manual Publishing\n```bash\n# Build\nuv build\n\n# Publish with uv\nuv publish --token your-token\n\n# Or with twine\npython -m twine upload dist/*\n```\n\n## Contributing\n\n1. Fork the repository\n2. Create a feature branch\n3. Make your changes\n4. Add tests for new functionality\n5. Ensure all tests pass\n6. Submit a pull request\n\n## License\n\nMIT License - see LICENSE file for details.\n\n## Support\n\n- **Issues**: [GitHub Issues](https://github.com/example/yaml-to-langgraph/issues)\n- **Documentation**: [GitHub Wiki](https://github.com/example/yaml-to-langgraph/wiki)\n- **Discussions**: [GitHub Discussions](https://github.com/example/yaml-to-langgraph/discussions)",
"bugtrack_url": null,
"license": "MIT",
"summary": "Convert YAML workflow files to LangGraph implementations",
"version": "1.0.3",
"project_urls": {
"Bug Tracker": "https://github.com/example/yaml-to-langgraph/issues",
"Documentation": "https://github.com/example/yaml-to-langgraph#readme",
"Homepage": "https://github.com/example/yaml-to-langgraph",
"Repository": "https://github.com/example/yaml-to-langgraph.git"
},
"split_keywords": [
"converter",
" langchain",
" langgraph",
" workflow",
" yaml"
],
"urls": [
{
"comment_text": null,
"digests": {
"blake2b_256": "e022654144e2e884cdaa0d5592f43aad0e3ece32b66772ac4228f92ff921ffea",
"md5": "260bb48e2c31fffc002123a4273a5f6c",
"sha256": "62b904130c3d94aa472c7b705dfe506635e6c9645348f06f4c5d35cb6cf854aa"
},
"downloads": -1,
"filename": "yaml_to_langgraph-1.0.3-py3-none-any.whl",
"has_sig": false,
"md5_digest": "260bb48e2c31fffc002123a4273a5f6c",
"packagetype": "bdist_wheel",
"python_version": "py3",
"requires_python": ">=3.9",
"size": 33711,
"upload_time": "2025-09-09T17:44:40",
"upload_time_iso_8601": "2025-09-09T17:44:40.033716Z",
"url": "https://files.pythonhosted.org/packages/e0/22/654144e2e884cdaa0d5592f43aad0e3ece32b66772ac4228f92ff921ffea/yaml_to_langgraph-1.0.3-py3-none-any.whl",
"yanked": false,
"yanked_reason": null
},
{
"comment_text": null,
"digests": {
"blake2b_256": "2d6f935a7e2f3e73c0dc210eea561cad7a0ff61ab867a7bd97b4b591731530bb",
"md5": "a7dfe0a71bd74fb07c25cbaabaaa1942",
"sha256": "2eda2ca5712d604c11ceb96502cad78c97d1416adc8df2681d530b157849d8ea"
},
"downloads": -1,
"filename": "yaml_to_langgraph-1.0.3.tar.gz",
"has_sig": false,
"md5_digest": "a7dfe0a71bd74fb07c25cbaabaaa1942",
"packagetype": "sdist",
"python_version": "source",
"requires_python": ">=3.9",
"size": 38408,
"upload_time": "2025-09-09T17:44:44",
"upload_time_iso_8601": "2025-09-09T17:44:44.271698Z",
"url": "https://files.pythonhosted.org/packages/2d/6f/935a7e2f3e73c0dc210eea561cad7a0ff61ab867a7bd97b4b591731530bb/yaml_to_langgraph-1.0.3.tar.gz",
"yanked": false,
"yanked_reason": null
}
],
"upload_time": "2025-09-09 17:44:44",
"github": true,
"gitlab": false,
"bitbucket": false,
"codeberg": false,
"github_user": "example",
"github_project": "yaml-to-langgraph",
"github_not_found": true,
"lcname": "yaml-to-langgraph"
}