Feuille de chaleur de cadre d'IA pyrantique
Aperçu général
Pydantique L'IA est un puissant cadre d'agents Python conçu pour rendre les applications de production de bâtiment plus simples et plus fiables. Construite en plus de la populaire bibliothèque de validation de données Pydantic, l'IA Pydantic comble l'écart entre les applications Python traditionnelles et les workflows pilotés par l'IA en fournissant une sécurité de type robuste, la validation des schémas et des sorties structurées pour les interactions avec l'IA.
Ce qui distingue l'IA pydantique est son accent sur la préparation à la production et la sécurité de type. Alors que de nombreux cadres d'IA priorisent la flexibilité au détriment de la fiabilité, l'IA Pydantic veille à ce que les sorties générées par l'IA soient conformes aux schémas attendus, ce qui facilite la construction d'applications robustes qui peuvent gérer l'imprévisibilité de grands modèles linguistiques. En tirant parti des annotations de type de Python et des capacités de validation de Pydantic, le cadre fournit une approche structurée du développement de l'IA qui réduit le code de plaque de chaudière et les erreurs potentielles d'exécution.
Pydantique L'IA est particulièrement précieuse pour les développeurs qui ont besoin d'intégrer les capacités d'IA dans les applications Python existantes ou de construire de nouvelles fonctionnalités alimentées par l'IA avec confiance. Son accent sur la sécurité de type, la validation et l'intégration propre avec les pratiques modernes Python en fait un excellent choix pour les environnements de production où la fiabilité et la maintenance sont primordiales.
Installation et configuration
Installation de base
# Install Pydantic AI
pip install pydantic-ai
# Install with optional dependencies
pip install "pydantic-ai[all]"
# Install development version
pip install git+https://github.com/pydantic/pydantic-ai.git
Configuration de l'environnement
import os
from pydantic_ai import Agent, Output, Prompt
# Set up API keys
os.environ["OPENAI_API_KEY"] = "your-openai-api-key"
# Basic agent configuration
agent = Agent(
model="gpt-4",
temperature=0.7,
max_tokens=1000
)
```_
### Structure du projet
pydantic_ai_project/ ├── agents/ │ ├── init.py │ ├── text_agent.py │ └── structured_agent.py ├── models/ │ ├── init.py │ ├── input_models.py │ └── output_models.py ├── prompts/ │ ├── init.py │ └── templates.py ├── services/ │ ├── init.py │ └── ai_service.py ├── utils/ │ ├── init.py │ └── validators.py ├── config/ │ ├── init.py │ └── settings.py └── main.py
## Concepts fondamentaux
### Agent
La classe Agent est l'interface principale pour interagir avec les modèles de langage. Il gère la communication avec le LLM sous-jacent et fournit des méthodes pour générer des réponses.
### Rapide
Les instructions fournies par les fournisseurs définissent les instructions envoyées au modèle de langue. L'IA pydantique fournit des moyens structurés pour créer et gérer des invites.
### Produit
Les classes de résultats définissent la structure attendue des réponses à partir du modèle linguistique. Ils tirent parti des capacités de validation de Pydantic pour s'assurer que les réponses sont conformes au schéma prévu.
### Validateur
Les validateurs sont des fonctions qui vérifient si la sortie générée répond à des critères spécifiques au-delà de la validation de base du schéma.
## Utilisation de base
### Création d'un Agent Simple
```python
from pydantic_ai import Agent
# Create a basic agent
agent = Agent(
model="gpt-4",
temperature=0.7,
max_tokens=1000
)
# Generate a simple text response
response = agent.run("Explain quantum computing in simple terms.")
print(response)
Sortie structurée avec modèles pyrantiques
from pydantic_ai import Agent, Output
from pydantic import BaseModel, Field
from typing import List
# Define output schema
class MovieRecommendation(BaseModel):
title: str = Field(description="The title of the movie")
year: int = Field(description="The year the movie was released")
director: str = Field(description="The director of the movie")
genre: List[str] = Field(description="List of genres for the movie")
rating: float = Field(description="Rating from 0.0 to 10.0")
class MovieRecommendations(BaseModel):
recommendations: List[MovieRecommendation] = Field(description="List of movie recommendations")
reasoning: str = Field(description="Explanation for these recommendations")
# Create output definition
movie_output = Output(MovieRecommendations)
# Create agent and get structured recommendations
agent = Agent(model="gpt-4")
result = agent.run(
"Recommend 3 science fiction movies from the 1980s",
output=movie_output
)
# Access structured data
for movie in result.recommendations:
print(f"\\\\{movie.title\\\\} (\\\\{movie.year\\\\}) - Directed by \\\\{movie.director\\\\}")
print(f"Genres: \\\\{', '.join(movie.genre)\\\\}")
print(f"Rating: \\\\{movie.rating\\\\}/10")
print()
Modèles rapides
from pydantic_ai import Agent, Prompt
from typing import List
# Create a prompt template
movie_prompt = Prompt(
"""
You are a movie expert with extensive knowledge of cinema history.
Please recommend \\\\{num_movies\\\\} movies that match these criteria:
- Genre: \\\\{genre\\\\}
- Time period: \\\\{era\\\\}
- Mood: \\\\{mood\\\\}
For each movie, provide:
1. Title
2. Year of release
3. Director
4. Brief plot summary
5. Why it matches the criteria
"""
)
# Use the template with parameters
agent = Agent(model="gpt-4")
response = agent.run(
movie_prompt.format(
num_movies=3,
genre="Film Noir",
era="1940s",
mood="Suspenseful"
)
)
print(response)
Caractéristiques avancées
Prompts structurés avec Pydantic
from pydantic_ai import Agent, StructuredPrompt
from pydantic import BaseModel, Field
from typing import List, Optional
# Define input schema
class MovieCriteria(BaseModel):
genres: List[str] = Field(description="List of movie genres")
release_years: Optional[List[int]] = Field(description="List of years or range of years")
directors: Optional[List[str]] = Field(description="List of directors to include")
exclude_directors: Optional[List[str]] = Field(description="List of directors to exclude")
min_rating: Optional[float] = Field(description="Minimum rating threshold (0-10)")
keywords: Optional[List[str]] = Field(description="Thematic keywords to match")
# Create structured prompt
movie_prompt = StructuredPrompt(
"""
As a film expert, recommend 5 movies that match the following criteria:
\\\\{\\\\{criteria\\\\}\\\\}
For each movie, provide the title, year, director, and a brief explanation of why it matches the criteria.
""",
criteria=MovieCriteria
)
# Use structured prompt
agent = Agent(model="gpt-4")
response = agent.run(
movie_prompt,
criteria=MovieCriteria(
genres=["Science Fiction", "Horror"],
release_years=[1970, 1971, 1972, 1973, 1974, 1975, 1976, 1977, 1978, 1979],
directors=["John Carpenter", "David Cronenberg", "Ridley Scott"],
min_rating=7.5,
keywords=["Body horror", "Dystopia", "Alien"]
)
)
print(response)
Validateurs personnalisés
from pydantic_ai import Agent, Output, Validator
from pydantic import BaseModel, Field
from typing import List
# Define output schema
class NewsArticleSummary(BaseModel):
title: str = Field(description="The title of the article")
source: str = Field(description="The source of the article")
summary: str = Field(description="A concise summary of the article")
key_points: List[str] = Field(description="Key points from the article")
bias_assessment: str = Field(description="Assessment of potential bias in the article")
# Create custom validators
def check_summary_length(output: NewsArticleSummary) -> bool:
"""Ensure summary is between 100 and 300 characters."""
return 100 <= len(output.summary) <= 300
def check_key_points(output: NewsArticleSummary) -> bool:
"""Ensure there are 3-5 key points and none are too long."""
if not (3 <= len(output.key_points) <= 5):
return False
return all(len(point) <= 100 for point in output.key_points)
# Create validator with custom checks
news_validator = Validator(
checks=[check_summary_length, check_key_points],
max_retries=3
)
# Create output with validator
news_output = Output(
NewsArticleSummary,
validator=news_validator
)
# Use with agent
agent = Agent(model="gpt-4")
result = agent.run(
"Summarize this news article about climate change: [article text here]",
output=news_output
)
print(f"Title: \\\\{result.title\\\\}")
print(f"Source: \\\\{result.source\\\\}")
print(f"Summary: \\\\{result.summary\\\\}")
print("Key Points:")
for point in result.key_points:
print(f"- \\\\{point\\\\}")
print(f"Bias Assessment: \\\\{result.bias_assessment\\\\}")
Rationalisation des réponses
from pydantic_ai import Agent
import asyncio
# Create agent
agent = Agent(model="gpt-4")
# Synchronous streaming
for chunk in agent.stream("Write a short story about a robot learning to paint."):
print(chunk, end="", flush=True)
# Asynchronous streaming
async def stream_response():
async for chunk in agent.astream("Write a poem about artificial intelligence."):
print(chunk, end="", flush=True)
asyncio.run(stream_response())
Fonction Appel
from pydantic_ai import Agent, Function
from pydantic import BaseModel, Field
from typing import List, Optional
# Define function input schema
class WeatherRequest(BaseModel):
location: str = Field(description="City and country or postal code")
forecast_days: Optional[int] = Field(default=1, description="Number of days to forecast")
units: Optional[str] = Field(default="metric", description="Units system (metric or imperial)")
# Define function
def get_weather(request: WeatherRequest) -> str:
"""Get the current weather and forecast for a location."""
# In a real application, this would call a weather API
return f"Weather for \\\\{request.location\\\\}: Sunny, 25°C, with light winds."
# Register function with agent
agent = Agent(model="gpt-4")
weather_function = Function(get_weather)
agent.register_function(weather_function)
# Use function calling
response = agent.run(
"What's the weather like in Paris, France today?",
functions=[weather_function]
)
print(response)
Intégration des outils
from pydantic_ai import Agent, Tool
from pydantic import BaseModel, Field
from typing import List, Optional
import requests
# Define tool input schema
class SearchQuery(BaseModel):
query: str = Field(description="Search query string")
num_results: Optional[int] = Field(default=5, description="Number of results to return")
# Define tool output schema
class SearchResult(BaseModel):
title: str = Field(description="Title of the search result")
url: str = Field(description="URL of the search result")
snippet: str = Field(description="Text snippet from the search result")
class SearchResults(BaseModel):
results: List[SearchResult] = Field(description="List of search results")
# Create search tool
def web_search(query: SearchQuery) -> SearchResults:
"""Search the web for information."""
# In a real application, this would call a search API
mock_results = [
SearchResult(
title=f"Result \\\\{i\\\\} for \\\\{query.query\\\\}",
url=f"https://example.com/result\\\\{i\\\\}",
snippet=f"This is a snippet for result \\\\{i\\\\} about \\\\{query.query\\\\}..."
)
for i in range(1, query.num_results + 1)
]
return SearchResults(results=mock_results)
# Register tool with agent
agent = Agent(model="gpt-4")
search_tool = Tool(
name="web_search",
function=web_search,
description="Search the web for current information"
)
agent.register_tool(search_tool)
# Use tool in conversation
response = agent.run(
"Find me information about the latest advancements in quantum computing",
tools=[search_tool]
)
print(response)
Modèles avancés
Chaîne de raisonnement de la pensée
from pydantic_ai import Agent, Output
from pydantic import BaseModel, Field
from typing import List
# Define output schema with reasoning steps
class MathSolution(BaseModel):
problem: str = Field(description="The original math problem")
reasoning_steps: List[str] = Field(description="Step-by-step reasoning process")
final_answer: str = Field(description="The final numerical answer")
confidence: float = Field(description="Confidence in the answer (0-1)")
# Create output
math_output = Output(MathSolution)
# Use with agent
agent = Agent(model="gpt-4")
result = agent.run(
"Solve this math problem: If a train travels at 120 km/h and covers a distance of 360 km, how long does the journey take?",
output=math_output
)
print(f"Problem: \\\\{result.problem\\\\}")
print("Reasoning Steps:")
for i, step in enumerate(result.reasoning_steps, 1):
print(f"\\\\{i\\\\}. \\\\{step\\\\}")
print(f"Final Answer: \\\\{result.final_answer\\\\}")
print(f"Confidence: \\\\{result.confidence:.2f\\\\}")
Traitement en plusieurs étapes
from pydantic_ai import Agent, Output
from pydantic import BaseModel, Field
from typing import List
# Define intermediate and final output schemas
class TextAnalysis(BaseModel):
main_topics: List[str] = Field(description="Main topics identified in the text")
sentiment: str = Field(description="Overall sentiment of the text")
key_entities: List[str] = Field(description="Key entities mentioned in the text")
class ArticleSummary(BaseModel):
title: str = Field(description="Suggested title for the article")
summary: str = Field(description="Concise summary of the article")
keywords: List[str] = Field(description="Keywords for SEO")
# Create agent
agent = Agent(model="gpt-4")
# Multi-step process
def process_article(text: str) -> ArticleSummary:
# Step 1: Analyze the text
analysis_output = Output(TextAnalysis)
analysis = agent.run(
f"Analyze this text and identify main topics, sentiment, and key entities:\n\n\\\\{text\\\\}",
output=analysis_output
)
# Step 2: Generate summary based on analysis
summary_output = Output(ArticleSummary)
summary = agent.run(
f"""
Based on the following analysis, create a title, summary, and keywords:
Main Topics: \\\\{', '.join(analysis.main_topics)\\\\}
Sentiment: \\\\{analysis.sentiment\\\\}
Key Entities: \\\\{', '.join(analysis.key_entities)\\\\}
Original Text:
\\\\{text\\\\}
""",
output=summary_output
)
return summary
# Use the multi-step process
article_text = """
[Long article text here...]
"""
result = process_article(article_text)
print(f"Title: \\\\{result.title\\\\}")
print(f"Summary: \\\\{result.summary\\\\}")
print(f"Keywords: \\\\{', '.join(result.keywords)\\\\}")
Gestion des erreurs et retraits
from pydantic_ai import Agent, Output, Validator
from pydantic import BaseModel, Field, ValidationError
from typing import List, Optional
import time
# Define output schema
class CodeSolution(BaseModel):
problem_statement: str = Field(description="The original coding problem")
language: str = Field(description="Programming language used")
code: str = Field(description="The solution code")
explanation: str = Field(description="Explanation of how the code works")
test_cases: List[str] = Field(description="Example test cases")
# Custom validator with specific code checks
def validate_python_code(solution: CodeSolution) -> bool:
if solution.language.lower() != "python":
return True # Skip validation for non-Python code
# Check for common Python syntax issues
code = solution.code
if "import" not in code and "def " not in code:
return False
# Check for test cases
if len(solution.test_cases) < 2:
return False
return True
# Create validator with retry logic
code_validator = Validator(
checks=[validate_python_code],
max_retries=3,
retry_delay=1.0
)
# Create output with validator
code_output = Output(
CodeSolution,
validator=code_validator
)
# Use with agent and handle errors
agent = Agent(model="gpt-4")
try:
result = agent.run(
"Write a Python function to find the longest palindromic substring in a given string.",
output=code_output
)
print(f"Language: \\\\{result.language\\\\}")
print(f"Solution:\n\\\\{result.code\\\\}")
print(f"Explanation: \\\\{result.explanation\\\\}")
print("Test Cases:")
for test in result.test_cases:
print(f"- \\\\{test\\\\}")
except ValidationError as e:
print(f"Validation error: \\\\{e\\\\}")
# Handle validation failure
except Exception as e:
print(f"Error: \\\\{e\\\\}")
# Handle other errors
Opérations Async
from pydantic_ai import Agent, Output
from pydantic import BaseModel, Field
import asyncio
from typing import List
# Define output schemas
class TranslationResult(BaseModel):
original_text: str = Field(description="The original text")
translated_text: str = Field(description="The translated text")
language: str = Field(description="The target language")
# Create agent
agent = Agent(model="gpt-4")
# Async translation function
async def translate_text(text: str, languages: List[str]) -> List[TranslationResult]:
# Create output
translation_output = Output(TranslationResult)
# Create translation tasks
tasks = []
for language in languages:
task = agent.arun(
f"Translate the following text to \\\\{language\\\\}:\n\n\\\\{text\\\\}",
output=translation_output
)
tasks.append(task)
# Run tasks concurrently
results = await asyncio.gather(*tasks)
return results
# Use async function
async def main():
text = "Artificial intelligence is transforming the world in unprecedented ways."
languages = ["Spanish", "French", "German", "Japanese", "Russian"]
translations = await translate_text(text, languages)
for translation in translations:
print(f"\\\\{translation.language\\\\}: \\\\{translation.translated_text\\\\}")
# Run async function
asyncio.run(main())
Intégration aux cadres Web
Intégration FastAPI
from fastapi import FastAPI, HTTPException
from pydantic_ai import Agent, Output
from pydantic import BaseModel, Field
from typing import List
app = FastAPI()
# Initialize agent
agent = Agent(model="gpt-4")
# Define request and response models
class SummaryRequest(BaseModel):
text: str = Field(description="Text to summarize")
max_length: int = Field(default=200, description="Maximum summary length")
class SummaryResponse(BaseModel):
original_length: int = Field(description="Length of original text")
summary: str = Field(description="Generated summary")
keywords: List[str] = Field(description="Key topics in the text")
# Define output schema
class TextSummary(BaseModel):
summary: str = Field(description="Concise summary of the text")
keywords: List[str] = Field(description="Key topics extracted from the text")
# Create endpoint
@app.post("/summarize", response_model=SummaryResponse)
async def summarize_text(request: SummaryRequest):
try:
# Create output
summary_output = Output(TextSummary)
# Generate summary
result = await agent.arun(
f"""
Summarize the following text in no more than \\\\{request.max_length\\\\} characters:
\\\\{request.text\\\\}
""",
output=summary_output
)
# Create response
return SummaryResponse(
original_length=len(request.text),
summary=result.summary,
keywords=result.keywords
)
except Exception as e:
raise HTTPException(status_code=500, detail=str(e))
# Run with: uvicorn app:app --reload
Intégration des flocons
from flask import Flask, request, jsonify
from pydantic_ai import Agent, Output
from pydantic import BaseModel, Field
from typing import List
app = Flask(__name__)
# Initialize agent
agent = Agent(model="gpt-4")
# Define output schema
class ContentGenerator(BaseModel):
title: str = Field(description="Attention-grabbing title")
introduction: str = Field(description="Engaging introduction paragraph")
sections: List[str] = Field(description="Main content sections")
conclusion: str = Field(description="Concluding paragraph")
# Create output
content_output = Output(ContentGenerator)
@app.route("/generate-content", methods=["POST"])
def generate_content():
data = request.json
topic = data.get("topic", "")
tone = data.get("tone", "informative")
length = data.get("length", "medium")
if not topic:
return jsonify(\\\\{"error": "Topic is required"\\\\}), 400
try:
# Generate content
result = agent.run(
f"""
Generate content about "\\\\{topic\\\\}" with a \\\\{tone\\\\} tone.
The content should be \\\\{length\\\\} length.
""",
output=content_output
)
# Create response
return jsonify(\\\\{
"title": result.title,
"introduction": result.introduction,
"sections": result.sections,
"conclusion": result.conclusion
\\\\})
except Exception as e:
return jsonify(\\\\{"error": str(e)\\\\}), 500
# Run with: flask run
Meilleures pratiques
Conception du schéma
- Démarrer Simple: Commencez par des schémas simples et ajoutez progressivement la complexité
- Utiliser les descriptions des champs: Toujours inclure des descriptions claires pour chaque champ
- ** Types appropriés** : Choisissez les types appropriés pour chaque champ (chaîne, int, flotteur, liste, etc.)
- ** Champs facultatifs**: Utiliser Optionnel pour les champs qui pourraient ne pas toujours être présents
- ** Contraintes de validation**: Ajouter des contraintes comme la longueur min/max, les motifs régex, etc.
- Modèles nouveaux: Utiliser des modèles imbriqués pour des structures de données complexes
- Enums: Utilisez les classes Enum pour les champs avec un ensemble fixe de valeurs possibles
Ingénierie rapide
- ** Instructions claires**: Fournir des instructions claires et précises dans les instructions
- Contexte: Inclure le contexte pertinent pour la tâche
- Exemples: Inclure des exemples de résultats attendus dans la mesure du possible
- Format structuré: Utiliser des formats structurés comme des listes ou des sections numérotées
- Éviter l'ambiguïté: Soyez explicite sur ce que vous voulez que le modèle fasse
- Raffinement itératif: Raffiner les appels en fonction des sorties du modèle
Gestion des erreurs
- ** Erreurs de validation**: Poignez les erreurs de validation avec grâce
- Retry Logic: Mettre en œuvre la logique de retry pour les erreurs transitoires
- Fallbacks: Avoir des stratégies de repli lorsque l'approche primaire échoue
- Loging: Erreurs de log et réponses du modèle pour le débogage
- Rétroaction de l'utilisateur: Fournir des messages d'erreur utiles aux utilisateurs
Optimisation des performances
- ** Traitement par lots**: Traiter plusieurs articles par lots lorsque c'est possible
- Cachage: réponses Cache pour des demandes identiques ou similaires
- ** Opérations d'Async** : Utiliser les fonctions async pour les opérations simultanées
- Sélection de modèle: Choisir des modèles appropriés en fonction de la complexité des tâches
- ** Gestion des jetons** : Attention à l'utilisation de jetons pour contrôler les coûts
Dépannage
Questions communes
Défauts de validation du schéma
- Care : La sortie du modèle ne correspond pas au schéma attendu
- Solution: Affinez les invite à être plus explicite sur le format requis, ou ajustez le schéma pour être plus flexible
Produits incompatibles
- Cause: Invitations à vide ou réglages à haute température
- Solution : Plus précise et réduit la température pour des sorties plus cohérentes
Performance lente
- Care: Grandes requêtes, schémas complexes ou traitement inefficace
- Solution: Optimiser les appels, utiliser les opérations d'async ou mettre en place le cache
Utilisation haute
- Cause: Invitations verbales ou contexte inutile
- Solution: Rationaliser les appels, utiliser des modèles plus efficaces ou mettre en œuvre la surveillance de l'utilisation des jetons
*Cette feuille de triche complète Pydantic AI fournit tout le nécessaire pour construire des applications AI de qualité de production avec la sécurité de type et la validation. De la configuration de base aux modèles avancés, utilisez ces exemples et les meilleures pratiques pour créer des fonctionnalités robustes et durables avec l'approche structurée de l'IA Pydantic. *