329 lines
8.7 KiB
Plaintext
329 lines
8.7 KiB
Plaintext
---
|
|
title: "Context Managers"
|
|
description: "Use AgentOps traces as Python context managers for automatic lifecycle management"
|
|
---
|
|
|
|
# Context Managers
|
|
|
|
AgentOps provides native context manager support for traces, allowing you to use Python's `with` statement for automatic trace lifecycle management. This approach ensures traces are properly started and ended, even when exceptions occur.
|
|
|
|
## Basic Usage
|
|
|
|
The simplest way to use context managers is with the `start_trace()` function:
|
|
|
|
```python
|
|
import agentops
|
|
|
|
# Initialize AgentOps
|
|
agentops.init(api_key="your-api-key")
|
|
|
|
# Use context manager for automatic trace management
|
|
with agentops.start_trace("my_workflow") as trace:
|
|
# Your code here
|
|
print("Processing data...")
|
|
# Trace automatically ends when exiting the with block
|
|
```
|
|
|
|
The trace will automatically:
|
|
- Start when entering the `with` block
|
|
- End with "Success" status when exiting normally
|
|
- End with "Error" status if an exception occurs
|
|
- Clean up resources properly in all cases
|
|
|
|
## Advanced Usage
|
|
|
|
### Traces with Tags
|
|
|
|
You can add tags to traces for better organization and filtering:
|
|
|
|
```python
|
|
import agentops
|
|
|
|
agentops.init(api_key="your-api-key")
|
|
|
|
# Using list tags
|
|
with agentops.start_trace("data_processing", tags=["batch", "production"]):
|
|
process_batch_data()
|
|
|
|
# Using dictionary tags for more structured metadata
|
|
with agentops.start_trace("user_request", tags={
|
|
"user_id": "12345",
|
|
"request_type": "query",
|
|
"priority": "high"
|
|
}):
|
|
handle_user_request()
|
|
```
|
|
|
|
### Parallel Traces
|
|
|
|
Context managers create independent parallel traces, not parent-child relationships:
|
|
|
|
```python
|
|
import agentops
|
|
|
|
agentops.init(api_key="your-api-key")
|
|
|
|
# Sequential parallel traces
|
|
with agentops.start_trace("task_1"):
|
|
print("Task 1 executing")
|
|
|
|
with agentops.start_trace("task_2"):
|
|
print("Task 2 executing")
|
|
|
|
# Nested context managers create parallel traces
|
|
with agentops.start_trace("outer_workflow"):
|
|
print("Outer workflow started")
|
|
|
|
with agentops.start_trace("inner_task"):
|
|
print("Inner task executing (parallel to outer)")
|
|
|
|
print("Outer workflow continuing")
|
|
```
|
|
|
|
### Exception Handling
|
|
|
|
Context managers automatically handle exceptions and set appropriate trace states:
|
|
|
|
```python
|
|
import agentops
|
|
|
|
agentops.init(api_key="your-api-key")
|
|
|
|
# Automatic error handling
|
|
try:
|
|
with agentops.start_trace("risky_operation"):
|
|
# This will automatically set trace status to "Error"
|
|
raise ValueError("Something went wrong")
|
|
except ValueError as e:
|
|
print(f"Caught error: {e}")
|
|
# Trace has already been ended with Error status
|
|
|
|
# Graceful degradation pattern
|
|
try:
|
|
with agentops.start_trace("primary_service"):
|
|
result = call_primary_service()
|
|
except ServiceUnavailableError:
|
|
with agentops.start_trace("fallback_service"):
|
|
result = call_fallback_service()
|
|
```
|
|
|
|
### Concurrent Execution
|
|
|
|
Context managers work seamlessly with threading and asyncio:
|
|
|
|
<CodeGroup>
|
|
|
|
```python Threading
|
|
import agentops
|
|
import threading
|
|
|
|
agentops.init(api_key="your-api-key")
|
|
|
|
# With threading
|
|
def worker_function(worker_id):
|
|
with agentops.start_trace(f"worker_{worker_id}"):
|
|
# Each thread gets its own independent trace
|
|
process_work(worker_id)
|
|
|
|
threads = []
|
|
for i in range(3):
|
|
thread = threading.Thread(target=worker_function, args=(i,))
|
|
threads.append(thread)
|
|
thread.start()
|
|
|
|
for thread in threads:
|
|
thread.join()
|
|
```
|
|
|
|
```python Asyncio
|
|
import agentops
|
|
import asyncio
|
|
|
|
agentops.init(api_key="your-api-key")
|
|
|
|
# With asyncio
|
|
async def async_task(task_id):
|
|
with agentops.start_trace(f"async_task_{task_id}"):
|
|
await asyncio.sleep(0.1) # Simulate async work
|
|
return f"result_{task_id}"
|
|
|
|
async def main():
|
|
tasks = [async_task(i) for i in range(3)]
|
|
results = await asyncio.gather(*tasks)
|
|
return results
|
|
|
|
# Run async tasks
|
|
results = asyncio.run(main())
|
|
```
|
|
|
|
</CodeGroup>
|
|
|
|
## Production Patterns
|
|
|
|
### API Endpoint Monitoring
|
|
|
|
```python
|
|
import agentops
|
|
from flask import Flask, request
|
|
|
|
app = Flask(__name__)
|
|
agentops.init(api_key="your-api-key")
|
|
|
|
@app.route('/api/process', methods=['POST'])
|
|
def process_request():
|
|
# Create trace for each API request
|
|
with agentops.start_trace("api_request", tags={
|
|
"endpoint": "/api/process",
|
|
"method": "POST",
|
|
"user_id": request.headers.get("user-id")
|
|
}):
|
|
try:
|
|
data = request.get_json()
|
|
result = process_data(data)
|
|
return {"status": "success", "result": result}
|
|
except Exception as e:
|
|
# Exception automatically sets trace to Error status
|
|
return {"status": "error", "message": str(e)}, 500
|
|
```
|
|
|
|
### Batch Processing
|
|
|
|
```python
|
|
import agentops
|
|
|
|
agentops.init(api_key="your-api-key")
|
|
|
|
def process_batch(items):
|
|
with agentops.start_trace("batch_processing", tags={
|
|
"batch_size": len(items),
|
|
"batch_type": "data_processing"
|
|
}):
|
|
successful = 0
|
|
failed = 0
|
|
|
|
for item in items:
|
|
try:
|
|
with agentops.start_trace("item_processing", tags={
|
|
"item_id": item.get("id"),
|
|
"item_type": item.get("type")
|
|
}):
|
|
process_item(item)
|
|
successful += 1
|
|
except Exception as e:
|
|
failed += 1
|
|
print(f"Failed to process item {item.get('id')}: {e}")
|
|
|
|
print(f"Batch completed: {successful} successful, {failed} failed")
|
|
```
|
|
|
|
### Retry Logic
|
|
|
|
```python
|
|
import agentops
|
|
import time
|
|
|
|
agentops.init(api_key="your-api-key")
|
|
|
|
def retry_operation(operation_name, max_retries=3):
|
|
for attempt in range(max_retries):
|
|
try:
|
|
with agentops.start_trace(f"{operation_name}_attempt_{attempt + 1}", tags={
|
|
"operation": operation_name,
|
|
"attempt": attempt + 1,
|
|
"max_retries": max_retries
|
|
}):
|
|
# Your operation here
|
|
result = perform_operation()
|
|
return result # Success - exit retry loop
|
|
|
|
except Exception as e:
|
|
if attempt < max_retries - 1:
|
|
wait_time = 2 ** attempt # Exponential backoff
|
|
print(f"Attempt {attempt + 1} failed: {e}. Retrying in {wait_time}s...")
|
|
time.sleep(wait_time)
|
|
else:
|
|
print(f"All {max_retries} attempts failed")
|
|
raise
|
|
```
|
|
|
|
## Backward Compatibility
|
|
|
|
Context managers are fully backward compatible with existing AgentOps code patterns:
|
|
|
|
<CodeGroup>
|
|
|
|
```python Manual Management
|
|
import agentops
|
|
|
|
agentops.init(api_key="your-api-key")
|
|
|
|
# Manual trace management (legacy)
|
|
trace = agentops.start_trace("manual_trace")
|
|
# ... your code ...
|
|
agentops.end_trace(trace, "Success")
|
|
```
|
|
|
|
```python Context Manager
|
|
import agentops
|
|
|
|
agentops.init(api_key="your-api-key")
|
|
|
|
# Context manager (new, recommended)
|
|
with agentops.start_trace("context_managed_trace") as trace:
|
|
# ... your code ...
|
|
pass # Automatically ended
|
|
```
|
|
|
|
```python Property Access
|
|
import agentops
|
|
|
|
agentops.init(api_key="your-api-key")
|
|
|
|
# Accessing trace properties
|
|
with agentops.start_trace("property_access") as trace:
|
|
span = trace.span # Access underlying span
|
|
trace_id = trace.span.get_span_context().trace_id
|
|
```
|
|
|
|
```python Mixed Usage
|
|
import agentops
|
|
|
|
agentops.init(api_key="your-api-key")
|
|
|
|
# Mixed usage
|
|
trace = agentops.start_trace("mixed_usage")
|
|
try:
|
|
with trace: # Use existing trace as context manager
|
|
# ... your code ...
|
|
pass
|
|
except Exception:
|
|
agentops.end_trace(trace, "Error")
|
|
```
|
|
|
|
</CodeGroup>
|
|
|
|
## Examples
|
|
|
|
For complete working examples, see the following files in the AgentOps repository:
|
|
|
|
<CardGroup cols={2}>
|
|
<Card title="Basic Usage" icon="play" href="https://github.com/AgentOps-AI/agentops/blob/main/examples/context_manager/basic_usage.py">
|
|
Simple context manager patterns and error handling
|
|
</Card>
|
|
<Card title="Parallel Traces" icon="arrows-split-up-and-left" href="https://github.com/AgentOps-AI/agentops/blob/main/examples/context_manager/parallel_traces.py">
|
|
Sequential, nested, and concurrent trace patterns
|
|
</Card>
|
|
<Card title="Error Handling" icon="shield-exclamation" href="https://github.com/AgentOps-AI/agentops/blob/main/examples/context_manager/error_handling.py">
|
|
Exception handling, retry patterns, and graceful degradation
|
|
</Card>
|
|
<Card title="Production Patterns" icon="server" href="https://github.com/AgentOps-AI/agentops/blob/main/examples/context_manager/production_patterns.py">
|
|
API endpoints, batch processing, microservices, and monitoring
|
|
</Card>
|
|
</CardGroup>
|
|
|
|
These examples demonstrate real-world usage patterns and best practices for using AgentOps context managers in production applications.
|
|
|
|
## API Reference
|
|
|
|
For detailed API information, see the [SDK Reference](/v2/usage/sdk-reference#trace-management) documentation.
|