init
This commit is contained in:
96
functionality/structured_output/README.md
Normal file
96
functionality/structured_output/README.md
Normal file
@@ -0,0 +1,96 @@
|
||||
# Structured Output Example
|
||||
|
||||
## What This Example Demonstrates
|
||||
|
||||
This example showcases **structured output generation** using AgentScope with Pydantic models. It demonstrates how to constrain AI model outputs to follow specific data structures and formats, ensuring consistent and parseable responses.
|
||||
|
||||
### Key Features:
|
||||
- **Structured Data Generation**: Forces agent responses to conform to
|
||||
predefined schemas
|
||||
- **Pydantic Integration**: Uses Pydantic models to define output structure with validation
|
||||
- **Type Safety**: Ensures output data types match expected formats
|
||||
- **Field Validation**: Includes constraints like age limits (0-120) and enum choices
|
||||
- **JSON Output**: Generates clean, structured JSON responses
|
||||
|
||||
### Example Models:
|
||||
|
||||
1. **TableModel**: Structured person information
|
||||
- `name`: Person's name (string)
|
||||
- `age`: Person's age (integer,0-120)
|
||||
- `intro`: One-sentence introduction (string)
|
||||
- `honors`: List of honors/achievements (array of strings)
|
||||
|
||||
2. **ChoiceModel**: Constrained choice selection
|
||||
- `choice`: Must be one of "apple", "banana", or "orange"
|
||||
|
||||
### Use Cases:
|
||||
- **Data Extraction**: Extract structured information from unstructured text
|
||||
- **Form Generation**: Generate consistent data for databases or APIs
|
||||
- **Survey Responses**: Ensure responses fit predefined categories
|
||||
- **Content Classification**: Categorize content into specific types
|
||||
|
||||
## How to Run This Example
|
||||
1. **Set Environment Variable:**
|
||||
```bash
|
||||
export DASHSCOPE_API_KEY="your_dashscope_api_key_here"
|
||||
```
|
||||
2. **Run the script:**
|
||||
```bash
|
||||
python main.py
|
||||
```
|
||||
3. **Expected Output:**
|
||||
The program will generate two structured responses like below:
|
||||
```
|
||||
Structured Output 1:
|
||||
{
|
||||
"name": "Albert Einstein",
|
||||
"age": 76,
|
||||
"intro": 1,
|
||||
"honors": [
|
||||
"Nobel Prize in Physics (1921)",
|
||||
"Copley Medal (1925)"
|
||||
]
|
||||
}
|
||||
Structured Output 2:
|
||||
{
|
||||
"choice": "apple"
|
||||
}
|
||||
```
|
||||
|
||||
>💡**Note:** The specific content will vary with each run since the agent generates different responses, but the JSON structure will always conform to the predefined Pydantic models (`TableModel` and `ChoiceModel`).
|
||||
|
||||
## How It Works:
|
||||
1. The agent receives a query along with a structured_model parameter
|
||||
2. The agent generates a response that conforms to the Pydantic model schema
|
||||
3. The structured data is returned in res.metadata as a validated JSON object
|
||||
4. Pydantic ensures all field types and constraints are satisfied
|
||||
|
||||
## Custom Pydantic Models
|
||||
Create your own structured output models for specific use cases, for example:
|
||||
|
||||
```
|
||||
from typing import Optional
|
||||
from pydantic import BaseModel, Field, EmailStr
|
||||
|
||||
class BusinessModel(BaseModel):
|
||||
"""Business information extraction model."""
|
||||
|
||||
company_name: str = Field(description="Name of the company")
|
||||
industry: str = Field(description="Industry sector")
|
||||
founded_year: int = Field(description="Year founded", ge=1800, le=2024)
|
||||
headquarters: str = Field(description="Location of headquarters")
|
||||
employee_count: Optional[int] = Field(description="Number of employees", ge=1)
|
||||
email: Optional[EmailStr] = Field(description="Contact email address")
|
||||
website: Optional[str] = Field(description="Company website URL")
|
||||
|
||||
# Usage
|
||||
query = Msg("user", "Tell me about Tesla Inc.", "user")
|
||||
res = await agent(query, structured_model=BusinessModel)
|
||||
```
|
||||
|
||||
## Best Practices for Structured Output
|
||||
|
||||
1. **Use Descriptive Field Names:** Make field purposes clear
|
||||
2. **Add Field Descriptions:** Help the agent understand what data to generate
|
||||
3. **Set Validation Constraints:** Use Pydantic validators for data integrity
|
||||
4. **Choose Appropriate Types:** Use specific types like EmailStr, datetime, etc.
|
||||
79
functionality/structured_output/main.py
Normal file
79
functionality/structured_output/main.py
Normal file
@@ -0,0 +1,79 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
"""The main entry point of the structured output example."""
|
||||
import asyncio
|
||||
import json
|
||||
import os
|
||||
from typing import Literal
|
||||
|
||||
from agentscope.agent import ReActAgent
|
||||
from agentscope.formatter import DashScopeChatFormatter
|
||||
from agentscope.memory import InMemoryMemory
|
||||
from agentscope.message import Msg
|
||||
from agentscope.model import DashScopeChatModel
|
||||
from agentscope.tool import Toolkit
|
||||
from pydantic import BaseModel, Field
|
||||
|
||||
|
||||
class TableModel(BaseModel):
|
||||
"""A simple table model for structured output."""
|
||||
|
||||
name: str = Field(description="The name of the person")
|
||||
age: int = Field(description="The age of the person", ge=0, le=120)
|
||||
intro: str = Field(description="A one-sentence introduction of the person")
|
||||
honors: list[str] = Field(
|
||||
description="A list of honors received by this person",
|
||||
)
|
||||
|
||||
|
||||
class ChoiceModel(BaseModel):
|
||||
"""A simple choice model for structured output."""
|
||||
|
||||
choice: Literal["apple", "banana", "orange"] = Field(
|
||||
description="Your choice of fruit",
|
||||
)
|
||||
|
||||
|
||||
async def main() -> None:
|
||||
"""The main entry point for the structured output example."""
|
||||
toolkit = Toolkit()
|
||||
agent = ReActAgent(
|
||||
name="Friday",
|
||||
sys_prompt="You are a helpful assistant named Friday.",
|
||||
model=DashScopeChatModel(
|
||||
api_key=os.environ.get("DASHSCOPE_API_KEY"),
|
||||
model_name="qwen-max",
|
||||
stream=True,
|
||||
),
|
||||
formatter=DashScopeChatFormatter(),
|
||||
toolkit=toolkit,
|
||||
memory=InMemoryMemory(),
|
||||
)
|
||||
|
||||
query_msg_1 = Msg(
|
||||
"user",
|
||||
"Please introduce Einstein",
|
||||
"user",
|
||||
)
|
||||
res = await agent(query_msg_1, structured_model=TableModel)
|
||||
print(
|
||||
"Structured Output 1:\n"
|
||||
"```\n"
|
||||
f"{json.dumps(res.metadata, indent=4)}\n"
|
||||
"```",
|
||||
)
|
||||
|
||||
query_msg_2 = Msg(
|
||||
"user",
|
||||
"Choose one of your favorite fruit",
|
||||
"user",
|
||||
)
|
||||
res = await agent(query_msg_2, structured_model=ChoiceModel)
|
||||
print(
|
||||
"Structured Output 2:\n"
|
||||
"```\n"
|
||||
f"{json.dumps(res.metadata, indent=4)}\n"
|
||||
"```",
|
||||
)
|
||||
|
||||
|
||||
asyncio.run(main())
|
||||
1
functionality/structured_output/requirements.txt
Normal file
1
functionality/structured_output/requirements.txt
Normal file
@@ -0,0 +1 @@
|
||||
agentscope[full]>=1.0.5
|
||||
Reference in New Issue
Block a user