mirror of
https://github.com/microsoft/agent-framework.git
synced 2026-06-16 21:04:09 +08:00
Compare commits
16
Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
9e3b2fa09a | ||
|
|
5687e13221 | ||
|
|
a151f10cc2 | ||
|
|
b773830e4b | ||
|
|
975884f32d | ||
|
|
b5ca0c8eda | ||
|
|
dd3e2b6e53 | ||
|
|
48d124efbe | ||
|
|
6e9420f614 | ||
|
|
2ab859dd94 | ||
|
|
e192af93a7 | ||
|
|
3dbdecedda | ||
|
|
15d0c34d9f | ||
|
|
620da7a829 | ||
|
|
80b25a782b | ||
|
|
ffe2e787ba |
@@ -206,6 +206,7 @@ agents.md
|
||||
WARP.md
|
||||
**/memory-bank/
|
||||
**/projectBrief.md
|
||||
**/tmpclaude*
|
||||
|
||||
# Azurite storage emulator files
|
||||
*/__azurite_db_blob__.json
|
||||
|
||||
@@ -26,7 +26,7 @@
|
||||
<PackageVersion Include="Azure.Identity" Version="1.17.1" />
|
||||
<PackageVersion Include="Azure.Monitor.OpenTelemetry.Exporter" Version="1.4.0" />
|
||||
<!-- Google Gemini -->
|
||||
<PackageVersion Include="Google.GenAI" Version="0.9.0" />
|
||||
<PackageVersion Include="Google.GenAI" Version="0.11.0" />
|
||||
<PackageVersion Include="Mscc.GenerativeAI.Microsoft" Version="2.9.3" />
|
||||
<!-- Microsoft.Azure.* -->
|
||||
<PackageVersion Include="Microsoft.Azure.Cosmos" Version="3.54.0" />
|
||||
|
||||
+1
-1
@@ -21,7 +21,7 @@ var deploymentName = Environment.GetEnvironmentVariable("AZURE_OPENAI_DEPLOYMENT
|
||||
|
||||
var agent = new AzureOpenAIClient(new Uri(endpoint), new AzureCliCredential())
|
||||
.GetOpenAIResponseClient(deploymentName)
|
||||
.CreateAIAgent(name: "HaikuBot", instructions: "You are an upbeat assistant that writes beautifully.");
|
||||
.AsAIAgent(name: "HaikuBot", instructions: "You are an upbeat assistant that writes beautifully.");
|
||||
|
||||
Console.WriteLine(await agent.RunAsync("Write a haiku about Microsoft Agent Framework."));
|
||||
```
|
||||
|
||||
@@ -29,7 +29,7 @@ internal sealed class HostClientAgent
|
||||
// Create the agent that uses the remote agents as tools
|
||||
this.Agent = new OpenAIClient(new ApiKeyCredential(apiKey))
|
||||
.GetChatClient(modelId)
|
||||
.CreateAIAgent(instructions: "You specialize in handling queries for users and using your tools to provide answers.", name: "HostClient", tools: tools);
|
||||
.AsAIAgent(instructions: "You specialize in handling queries for users and using your tools to provide answers.", name: "HostClient", tools: tools);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
|
||||
@@ -35,7 +35,7 @@ internal static class HostAgentFactory
|
||||
{
|
||||
AIAgent agent = new OpenAIClient(apiKey)
|
||||
.GetChatClient(model)
|
||||
.CreateAIAgent(instructions, name, tools: tools);
|
||||
.AsAIAgent(instructions, name, tools: tools);
|
||||
|
||||
AgentCard agentCard = agentType.ToUpperInvariant() switch
|
||||
{
|
||||
|
||||
@@ -83,7 +83,7 @@ public static class Program
|
||||
serverUrl,
|
||||
jsonSerializerOptions: AGUIClientSerializerContext.Default.Options);
|
||||
|
||||
AIAgent agent = chatClient.CreateAIAgent(
|
||||
AIAgent agent = chatClient.AsAIAgent(
|
||||
name: "agui-client",
|
||||
description: "AG-UI Client Agent",
|
||||
tools: [changeBackground, readClientClimateSensors]);
|
||||
|
||||
@@ -33,7 +33,7 @@ internal static class ChatClientAgentFactory
|
||||
{
|
||||
ChatClient chatClient = s_azureOpenAIClient!.GetChatClient(s_deploymentName!);
|
||||
|
||||
return chatClient.AsIChatClient().CreateAIAgent(
|
||||
return chatClient.AsIChatClient().AsAIAgent(
|
||||
name: "AgenticChat",
|
||||
description: "A simple chat agent using Azure OpenAI");
|
||||
}
|
||||
@@ -42,7 +42,7 @@ internal static class ChatClientAgentFactory
|
||||
{
|
||||
ChatClient chatClient = s_azureOpenAIClient!.GetChatClient(s_deploymentName!);
|
||||
|
||||
return chatClient.AsIChatClient().CreateAIAgent(
|
||||
return chatClient.AsIChatClient().AsAIAgent(
|
||||
name: "BackendToolRenderer",
|
||||
description: "An agent that can render backend tools using Azure OpenAI",
|
||||
tools: [AIFunctionFactory.Create(
|
||||
@@ -56,7 +56,7 @@ internal static class ChatClientAgentFactory
|
||||
{
|
||||
ChatClient chatClient = s_azureOpenAIClient!.GetChatClient(s_deploymentName!);
|
||||
|
||||
return chatClient.AsIChatClient().CreateAIAgent(
|
||||
return chatClient.AsIChatClient().AsAIAgent(
|
||||
name: "HumanInTheLoopAgent",
|
||||
description: "An agent that involves human feedback in its decision-making process using Azure OpenAI");
|
||||
}
|
||||
@@ -65,7 +65,7 @@ internal static class ChatClientAgentFactory
|
||||
{
|
||||
ChatClient chatClient = s_azureOpenAIClient!.GetChatClient(s_deploymentName!);
|
||||
|
||||
return chatClient.AsIChatClient().CreateAIAgent(
|
||||
return chatClient.AsIChatClient().AsAIAgent(
|
||||
name: "ToolBasedGenerativeUIAgent",
|
||||
description: "An agent that uses tools to generate user interfaces using Azure OpenAI");
|
||||
}
|
||||
@@ -73,7 +73,7 @@ internal static class ChatClientAgentFactory
|
||||
public static AIAgent CreateAgenticUI(JsonSerializerOptions options)
|
||||
{
|
||||
ChatClient chatClient = s_azureOpenAIClient!.GetChatClient(s_deploymentName!);
|
||||
var baseAgent = chatClient.AsIChatClient().CreateAIAgent(new ChatClientAgentOptions
|
||||
var baseAgent = chatClient.AsIChatClient().AsAIAgent(new ChatClientAgentOptions
|
||||
{
|
||||
Name = "AgenticUIAgent",
|
||||
Description = "An agent that generates agentic user interfaces using Azure OpenAI",
|
||||
@@ -116,7 +116,7 @@ internal static class ChatClientAgentFactory
|
||||
{
|
||||
ChatClient chatClient = s_azureOpenAIClient!.GetChatClient(s_deploymentName!);
|
||||
|
||||
var baseAgent = chatClient.AsIChatClient().CreateAIAgent(
|
||||
var baseAgent = chatClient.AsIChatClient().AsAIAgent(
|
||||
name: "SharedStateAgent",
|
||||
description: "An agent that demonstrates shared state patterns using Azure OpenAI");
|
||||
|
||||
@@ -127,7 +127,7 @@ internal static class ChatClientAgentFactory
|
||||
{
|
||||
ChatClient chatClient = s_azureOpenAIClient!.GetChatClient(s_deploymentName!);
|
||||
|
||||
var baseAgent = chatClient.AsIChatClient().CreateAIAgent(new ChatClientAgentOptions
|
||||
var baseAgent = chatClient.AsIChatClient().AsAIAgent(new ChatClientAgentOptions
|
||||
{
|
||||
Name = "PredictiveStateUpdatesAgent",
|
||||
Description = "An agent that demonstrates predictive state updates using Azure OpenAI",
|
||||
|
||||
@@ -23,7 +23,7 @@ var agent = new AzureOpenAIClient(
|
||||
new Uri(endpoint),
|
||||
new DefaultAzureCredential())
|
||||
.GetChatClient(deploymentName)
|
||||
.CreateAIAgent(
|
||||
.AsAIAgent(
|
||||
name: "AGUIAssistant",
|
||||
tools: [
|
||||
AIFunctionFactory.Create(
|
||||
|
||||
@@ -119,7 +119,7 @@ The `AGUIServer` uses the `MapAGUI` extension method to expose an agent through
|
||||
```csharp
|
||||
AIAgent agent = new OpenAIClient(apiKey)
|
||||
.GetChatClient(model)
|
||||
.CreateAIAgent(
|
||||
.AsAIAgent(
|
||||
instructions: "You are a helpful assistant.",
|
||||
name: "AGUIAssistant");
|
||||
|
||||
@@ -144,7 +144,7 @@ var chatClient = new AGUIChatClient(
|
||||
modelId: "agui-client",
|
||||
jsonSerializerOptions: null);
|
||||
|
||||
AIAgent agent = chatClient.CreateAIAgent(
|
||||
AIAgent agent = chatClient.AsAIAgent(
|
||||
instructions: null,
|
||||
name: "agui-client",
|
||||
description: "AG-UI Client Agent",
|
||||
|
||||
@@ -74,7 +74,7 @@ AzureOpenAIClient azureOpenAIClient = new AzureOpenAIClient(
|
||||
ChatClient chatClient = azureOpenAIClient.GetChatClient(deploymentName);
|
||||
|
||||
// Create AI agent
|
||||
ChatClientAgent agent = chatClient.AsIChatClient().CreateAIAgent(
|
||||
ChatClientAgent agent = chatClient.AsIChatClient().AsAIAgent(
|
||||
name: "ChatAssistant",
|
||||
instructions: "You are a helpful assistant.");
|
||||
|
||||
@@ -162,7 +162,7 @@ dotnet run
|
||||
Edit the instructions in `Server/Program.cs`:
|
||||
|
||||
```csharp
|
||||
ChatClientAgent agent = chatClient.AsIChatClient().CreateAIAgent(
|
||||
ChatClientAgent agent = chatClient.AsIChatClient().AsAIAgent(
|
||||
name: "ChatAssistant",
|
||||
instructions: "You are a helpful coding assistant specializing in C# and .NET.");
|
||||
```
|
||||
|
||||
@@ -25,7 +25,7 @@ AzureOpenAIClient azureOpenAIClient = new(
|
||||
|
||||
ChatClient chatClient = azureOpenAIClient.GetChatClient(deploymentName);
|
||||
|
||||
ChatClientAgent agent = chatClient.AsIChatClient().CreateAIAgent(
|
||||
ChatClientAgent agent = chatClient.AsIChatClient().AsAIAgent(
|
||||
name: "ChatAssistant",
|
||||
instructions: "You are a helpful assistant.");
|
||||
|
||||
|
||||
@@ -25,7 +25,7 @@ AzureOpenAIClient client = !string.IsNullOrEmpty(azureOpenAiKey)
|
||||
const string JokerName = "Joker";
|
||||
const string JokerInstructions = "You are good at telling jokes.";
|
||||
|
||||
AIAgent agent = client.GetChatClient(deploymentName).CreateAIAgent(JokerInstructions, JokerName);
|
||||
AIAgent agent = client.GetChatClient(deploymentName).AsAIAgent(JokerInstructions, JokerName);
|
||||
|
||||
// Configure the function app to host the AI agent.
|
||||
// This will automatically generate HTTP API endpoints for the agent.
|
||||
|
||||
@@ -29,7 +29,7 @@ const string WriterInstructions =
|
||||
when given an improved sentence you polish it further.
|
||||
""";
|
||||
|
||||
AIAgent writerAgent = client.GetChatClient(deploymentName).CreateAIAgent(WriterInstructions, WriterName);
|
||||
AIAgent writerAgent = client.GetChatClient(deploymentName).AsAIAgent(WriterInstructions, WriterName);
|
||||
|
||||
using IHost app = FunctionsApplication
|
||||
.CreateBuilder(args)
|
||||
|
||||
@@ -28,8 +28,8 @@ const string PhysicistInstructions = "You are an expert in physics. You answer q
|
||||
const string ChemistName = "ChemistAgent";
|
||||
const string ChemistInstructions = "You are an expert in chemistry. You answer questions from a chemistry perspective.";
|
||||
|
||||
AIAgent physicistAgent = client.GetChatClient(deploymentName).CreateAIAgent(PhysicistInstructions, PhysicistName);
|
||||
AIAgent chemistAgent = client.GetChatClient(deploymentName).CreateAIAgent(ChemistInstructions, ChemistName);
|
||||
AIAgent physicistAgent = client.GetChatClient(deploymentName).AsAIAgent(PhysicistInstructions, PhysicistName);
|
||||
AIAgent chemistAgent = client.GetChatClient(deploymentName).AsAIAgent(ChemistInstructions, ChemistName);
|
||||
|
||||
using IHost app = FunctionsApplication
|
||||
.CreateBuilder(args)
|
||||
|
||||
@@ -29,10 +29,10 @@ const string EmailAssistantName = "EmailAssistantAgent";
|
||||
const string EmailAssistantInstructions = "You are an email assistant that helps users draft responses to emails with professionalism.";
|
||||
|
||||
AIAgent spamDetectionAgent = client.GetChatClient(deploymentName)
|
||||
.CreateAIAgent(SpamDetectionInstructions, SpamDetectionName);
|
||||
.AsAIAgent(SpamDetectionInstructions, SpamDetectionName);
|
||||
|
||||
AIAgent emailAssistantAgent = client.GetChatClient(deploymentName)
|
||||
.CreateAIAgent(EmailAssistantInstructions, EmailAssistantName);
|
||||
.AsAIAgent(EmailAssistantInstructions, EmailAssistantName);
|
||||
|
||||
using IHost app = FunctionsApplication
|
||||
.CreateBuilder(args)
|
||||
|
||||
@@ -29,7 +29,7 @@ const string WriterInstructions =
|
||||
You write engaging, informative, and well-structured content that follows best practices for readability and accuracy.
|
||||
""";
|
||||
|
||||
AIAgent writerAgent = client.GetChatClient(deploymentName).CreateAIAgent(WriterInstructions, WriterName);
|
||||
AIAgent writerAgent = client.GetChatClient(deploymentName).AsAIAgent(WriterInstructions, WriterName);
|
||||
|
||||
using IHost app = FunctionsApplication
|
||||
.CreateBuilder(args)
|
||||
|
||||
@@ -33,7 +33,7 @@ const string WriterAgentInstructions =
|
||||
You write engaging, informative, and well-structured content that follows best practices for readability and accuracy.
|
||||
""";
|
||||
|
||||
AIAgent writerAgent = client.GetChatClient(deploymentName).CreateAIAgent(WriterAgentInstructions, WriterAgentName);
|
||||
AIAgent writerAgent = client.GetChatClient(deploymentName).AsAIAgent(WriterAgentInstructions, WriterAgentName);
|
||||
|
||||
// Agent that can start content generation workflows using tools
|
||||
const string PublisherAgentName = "Publisher";
|
||||
@@ -57,7 +57,7 @@ using IHost app = FunctionsApplication
|
||||
// Initialize the tools to be used by the agent.
|
||||
Tools publisherTools = new(sp.GetRequiredService<ILogger<Tools>>());
|
||||
|
||||
return client.GetChatClient(deploymentName).CreateAIAgent(
|
||||
return client.GetChatClient(deploymentName).AsAIAgent(
|
||||
instructions: PublisherAgentInstructions,
|
||||
name: PublisherAgentName,
|
||||
services: sp,
|
||||
|
||||
@@ -28,13 +28,13 @@ AzureOpenAIClient client = !string.IsNullOrEmpty(azureOpenAiKey)
|
||||
: new AzureOpenAIClient(new Uri(endpoint), new AzureCliCredential());
|
||||
|
||||
// Define three AI agents we are going to use in this application.
|
||||
AIAgent agent1 = client.GetChatClient(deploymentName).CreateAIAgent("You are good at telling jokes.", "Joker");
|
||||
AIAgent agent1 = client.GetChatClient(deploymentName).AsAIAgent("You are good at telling jokes.", "Joker");
|
||||
|
||||
AIAgent agent2 = client.GetChatClient(deploymentName)
|
||||
.CreateAIAgent("Check stock prices.", "StockAdvisor");
|
||||
.AsAIAgent("Check stock prices.", "StockAdvisor");
|
||||
|
||||
AIAgent agent3 = client.GetChatClient(deploymentName)
|
||||
.CreateAIAgent("Recommend plants.", "PlantAdvisor", description: "Get plant recommendations.");
|
||||
.AsAIAgent("Recommend plants.", "PlantAdvisor", description: "Get plant recommendations.");
|
||||
|
||||
using IHost app = FunctionsApplication
|
||||
.CreateBuilder(args)
|
||||
|
||||
@@ -70,7 +70,7 @@ FunctionsApplicationBuilder builder = FunctionsApplication
|
||||
// Define the Travel Planner agent with tools for weather and events
|
||||
options.AddAIAgentFactory(TravelPlannerName, sp =>
|
||||
{
|
||||
return client.GetChatClient(deploymentName).CreateAIAgent(
|
||||
return client.GetChatClient(deploymentName).AsAIAgent(
|
||||
instructions: TravelPlannerInstructions,
|
||||
name: TravelPlannerName,
|
||||
services: sp,
|
||||
|
||||
@@ -23,14 +23,14 @@ A2ACardResolver agentCardResolver = new(new Uri(a2aAgentHost));
|
||||
AgentCard agentCard = await agentCardResolver.GetAgentCardAsync();
|
||||
|
||||
// Create an instance of the AIAgent for an existing A2A agent specified by the agent card.
|
||||
AIAgent a2aAgent = agentCard.GetAIAgent();
|
||||
AIAgent a2aAgent = agentCard.AsAIAgent();
|
||||
|
||||
// Create the main agent, and provide the a2a agent skills as a function tools.
|
||||
AIAgent agent = new AzureOpenAIClient(
|
||||
new Uri(endpoint),
|
||||
new AzureCliCredential())
|
||||
.GetChatClient(deploymentName)
|
||||
.CreateAIAgent(
|
||||
.AsAIAgent(
|
||||
instructions: "You are a helpful assistant that helps people with travel planning.",
|
||||
tools: [.. CreateFunctionTools(a2aAgent, agentCard)]
|
||||
);
|
||||
|
||||
@@ -14,7 +14,7 @@ A2ACardResolver agentCardResolver = new(new Uri(a2aAgentHost));
|
||||
AgentCard agentCard = await agentCardResolver.GetAgentCardAsync();
|
||||
|
||||
// Create an instance of the AIAgent for an existing A2A agent specified by the agent card.
|
||||
AIAgent agent = agentCard.GetAIAgent();
|
||||
AIAgent agent = agentCard.AsAIAgent();
|
||||
|
||||
AgentThread thread = await agent.GetNewThreadAsync();
|
||||
|
||||
|
||||
@@ -16,7 +16,7 @@ using HttpClient httpClient = new()
|
||||
|
||||
AGUIChatClient chatClient = new(httpClient, serverUrl);
|
||||
|
||||
AIAgent agent = chatClient.CreateAIAgent(
|
||||
AIAgent agent = chatClient.AsAIAgent(
|
||||
name: "agui-client",
|
||||
description: "AG-UI Client Agent");
|
||||
|
||||
|
||||
@@ -24,7 +24,7 @@ ChatClient chatClient = new AzureOpenAIClient(
|
||||
new DefaultAzureCredential())
|
||||
.GetChatClient(deploymentName);
|
||||
|
||||
AIAgent agent = chatClient.AsIChatClient().CreateAIAgent(
|
||||
AIAgent agent = chatClient.AsIChatClient().AsAIAgent(
|
||||
name: "AGUIAssistant",
|
||||
instructions: "You are a helpful assistant.");
|
||||
|
||||
|
||||
@@ -16,7 +16,7 @@ using HttpClient httpClient = new()
|
||||
|
||||
AGUIChatClient chatClient = new(httpClient, serverUrl);
|
||||
|
||||
AIAgent agent = chatClient.CreateAIAgent(
|
||||
AIAgent agent = chatClient.AsAIAgent(
|
||||
name: "agui-client",
|
||||
description: "AG-UI Client Agent");
|
||||
|
||||
|
||||
@@ -79,7 +79,7 @@ ChatClient chatClient = new AzureOpenAIClient(
|
||||
new DefaultAzureCredential())
|
||||
.GetChatClient(deploymentName);
|
||||
|
||||
ChatClientAgent agent = chatClient.AsIChatClient().CreateAIAgent(
|
||||
ChatClientAgent agent = chatClient.AsIChatClient().AsAIAgent(
|
||||
name: "AGUIAssistant",
|
||||
instructions: "You are a helpful assistant with access to restaurant information.",
|
||||
tools: tools);
|
||||
|
||||
@@ -28,7 +28,7 @@ using HttpClient httpClient = new()
|
||||
|
||||
AGUIChatClient chatClient = new(httpClient, serverUrl);
|
||||
|
||||
AIAgent agent = chatClient.CreateAIAgent(
|
||||
AIAgent agent = chatClient.AsAIAgent(
|
||||
name: "agui-client",
|
||||
description: "AG-UI Client Agent",
|
||||
tools: frontendTools);
|
||||
|
||||
@@ -24,7 +24,7 @@ ChatClient chatClient = new AzureOpenAIClient(
|
||||
new DefaultAzureCredential())
|
||||
.GetChatClient(deploymentName);
|
||||
|
||||
AIAgent agent = chatClient.AsIChatClient().CreateAIAgent(
|
||||
AIAgent agent = chatClient.AsIChatClient().AsAIAgent(
|
||||
name: "AGUIAssistant",
|
||||
instructions: "You are a helpful assistant.");
|
||||
|
||||
|
||||
@@ -16,7 +16,7 @@ using HttpClient httpClient = new()
|
||||
AGUIChatClient chatClient = new(httpClient, serverUrl);
|
||||
|
||||
// Create agent
|
||||
ChatClientAgent baseAgent = chatClient.CreateAIAgent(
|
||||
ChatClientAgent baseAgent = chatClient.AsAIAgent(
|
||||
name: "AGUIAssistant",
|
||||
instructions: "You are a helpful assistant.");
|
||||
|
||||
|
||||
@@ -57,7 +57,7 @@ ChatClient openAIChatClient = new AzureOpenAIClient(
|
||||
new DefaultAzureCredential())
|
||||
.GetChatClient(deploymentName);
|
||||
|
||||
ChatClientAgent baseAgent = openAIChatClient.AsIChatClient().CreateAIAgent(
|
||||
ChatClientAgent baseAgent = openAIChatClient.AsIChatClient().AsAIAgent(
|
||||
name: "AGUIAssistant",
|
||||
instructions: "You are a helpful assistant in charge of approving expenses",
|
||||
tools: tools);
|
||||
|
||||
@@ -19,7 +19,7 @@ using HttpClient httpClient = new()
|
||||
|
||||
AGUIChatClient chatClient = new(httpClient, serverUrl);
|
||||
|
||||
AIAgent baseAgent = chatClient.CreateAIAgent(
|
||||
AIAgent baseAgent = chatClient.AsAIAgent(
|
||||
name: "recipe-client",
|
||||
description: "AG-UI Recipe Client Agent");
|
||||
|
||||
|
||||
@@ -34,7 +34,7 @@ ChatClient chatClient = new AzureOpenAIClient(
|
||||
new DefaultAzureCredential())
|
||||
.GetChatClient(deploymentName);
|
||||
|
||||
AIAgent baseAgent = chatClient.AsIChatClient().CreateAIAgent(
|
||||
AIAgent baseAgent = chatClient.AsIChatClient().AsAIAgent(
|
||||
name: "RecipeAgent",
|
||||
instructions: """
|
||||
You are a helpful recipe assistant. When users ask you to create or suggest a recipe,
|
||||
|
||||
@@ -26,7 +26,7 @@ using Microsoft.Agents.AI.A2A;
|
||||
A2AClient a2aClient = new(new Uri("https://your-a2a-agent-host/echo"));
|
||||
|
||||
// Create an AIAgent from the A2AClient
|
||||
AIAgent agent = a2aClient.GetAIAgent();
|
||||
AIAgent agent = a2aClient.AsAIAgent();
|
||||
|
||||
// Run the agent
|
||||
AgentResponse response = await agent.RunAsync("Tell me a joke about a pirate.");
|
||||
|
||||
@@ -26,7 +26,7 @@ AnthropicClient? client = (resource is null)
|
||||
? new AnthropicFoundryClient(new AnthropicFoundryApiKeyCredentials(apiKey, resource)) // If an apiKey is provided, use Foundry with ApiKey authentication
|
||||
: new AnthropicFoundryClient(new AnthropicAzureTokenCredential(new AzureCliCredential(), resource)); // Otherwise, use Foundry with Azure Client authentication
|
||||
|
||||
AIAgent agent = client.CreateAIAgent(model: deploymentName, instructions: JokerInstructions, name: JokerName);
|
||||
AIAgent agent = client.AsAIAgent(model: deploymentName, instructions: JokerInstructions, name: JokerName);
|
||||
|
||||
// Invoke the agent and output the text result.
|
||||
Console.WriteLine(await agent.RunAsync("Tell me a joke about a pirate."));
|
||||
|
||||
@@ -27,7 +27,7 @@ var createdAgentVersion = aiProjectClient.Agents.CreateAgentVersion(agentName: J
|
||||
// agentVersion.Name = <agentName>
|
||||
|
||||
// You can retrieve an AIAgent for an already created server side agent version.
|
||||
AIAgent existingJokerAgent = aiProjectClient.GetAIAgent(createdAgentVersion);
|
||||
AIAgent existingJokerAgent = aiProjectClient.AsAIAgent(createdAgentVersion);
|
||||
|
||||
// You can also create another AIAgent version by providing the same name with a different definition.
|
||||
AIAgent newJokerAgent = aiProjectClient.CreateAIAgent(name: JokerName, model: deploymentName, instructions: "You are extremely hilarious at telling jokes.");
|
||||
|
||||
+1
-1
@@ -25,7 +25,7 @@ OpenAIClient client = string.IsNullOrWhiteSpace(apiKey)
|
||||
|
||||
AIAgent agent = client
|
||||
.GetChatClient(model)
|
||||
.CreateAIAgent(instructions: "You are good at telling jokes.", name: "Joker");
|
||||
.AsAIAgent(instructions: "You are good at telling jokes.", name: "Joker");
|
||||
|
||||
// Invoke the agent and output the text result.
|
||||
Console.WriteLine(await agent.RunAsync("Tell me a joke about a pirate."));
|
||||
|
||||
+1
-1
@@ -14,7 +14,7 @@ AIAgent agent = new AzureOpenAIClient(
|
||||
new Uri(endpoint),
|
||||
new AzureCliCredential())
|
||||
.GetChatClient(deploymentName)
|
||||
.CreateAIAgent(instructions: "You are good at telling jokes.", name: "Joker");
|
||||
.AsAIAgent(instructions: "You are good at telling jokes.", name: "Joker");
|
||||
|
||||
// Invoke the agent and output the text result.
|
||||
Console.WriteLine(await agent.RunAsync("Tell me a joke about a pirate."));
|
||||
|
||||
+1
-1
@@ -14,7 +14,7 @@ AIAgent agent = new AzureOpenAIClient(
|
||||
new Uri(endpoint),
|
||||
new AzureCliCredential())
|
||||
.GetResponsesClient(deploymentName)
|
||||
.CreateAIAgent(instructions: "You are good at telling jokes.", name: "Joker");
|
||||
.AsAIAgent(instructions: "You are good at telling jokes.", name: "Joker");
|
||||
|
||||
// Invoke the agent and output the text result.
|
||||
Console.WriteLine(await agent.RunAsync("Tell me a joke about a pirate."));
|
||||
|
||||
-558
@@ -1,558 +0,0 @@
|
||||
// Copyright (c) Microsoft. All rights reserved.
|
||||
|
||||
using System.Runtime.CompilerServices;
|
||||
using Google.Apis.Util;
|
||||
using Google.GenAI;
|
||||
using Google.GenAI.Types;
|
||||
|
||||
namespace Microsoft.Extensions.AI;
|
||||
|
||||
/// <summary>Provides an <see cref="IChatClient"/> implementation based on <see cref="Client"/>.</summary>
|
||||
internal sealed class GoogleGenAIChatClient : IChatClient
|
||||
{
|
||||
/// <summary>The wrapped <see cref="Client"/> instance (optional).</summary>
|
||||
private readonly Client? _client;
|
||||
|
||||
/// <summary>The wrapped <see cref="Models"/> instance.</summary>
|
||||
private readonly Models _models;
|
||||
|
||||
/// <summary>The default model that should be used when no override is specified.</summary>
|
||||
private readonly string? _defaultModelId;
|
||||
|
||||
/// <summary>Lazily-initialized metadata describing the implementation.</summary>
|
||||
private ChatClientMetadata? _metadata;
|
||||
|
||||
/// <summary>Initializes a new <see cref="GoogleGenAIChatClient"/> instance.</summary>
|
||||
public GoogleGenAIChatClient(Client client, string? defaultModelId)
|
||||
{
|
||||
this._client = client;
|
||||
this._models = client.Models;
|
||||
this._defaultModelId = defaultModelId;
|
||||
}
|
||||
|
||||
/// <summary>Initializes a new <see cref="GoogleGenAIChatClient"/> instance.</summary>
|
||||
public GoogleGenAIChatClient(Models client, string? defaultModelId)
|
||||
{
|
||||
this._models = client;
|
||||
this._defaultModelId = defaultModelId;
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public async Task<ChatResponse> GetResponseAsync(IEnumerable<ChatMessage> messages, ChatOptions? options = null, CancellationToken cancellationToken = default)
|
||||
{
|
||||
Utilities.ThrowIfNull(messages, nameof(messages));
|
||||
|
||||
// Create the request.
|
||||
(string? modelId, List<Content> contents, GenerateContentConfig config) = this.CreateRequest(messages, options);
|
||||
|
||||
// Send it.
|
||||
GenerateContentResponse generateResult = await this._models.GenerateContentAsync(modelId!, contents, config).ConfigureAwait(false);
|
||||
|
||||
// Create the response.
|
||||
ChatResponse chatResponse = new(new ChatMessage(ChatRole.Assistant, []))
|
||||
{
|
||||
CreatedAt = generateResult.CreateTime is { } dt ? new DateTimeOffset(dt) : null,
|
||||
ModelId = !string.IsNullOrWhiteSpace(generateResult.ModelVersion) ? generateResult.ModelVersion : modelId,
|
||||
RawRepresentation = generateResult,
|
||||
ResponseId = generateResult.ResponseId,
|
||||
};
|
||||
|
||||
// Populate the response messages.
|
||||
chatResponse.FinishReason = PopulateResponseContents(generateResult, chatResponse.Messages[0].Contents);
|
||||
|
||||
// Populate usage information if there is any.
|
||||
if (generateResult.UsageMetadata is { } usageMetadata)
|
||||
{
|
||||
chatResponse.Usage = ExtractUsageDetails(usageMetadata);
|
||||
}
|
||||
|
||||
// Return the response.
|
||||
return chatResponse;
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public async IAsyncEnumerable<ChatResponseUpdate> GetStreamingResponseAsync(IEnumerable<ChatMessage> messages, ChatOptions? options = null, [EnumeratorCancellation] CancellationToken cancellationToken = default)
|
||||
{
|
||||
Utilities.ThrowIfNull(messages, nameof(messages));
|
||||
|
||||
// Create the request.
|
||||
(string? modelId, List<Content> contents, GenerateContentConfig config) = this.CreateRequest(messages, options);
|
||||
|
||||
// Send it, and process the results.
|
||||
await foreach (GenerateContentResponse generateResult in this._models.GenerateContentStreamAsync(modelId!, contents, config).WithCancellation(cancellationToken).ConfigureAwait(false))
|
||||
{
|
||||
// Create a response update for each result in the stream.
|
||||
ChatResponseUpdate responseUpdate = new(ChatRole.Assistant, [])
|
||||
{
|
||||
CreatedAt = generateResult.CreateTime is { } dt ? new DateTimeOffset(dt) : null,
|
||||
ModelId = !string.IsNullOrWhiteSpace(generateResult.ModelVersion) ? generateResult.ModelVersion : modelId,
|
||||
RawRepresentation = generateResult,
|
||||
ResponseId = generateResult.ResponseId,
|
||||
};
|
||||
|
||||
// Populate the response update contents.
|
||||
responseUpdate.FinishReason = PopulateResponseContents(generateResult, responseUpdate.Contents);
|
||||
|
||||
// Populate usage information if there is any.
|
||||
if (generateResult.UsageMetadata is { } usageMetadata)
|
||||
{
|
||||
responseUpdate.Contents.Add(new UsageContent(ExtractUsageDetails(usageMetadata)));
|
||||
}
|
||||
|
||||
// Yield the update.
|
||||
yield return responseUpdate;
|
||||
}
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public object? GetService(System.Type serviceType, object? serviceKey = null)
|
||||
{
|
||||
Utilities.ThrowIfNull(serviceType, nameof(serviceType));
|
||||
|
||||
if (serviceKey is null)
|
||||
{
|
||||
// If there's a request for metadata, lazily-initialize it and return it. We don't need to worry about race conditions,
|
||||
// as there's no requirement that the same instance be returned each time, and creation is idempotent.
|
||||
if (serviceType == typeof(ChatClientMetadata))
|
||||
{
|
||||
return this._metadata ??= new("gcp.gen_ai", new("https://generativelanguage.googleapis.com/"), defaultModelId: this._defaultModelId);
|
||||
}
|
||||
|
||||
// Allow a consumer to "break glass" and access the underlying client if they need it.
|
||||
if (serviceType.IsInstanceOfType(this._models))
|
||||
{
|
||||
return this._models;
|
||||
}
|
||||
|
||||
if (this._client is not null && serviceType.IsInstanceOfType(this._client))
|
||||
{
|
||||
return this._client;
|
||||
}
|
||||
|
||||
if (serviceType.IsInstanceOfType(this))
|
||||
{
|
||||
return this;
|
||||
}
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
void IDisposable.Dispose() { /* nop */ }
|
||||
|
||||
/// <summary>Creates the message parameters for <see cref="Models.GenerateContentAsync(string, List{Content}, GenerateContentConfig?)"/> from <paramref name="messages"/> and <paramref name="options"/>.</summary>
|
||||
private (string? ModelId, List<Content> Contents, GenerateContentConfig Config) CreateRequest(IEnumerable<ChatMessage> messages, ChatOptions? options)
|
||||
{
|
||||
// Create the GenerateContentConfig object. If the options contains a RawRepresentationFactory, try to use it to
|
||||
// create the request instance, allowing the caller to populate it with GenAI-specific options. Otherwise, create
|
||||
// a new instance directly.
|
||||
string? model = this._defaultModelId;
|
||||
List<Content> contents = [];
|
||||
GenerateContentConfig config = options?.RawRepresentationFactory?.Invoke(this) as GenerateContentConfig ?? new();
|
||||
|
||||
if (options is not null)
|
||||
{
|
||||
if (options.FrequencyPenalty is { } frequencyPenalty)
|
||||
{
|
||||
config.FrequencyPenalty ??= frequencyPenalty;
|
||||
}
|
||||
|
||||
if (options.Instructions is { } instructions)
|
||||
{
|
||||
((config.SystemInstruction ??= new()).Parts ??= []).Add(new() { Text = instructions });
|
||||
}
|
||||
|
||||
if (options.MaxOutputTokens is { } maxOutputTokens)
|
||||
{
|
||||
config.MaxOutputTokens ??= maxOutputTokens;
|
||||
}
|
||||
|
||||
if (!string.IsNullOrWhiteSpace(options.ModelId))
|
||||
{
|
||||
model = options.ModelId;
|
||||
}
|
||||
|
||||
if (options.PresencePenalty is { } presencePenalty)
|
||||
{
|
||||
config.PresencePenalty ??= presencePenalty;
|
||||
}
|
||||
|
||||
if (options.Seed is { } seed)
|
||||
{
|
||||
config.Seed ??= (int)seed;
|
||||
}
|
||||
|
||||
if (options.StopSequences is { } stopSequences)
|
||||
{
|
||||
(config.StopSequences ??= []).AddRange(stopSequences);
|
||||
}
|
||||
|
||||
if (options.Temperature is { } temperature)
|
||||
{
|
||||
config.Temperature ??= temperature;
|
||||
}
|
||||
|
||||
if (options.TopP is { } topP)
|
||||
{
|
||||
config.TopP ??= topP;
|
||||
}
|
||||
|
||||
if (options.TopK is { } topK)
|
||||
{
|
||||
config.TopK ??= topK;
|
||||
}
|
||||
|
||||
// Populate tools. Each kind of tool is added on its own, except for function declarations,
|
||||
// which are grouped into a single FunctionDeclaration.
|
||||
List<FunctionDeclaration>? functionDeclarations = null;
|
||||
if (options.Tools is { } tools)
|
||||
{
|
||||
foreach (var tool in tools)
|
||||
{
|
||||
switch (tool)
|
||||
{
|
||||
case AIFunctionDeclaration af:
|
||||
functionDeclarations ??= [];
|
||||
functionDeclarations.Add(new()
|
||||
{
|
||||
Name = af.Name,
|
||||
Description = af.Description ?? "",
|
||||
ParametersJsonSchema = af.JsonSchema,
|
||||
});
|
||||
break;
|
||||
|
||||
case HostedCodeInterpreterTool:
|
||||
(config.Tools ??= []).Add(new() { CodeExecution = new() });
|
||||
break;
|
||||
|
||||
case HostedFileSearchTool:
|
||||
(config.Tools ??= []).Add(new() { Retrieval = new() });
|
||||
break;
|
||||
|
||||
case HostedWebSearchTool:
|
||||
(config.Tools ??= []).Add(new() { GoogleSearch = new() });
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (functionDeclarations is { Count: > 0 })
|
||||
{
|
||||
Tool functionTools = new();
|
||||
(functionTools.FunctionDeclarations ??= []).AddRange(functionDeclarations);
|
||||
(config.Tools ??= []).Add(functionTools);
|
||||
}
|
||||
|
||||
// Transfer over the tool mode if there are any tools.
|
||||
if (options.ToolMode is { } toolMode && config.Tools?.Count > 0)
|
||||
{
|
||||
switch (toolMode)
|
||||
{
|
||||
case NoneChatToolMode:
|
||||
config.ToolConfig = new() { FunctionCallingConfig = new() { Mode = FunctionCallingConfigMode.NONE } };
|
||||
break;
|
||||
|
||||
case AutoChatToolMode:
|
||||
config.ToolConfig = new() { FunctionCallingConfig = new() { Mode = FunctionCallingConfigMode.AUTO } };
|
||||
break;
|
||||
|
||||
case RequiredChatToolMode required:
|
||||
config.ToolConfig = new() { FunctionCallingConfig = new() { Mode = FunctionCallingConfigMode.ANY } };
|
||||
if (required.RequiredFunctionName is not null)
|
||||
{
|
||||
((config.ToolConfig.FunctionCallingConfig ??= new()).AllowedFunctionNames ??= []).Add(required.RequiredFunctionName);
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// Set the response format if specified.
|
||||
if (options.ResponseFormat is ChatResponseFormatJson responseFormat)
|
||||
{
|
||||
config.ResponseMimeType = "application/json";
|
||||
if (responseFormat.Schema is { } schema)
|
||||
{
|
||||
config.ResponseJsonSchema = schema;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Transfer messages to request, handling system messages specially
|
||||
Dictionary<string, string>? callIdToFunctionNames = null;
|
||||
foreach (var message in messages)
|
||||
{
|
||||
if (message.Role == ChatRole.System)
|
||||
{
|
||||
string instruction = message.Text;
|
||||
if (!string.IsNullOrWhiteSpace(instruction))
|
||||
{
|
||||
((config.SystemInstruction ??= new()).Parts ??= []).Add(new() { Text = instruction });
|
||||
}
|
||||
|
||||
continue;
|
||||
}
|
||||
|
||||
Content content = new() { Role = message.Role == ChatRole.Assistant ? "model" : "user" };
|
||||
content.Parts ??= [];
|
||||
AddPartsForAIContents(ref callIdToFunctionNames, message.Contents, content.Parts);
|
||||
|
||||
contents.Add(content);
|
||||
}
|
||||
|
||||
// Make sure the request contains at least one content part (the request would always fail if empty).
|
||||
if (!contents.SelectMany(c => c.Parts ?? Enumerable.Empty<Part>()).Any())
|
||||
{
|
||||
contents.Add(new() { Role = "user", Parts = new() { { new() { Text = "" } } } });
|
||||
}
|
||||
|
||||
return (model, contents, config);
|
||||
}
|
||||
|
||||
/// <summary>Creates <see cref="Part"/>s for <paramref name="contents"/> and adds them to <paramref name="parts"/>.</summary>
|
||||
private static void AddPartsForAIContents(ref Dictionary<string, string>? callIdToFunctionNames, IList<AIContent> contents, List<Part> parts)
|
||||
{
|
||||
for (int i = 0; i < contents.Count; i++)
|
||||
{
|
||||
var content = contents[i];
|
||||
|
||||
byte[]? thoughtSignature = null;
|
||||
if (content is not TextReasoningContent { ProtectedData: not null } &&
|
||||
i + 1 < contents.Count &&
|
||||
contents[i + 1] is TextReasoningContent nextReasoning &&
|
||||
string.IsNullOrWhiteSpace(nextReasoning.Text) &&
|
||||
nextReasoning.ProtectedData is { } protectedData)
|
||||
{
|
||||
i++;
|
||||
thoughtSignature = Convert.FromBase64String(protectedData);
|
||||
}
|
||||
|
||||
Part? part = null;
|
||||
switch (content)
|
||||
{
|
||||
case TextContent textContent:
|
||||
part = new() { Text = textContent.Text };
|
||||
break;
|
||||
|
||||
case TextReasoningContent reasoningContent:
|
||||
part = new()
|
||||
{
|
||||
Thought = true,
|
||||
Text = !string.IsNullOrWhiteSpace(reasoningContent.Text) ? reasoningContent.Text : null,
|
||||
ThoughtSignature = reasoningContent.ProtectedData is not null ? Convert.FromBase64String(reasoningContent.ProtectedData) : null,
|
||||
};
|
||||
break;
|
||||
|
||||
case DataContent dataContent:
|
||||
part = new()
|
||||
{
|
||||
InlineData = new()
|
||||
{
|
||||
MimeType = dataContent.MediaType,
|
||||
Data = dataContent.Data.ToArray(),
|
||||
DisplayName = dataContent.Name,
|
||||
}
|
||||
};
|
||||
break;
|
||||
|
||||
case UriContent uriContent:
|
||||
part = new()
|
||||
{
|
||||
FileData = new()
|
||||
{
|
||||
FileUri = uriContent.Uri.AbsoluteUri,
|
||||
MimeType = uriContent.MediaType,
|
||||
}
|
||||
};
|
||||
break;
|
||||
|
||||
case FunctionCallContent functionCallContent:
|
||||
(callIdToFunctionNames ??= [])[functionCallContent.CallId] = functionCallContent.Name;
|
||||
callIdToFunctionNames[""] = functionCallContent.Name; // track last function name in case calls don't have IDs
|
||||
|
||||
part = new()
|
||||
{
|
||||
FunctionCall = new()
|
||||
{
|
||||
Id = functionCallContent.CallId,
|
||||
Name = functionCallContent.Name,
|
||||
Args = functionCallContent.Arguments is null ? null : functionCallContent.Arguments as Dictionary<string, object> ?? new(functionCallContent.Arguments!),
|
||||
}
|
||||
};
|
||||
break;
|
||||
|
||||
case FunctionResultContent functionResultContent:
|
||||
part = new()
|
||||
{
|
||||
FunctionResponse = new()
|
||||
{
|
||||
Id = functionResultContent.CallId,
|
||||
Name = callIdToFunctionNames?.TryGetValue(functionResultContent.CallId, out string? functionName) is true || callIdToFunctionNames?.TryGetValue("", out functionName) is true ?
|
||||
functionName :
|
||||
null,
|
||||
Response = functionResultContent.Result is null ? null : new() { ["result"] = functionResultContent.Result },
|
||||
}
|
||||
};
|
||||
break;
|
||||
}
|
||||
|
||||
if (part is not null)
|
||||
{
|
||||
part.ThoughtSignature ??= thoughtSignature;
|
||||
parts.Add(part);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>Creates <see cref="AIContent"/>s for <paramref name="parts"/> and adds them to <paramref name="contents"/>.</summary>
|
||||
private static void AddAIContentsForParts(List<Part> parts, IList<AIContent> contents)
|
||||
{
|
||||
foreach (var part in parts)
|
||||
{
|
||||
AIContent? content = null;
|
||||
|
||||
if (!string.IsNullOrEmpty(part.Text))
|
||||
{
|
||||
content = part.Thought is true ?
|
||||
new TextReasoningContent(part.Text) :
|
||||
new TextContent(part.Text);
|
||||
}
|
||||
else if (part.InlineData is { } inlineData)
|
||||
{
|
||||
content = new DataContent(inlineData.Data, inlineData.MimeType ?? "application/octet-stream")
|
||||
{
|
||||
Name = inlineData.DisplayName,
|
||||
};
|
||||
}
|
||||
else if (part.FileData is { FileUri: not null } fileData)
|
||||
{
|
||||
content = new UriContent(new Uri(fileData.FileUri), fileData.MimeType ?? "application/octet-stream");
|
||||
}
|
||||
else if (part.FunctionCall is { Name: not null } functionCall)
|
||||
{
|
||||
content = new FunctionCallContent(functionCall.Id ?? "", functionCall.Name, functionCall.Args!);
|
||||
}
|
||||
else if (part.FunctionResponse is { } functionResponse)
|
||||
{
|
||||
content = new FunctionResultContent(
|
||||
functionResponse.Id ?? "",
|
||||
functionResponse.Response?.TryGetValue("output", out var output) is true ? output :
|
||||
functionResponse.Response?.TryGetValue("error", out var error) is true ? error :
|
||||
null);
|
||||
}
|
||||
|
||||
if (content is not null)
|
||||
{
|
||||
content.RawRepresentation = part;
|
||||
contents.Add(content);
|
||||
|
||||
if (part.ThoughtSignature is { } thoughtSignature)
|
||||
{
|
||||
contents.Add(new TextReasoningContent(null)
|
||||
{
|
||||
ProtectedData = Convert.ToBase64String(thoughtSignature),
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private static ChatFinishReason? PopulateResponseContents(GenerateContentResponse generateResult, IList<AIContent> responseContents)
|
||||
{
|
||||
ChatFinishReason? finishReason = null;
|
||||
|
||||
// Populate the response messages. There should only be at most one candidate, but if there are more, ignore all but the first.
|
||||
if (generateResult.Candidates is { Count: > 0 } &&
|
||||
generateResult.Candidates[0] is { Content: { } candidateContent } candidate)
|
||||
{
|
||||
// Grab the finish reason if one exists.
|
||||
finishReason = ConvertFinishReason(candidate.FinishReason);
|
||||
|
||||
// Add all of the response content parts as AIContents.
|
||||
if (candidateContent.Parts is { } parts)
|
||||
{
|
||||
AddAIContentsForParts(parts, responseContents);
|
||||
}
|
||||
|
||||
// Add any citation metadata.
|
||||
if (candidate.CitationMetadata is { Citations: { Count: > 0 } citations } &&
|
||||
responseContents.OfType<TextContent>().FirstOrDefault() is TextContent textContent)
|
||||
{
|
||||
foreach (var citation in citations)
|
||||
{
|
||||
textContent.Annotations =
|
||||
[
|
||||
new CitationAnnotation()
|
||||
{
|
||||
Title = citation.Title,
|
||||
Url = Uri.TryCreate(citation.Uri, UriKind.Absolute, out Uri? uri) ? uri : null,
|
||||
AnnotatedRegions =
|
||||
[
|
||||
new TextSpanAnnotatedRegion()
|
||||
{
|
||||
StartIndex = citation.StartIndex,
|
||||
EndIndex = citation.EndIndex,
|
||||
}
|
||||
],
|
||||
}
|
||||
];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Populate error information if there is any.
|
||||
if (generateResult.PromptFeedback is { } promptFeedback)
|
||||
{
|
||||
responseContents.Add(new ErrorContent(promptFeedback.BlockReasonMessage));
|
||||
}
|
||||
|
||||
return finishReason;
|
||||
}
|
||||
|
||||
/// <summary>Creates an M.E.AI <see cref="ChatFinishReason"/> from a Google <see cref="FinishReason"/>.</summary>
|
||||
private static ChatFinishReason? ConvertFinishReason(FinishReason? finishReason)
|
||||
{
|
||||
return finishReason switch
|
||||
{
|
||||
null => null,
|
||||
|
||||
FinishReason.MAX_TOKENS =>
|
||||
ChatFinishReason.Length,
|
||||
|
||||
FinishReason.MALFORMED_FUNCTION_CALL or
|
||||
FinishReason.UNEXPECTED_TOOL_CALL =>
|
||||
ChatFinishReason.ToolCalls,
|
||||
|
||||
FinishReason.FINISH_REASON_UNSPECIFIED or
|
||||
FinishReason.STOP =>
|
||||
ChatFinishReason.Stop,
|
||||
|
||||
_ => ChatFinishReason.ContentFilter,
|
||||
};
|
||||
}
|
||||
|
||||
/// <summary>Creates a <see cref="UsageDetails"/> populated from the supplied <paramref name="usageMetadata"/>.</summary>
|
||||
private static UsageDetails ExtractUsageDetails(GenerateContentResponseUsageMetadata usageMetadata)
|
||||
{
|
||||
UsageDetails details = new()
|
||||
{
|
||||
InputTokenCount = usageMetadata.PromptTokenCount,
|
||||
OutputTokenCount = usageMetadata.CandidatesTokenCount,
|
||||
TotalTokenCount = usageMetadata.TotalTokenCount,
|
||||
};
|
||||
|
||||
AddIfPresent(nameof(usageMetadata.CachedContentTokenCount), usageMetadata.CachedContentTokenCount);
|
||||
AddIfPresent(nameof(usageMetadata.ThoughtsTokenCount), usageMetadata.ThoughtsTokenCount);
|
||||
AddIfPresent(nameof(usageMetadata.ToolUsePromptTokenCount), usageMetadata.ToolUsePromptTokenCount);
|
||||
|
||||
return details;
|
||||
|
||||
void AddIfPresent(string key, int? value)
|
||||
{
|
||||
if (value is int i)
|
||||
{
|
||||
(details.AdditionalCounts ??= [])[key] = i;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
-36
@@ -1,36 +0,0 @@
|
||||
// Copyright (c) Microsoft. All rights reserved.
|
||||
|
||||
using Google.Apis.Util;
|
||||
using Google.GenAI;
|
||||
|
||||
namespace Microsoft.Extensions.AI;
|
||||
|
||||
/// <summary>Provides implementations of Microsoft.Extensions.AI abstractions based on <see cref="Client"/>.</summary>
|
||||
public static class GoogleGenAIExtensions
|
||||
{
|
||||
/// <summary>
|
||||
/// Creates an <see cref="IChatClient"/> wrapper around the specified <see cref="Client"/>.
|
||||
/// </summary>
|
||||
/// <param name="client">The <see cref="Client"/> to wrap.</param>
|
||||
/// <param name="defaultModelId">The default model ID to use for chat requests if not specified in <see cref="ChatOptions.ModelId"/>.</param>
|
||||
/// <returns>An <see cref="IChatClient"/> that wraps the specified client.</returns>
|
||||
/// <exception cref="ArgumentNullException"><paramref name="client"/> is <see langword="null"/>.</exception>
|
||||
public static IChatClient AsIChatClient(this Client client, string? defaultModelId = null)
|
||||
{
|
||||
Utilities.ThrowIfNull(client, nameof(client));
|
||||
return new GoogleGenAIChatClient(client, defaultModelId);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Creates an <see cref="IChatClient"/> wrapper around the specified <see cref="Models"/>.
|
||||
/// </summary>
|
||||
/// <param name="models">The <see cref="Models"/> client to wrap.</param>
|
||||
/// <param name="defaultModelId">The default model ID to use for chat requests if not specified in <see cref="ChatOptions.ModelId"/>.</param>
|
||||
/// <returns>An <see cref="IChatClient"/> that wraps the specified <see cref="Models"/> client.</returns>
|
||||
/// <exception cref="ArgumentNullException"><paramref name="models"/> is <see langword="null"/>.</exception>
|
||||
public static IChatClient AsIChatClient(this Models models, string? defaultModelId = null)
|
||||
{
|
||||
Utilities.ThrowIfNull(models, nameof(models));
|
||||
return new GoogleGenAIChatClient(models, defaultModelId);
|
||||
}
|
||||
}
|
||||
@@ -14,8 +14,6 @@ string apiKey = Environment.GetEnvironmentVariable("GOOGLE_GENAI_API_KEY") ?? th
|
||||
string model = Environment.GetEnvironmentVariable("GOOGLE_GENAI_MODEL") ?? "gemini-2.5-flash";
|
||||
|
||||
// Using a Google GenAI IChatClient implementation
|
||||
// Until the PR https://github.com/googleapis/dotnet-genai/pull/81 is not merged this option
|
||||
// requires usage of also both GeminiChatClient.cs and GoogleGenAIExtensions.cs polyfills to work.
|
||||
|
||||
ChatClientAgent agentGenAI = new(
|
||||
new Client(vertexAI: false, apiKey: apiKey).AsIChatClient(model),
|
||||
|
||||
@@ -25,12 +25,7 @@ $env:GOOGLE_GENAI_MODEL="gemini-2.5-fast" # Optional, defaults to gemini-2.5-fa
|
||||
|
||||
### Google GenAI (Official)
|
||||
|
||||
The official Google GenAI package provides direct access to Google's Generative AI models. This sample uses an extension method to convert the Google client to an `IChatClient`.
|
||||
|
||||
> [!NOTE]
|
||||
> Until PR [googleapis/dotnet-genai#81](https://github.com/googleapis/dotnet-genai/pull/81) is merged, this option requires the additional `GeminiChatClient.cs` and `GoogleGenAIExtensions.cs` files included in this sample.
|
||||
>
|
||||
> We appreciate any community push by liking and commenting in the above PR to get it merged and release as part of official Google GenAI package.
|
||||
The official Google GenAI package provides direct access to Google's Generative AI models. This sample uses the `AsIChatClient()` extension method to convert the Google client to an `IChatClient`.
|
||||
|
||||
### Mscc.GenerativeAI.Microsoft (Community)
|
||||
|
||||
|
||||
@@ -12,7 +12,7 @@ var modelPath = Environment.GetEnvironmentVariable("ONNX_MODEL_PATH") ?? throw n
|
||||
|
||||
// Get a chat client for ONNX and use it to construct an AIAgent.
|
||||
using OnnxRuntimeGenAIChatClient chatClient = new(modelPath);
|
||||
AIAgent agent = chatClient.CreateAIAgent(instructions: "You are good at telling jokes.", name: "Joker");
|
||||
AIAgent agent = chatClient.AsAIAgent(instructions: "You are good at telling jokes.", name: "Joker");
|
||||
|
||||
// Invoke the agent and output the text result.
|
||||
Console.WriteLine(await agent.RunAsync("Tell me a joke about a pirate."));
|
||||
|
||||
@@ -11,7 +11,7 @@ var modelName = Environment.GetEnvironmentVariable("OLLAMA_MODEL_NAME") ?? throw
|
||||
|
||||
// Get a chat client for Ollama and use it to construct an AIAgent.
|
||||
AIAgent agent = new OllamaApiClient(new Uri(endpoint), modelName)
|
||||
.CreateAIAgent(instructions: "You are good at telling jokes.", name: "Joker");
|
||||
.AsAIAgent(instructions: "You are good at telling jokes.", name: "Joker");
|
||||
|
||||
// Invoke the agent and output the text result.
|
||||
Console.WriteLine(await agent.RunAsync("Tell me a joke about a pirate."));
|
||||
|
||||
+1
-1
@@ -13,7 +13,7 @@ var model = Environment.GetEnvironmentVariable("OPENAI_MODEL") ?? "gpt-4o-mini";
|
||||
AIAgent agent = new OpenAIClient(
|
||||
apiKey)
|
||||
.GetChatClient(model)
|
||||
.CreateAIAgent(instructions: "You are good at telling jokes.", name: "Joker");
|
||||
.AsAIAgent(instructions: "You are good at telling jokes.", name: "Joker");
|
||||
|
||||
// Invoke the agent and output the text result.
|
||||
Console.WriteLine(await agent.RunAsync("Tell me a joke about a pirate."));
|
||||
|
||||
@@ -12,7 +12,7 @@ var model = Environment.GetEnvironmentVariable("OPENAI_MODEL") ?? "gpt-4o-mini";
|
||||
AIAgent agent = new OpenAIClient(
|
||||
apiKey)
|
||||
.GetResponsesClient(model)
|
||||
.CreateAIAgent(instructions: "You are good at telling jokes.", name: "Joker");
|
||||
.AsAIAgent(instructions: "You are good at telling jokes.", name: "Joker");
|
||||
|
||||
// Invoke the agent and output the text result.
|
||||
Console.WriteLine(await agent.RunAsync("Tell me a joke about a pirate."));
|
||||
|
||||
+1
-1
@@ -11,7 +11,7 @@ var apiKey = Environment.GetEnvironmentVariable("ANTHROPIC_API_KEY") ?? throw ne
|
||||
var model = Environment.GetEnvironmentVariable("ANTHROPIC_MODEL") ?? "claude-haiku-4-5";
|
||||
|
||||
AIAgent agent = new AnthropicClient(new ClientOptions { APIKey = apiKey })
|
||||
.CreateAIAgent(model: model, instructions: "You are good at telling jokes.", name: "Joker");
|
||||
.AsAIAgent(model: model, instructions: "You are good at telling jokes.", name: "Joker");
|
||||
|
||||
// Invoke the agent and output the text result.
|
||||
var response = await agent.RunAsync("Tell me a joke about a pirate.");
|
||||
|
||||
+1
-1
@@ -14,7 +14,7 @@ var maxTokens = 4096;
|
||||
var thinkingTokens = 2048;
|
||||
|
||||
var agent = new AnthropicClient(new ClientOptions { APIKey = apiKey })
|
||||
.CreateAIAgent(
|
||||
.AsAIAgent(
|
||||
model: model,
|
||||
clientFactory: (chatClient) => chatClient
|
||||
.AsBuilder()
|
||||
|
||||
+1
-1
@@ -23,7 +23,7 @@ AITool tool = AIFunctionFactory.Create(GetWeather);
|
||||
|
||||
// Get anthropic client to create agents.
|
||||
AIAgent agent = new AnthropicClient { APIKey = apiKey }
|
||||
.CreateAIAgent(model: model, instructions: AssistantInstructions, name: AssistantName, tools: [tool]);
|
||||
.AsAIAgent(model: model, instructions: AssistantInstructions, name: AssistantName, tools: [tool]);
|
||||
|
||||
// Non-streaming agent interaction with function tools.
|
||||
AgentThread thread = await agent.GetNewThreadAsync();
|
||||
|
||||
+1
-1
@@ -30,7 +30,7 @@ AIAgent agent = new AzureOpenAIClient(
|
||||
new Uri(endpoint),
|
||||
new AzureCliCredential())
|
||||
.GetChatClient(deploymentName)
|
||||
.CreateAIAgent(new ChatClientAgentOptions
|
||||
.AsAIAgent(new ChatClientAgentOptions
|
||||
{
|
||||
ChatOptions = new() { Instructions = "You are good at telling jokes." },
|
||||
Name = "Joker",
|
||||
|
||||
+1
-1
@@ -28,7 +28,7 @@ AIAgent agent = new AzureOpenAIClient(
|
||||
new Uri(endpoint),
|
||||
new AzureCliCredential())
|
||||
.GetChatClient(deploymentName)
|
||||
.CreateAIAgent(new ChatClientAgentOptions()
|
||||
.AsAIAgent(new ChatClientAgentOptions()
|
||||
{
|
||||
ChatOptions = new() { Instructions = "You are a friendly travel assistant. Use known memories about the user when responding, and do not invent details." },
|
||||
AIContextProviderFactory = (ctx, ct) => new ValueTask<AIContextProvider>(ctx.SerializedState.ValueKind is not JsonValueKind.Null and not JsonValueKind.Undefined
|
||||
|
||||
+1
-1
@@ -30,7 +30,7 @@ ChatClient chatClient = new AzureOpenAIClient(
|
||||
// and preferably shared between multiple threads used by the same user, ensure that the
|
||||
// factory reads the user id from the current context and scopes the memory component
|
||||
// and its storage to that user id.
|
||||
AIAgent agent = chatClient.CreateAIAgent(new ChatClientAgentOptions()
|
||||
AIAgent agent = chatClient.AsAIAgent(new ChatClientAgentOptions()
|
||||
{
|
||||
ChatOptions = new() { Instructions = "You are a friendly assistant. Always address the user by their name." },
|
||||
AIContextProviderFactory = (ctx, ct) => new ValueTask<AIContextProvider>(new UserInfoMemory(chatClient.AsIChatClient(), ctx.SerializedState, ctx.JsonSerializerOptions))
|
||||
|
||||
+1
-1
@@ -12,7 +12,7 @@ var model = Environment.GetEnvironmentVariable("OPENAI_MODEL") ?? "gpt-4o-mini";
|
||||
|
||||
AIAgent agent = new OpenAIClient(apiKey)
|
||||
.GetChatClient(model)
|
||||
.CreateAIAgent(instructions: "You are good at telling jokes.", name: "Joker");
|
||||
.AsAIAgent(instructions: "You are good at telling jokes.", name: "Joker");
|
||||
|
||||
UserChatMessage chatMessage = new("Tell me a joke about a pirate.");
|
||||
|
||||
|
||||
+1
-1
@@ -59,7 +59,7 @@ TextSearchProviderOptions textSearchOptions = new()
|
||||
// Create the AI agent with the TextSearchProvider as the AI context provider.
|
||||
AIAgent agent = azureOpenAIClient
|
||||
.GetChatClient(deploymentName)
|
||||
.CreateAIAgent(new ChatClientAgentOptions
|
||||
.AsAIAgent(new ChatClientAgentOptions
|
||||
{
|
||||
ChatOptions = new() { Instructions = "You are a helpful support specialist for Contoso Outdoors. Answer questions using the provided context and cite the source document when available." },
|
||||
AIContextProviderFactory = (ctx, ct) => new ValueTask<AIContextProvider>(new TextSearchProvider(SearchAdapter, ctx.SerializedState, ctx.JsonSerializerOptions, textSearchOptions)),
|
||||
|
||||
+1
-1
@@ -68,7 +68,7 @@ TextSearchProviderOptions textSearchOptions = new()
|
||||
// Create the AI agent with the TextSearchProvider as the AI context provider.
|
||||
AIAgent agent = azureOpenAIClient
|
||||
.GetChatClient(deploymentName)
|
||||
.CreateAIAgent(new ChatClientAgentOptions
|
||||
.AsAIAgent(new ChatClientAgentOptions
|
||||
{
|
||||
ChatOptions = new() { Instructions = "You are a helpful support specialist for the Microsoft Agent Framework. Answer questions using the provided context and cite the source document when available. Keep responses brief." },
|
||||
AIContextProviderFactory = (ctx, ct) => new ValueTask<AIContextProvider>(new TextSearchProvider(SearchAdapter, ctx.SerializedState, ctx.JsonSerializerOptions, textSearchOptions))
|
||||
|
||||
+1
-1
@@ -26,7 +26,7 @@ AIAgent agent = new AzureOpenAIClient(
|
||||
new Uri(endpoint),
|
||||
new AzureCliCredential())
|
||||
.GetChatClient(deploymentName)
|
||||
.CreateAIAgent(new ChatClientAgentOptions
|
||||
.AsAIAgent(new ChatClientAgentOptions
|
||||
{
|
||||
ChatOptions = new() { Instructions = "You are a helpful support specialist for Contoso Outdoors. Answer questions using the provided context and cite the source document when available." },
|
||||
AIContextProviderFactory = (ctx, ct) => new ValueTask<AIContextProvider>(new TextSearchProvider(MockSearchAsync, ctx.SerializedState, ctx.JsonSerializerOptions, textSearchOptions))
|
||||
|
||||
@@ -14,7 +14,7 @@ AIAgent agent = new AzureOpenAIClient(
|
||||
new Uri(endpoint),
|
||||
new AzureCliCredential())
|
||||
.GetChatClient(deploymentName)
|
||||
.CreateAIAgent(instructions: "You are good at telling jokes.", name: "Joker");
|
||||
.AsAIAgent(instructions: "You are good at telling jokes.", name: "Joker");
|
||||
|
||||
// Invoke the agent and output the text result.
|
||||
Console.WriteLine(await agent.RunAsync("Tell me a joke about a pirate."));
|
||||
|
||||
@@ -14,7 +14,7 @@ AIAgent agent = new AzureOpenAIClient(
|
||||
new Uri(endpoint),
|
||||
new AzureCliCredential())
|
||||
.GetChatClient(deploymentName)
|
||||
.CreateAIAgent(instructions: "You are good at telling jokes.", name: "Joker");
|
||||
.AsAIAgent(instructions: "You are good at telling jokes.", name: "Joker");
|
||||
|
||||
// Invoke the agent with a multi-turn conversation, where the context is preserved in the thread object.
|
||||
AgentThread thread = await agent.GetNewThreadAsync();
|
||||
|
||||
@@ -22,7 +22,7 @@ AIAgent agent = new AzureOpenAIClient(
|
||||
new Uri(endpoint),
|
||||
new AzureCliCredential())
|
||||
.GetChatClient(deploymentName)
|
||||
.CreateAIAgent(instructions: "You are a helpful assistant", tools: [AIFunctionFactory.Create(GetWeather)]);
|
||||
.AsAIAgent(instructions: "You are a helpful assistant", tools: [AIFunctionFactory.Create(GetWeather)]);
|
||||
|
||||
// Non-streaming agent interaction with function tools.
|
||||
Console.WriteLine(await agent.RunAsync("What is the weather like in Amsterdam?"));
|
||||
|
||||
+1
-1
@@ -27,7 +27,7 @@ AIAgent agent = new AzureOpenAIClient(
|
||||
new Uri(endpoint),
|
||||
new AzureCliCredential())
|
||||
.GetChatClient(deploymentName)
|
||||
.CreateAIAgent(instructions: "You are a helpful assistant", tools: [new ApprovalRequiredAIFunction(AIFunctionFactory.Create(GetWeather))]);
|
||||
.AsAIAgent(instructions: "You are a helpful assistant", tools: [new ApprovalRequiredAIFunction(AIFunctionFactory.Create(GetWeather))]);
|
||||
|
||||
// Call the agent and check if there are any user input requests to handle.
|
||||
AgentThread thread = await agent.GetNewThreadAsync();
|
||||
|
||||
@@ -21,7 +21,7 @@ ChatClient chatClient = new AzureOpenAIClient(
|
||||
.GetChatClient(deploymentName);
|
||||
|
||||
// Create the ChatClientAgent with the specified name and instructions.
|
||||
ChatClientAgent agent = chatClient.CreateAIAgent(name: "HelpfulAssistant", instructions: "You are a helpful assistant.");
|
||||
ChatClientAgent agent = chatClient.AsAIAgent(name: "HelpfulAssistant", instructions: "You are a helpful assistant.");
|
||||
|
||||
// Set PersonInfo as the type parameter of RunAsync method to specify the expected structured output from the agent and invoke the agent with some unstructured input.
|
||||
AgentResponse<PersonInfo> response = await agent.RunAsync<PersonInfo>("Please provide information about John Smith, who is a 35-year-old software engineer.");
|
||||
@@ -33,7 +33,7 @@ Console.WriteLine($"Age: {response.Result.Age}");
|
||||
Console.WriteLine($"Occupation: {response.Result.Occupation}");
|
||||
|
||||
// Create the ChatClientAgent with the specified name, instructions, and expected structured output the agent should produce.
|
||||
ChatClientAgent agentWithPersonInfo = chatClient.CreateAIAgent(new ChatClientAgentOptions()
|
||||
ChatClientAgent agentWithPersonInfo = chatClient.AsAIAgent(new ChatClientAgentOptions()
|
||||
{
|
||||
Name = "HelpfulAssistant",
|
||||
ChatOptions = new() { Instructions = "You are a helpful assistant.", ResponseFormat = Microsoft.Extensions.AI.ChatResponseFormat.ForJsonSchema<PersonInfo>() }
|
||||
|
||||
@@ -16,7 +16,7 @@ AIAgent agent = new AzureOpenAIClient(
|
||||
new Uri(endpoint),
|
||||
new AzureCliCredential())
|
||||
.GetChatClient(deploymentName)
|
||||
.CreateAIAgent(instructions: "You are good at telling jokes.", name: "Joker");
|
||||
.AsAIAgent(instructions: "You are good at telling jokes.", name: "Joker");
|
||||
|
||||
// Start a new thread for the agent conversation.
|
||||
AgentThread thread = await agent.GetNewThreadAsync();
|
||||
|
||||
@@ -27,7 +27,7 @@ AIAgent agent = new AzureOpenAIClient(
|
||||
new Uri(endpoint),
|
||||
new AzureCliCredential())
|
||||
.GetChatClient(deploymentName)
|
||||
.CreateAIAgent(new ChatClientAgentOptions
|
||||
.AsAIAgent(new ChatClientAgentOptions
|
||||
{
|
||||
ChatOptions = new() { Instructions = "You are good at telling jokes." },
|
||||
Name = "Joker",
|
||||
|
||||
@@ -29,7 +29,7 @@ using var tracerProvider = tracerProviderBuilder.Build();
|
||||
// Create the agent, and enable OpenTelemetry instrumentation.
|
||||
AIAgent agent = new AzureOpenAIClient(new Uri(endpoint), new AzureCliCredential())
|
||||
.GetChatClient(deploymentName)
|
||||
.CreateAIAgent(instructions: "You are good at telling jokes.", name: "Joker")
|
||||
.AsAIAgent(instructions: "You are good at telling jokes.", name: "Joker")
|
||||
.AsBuilder()
|
||||
.UseOpenTelemetry(sourceName: sourceName)
|
||||
.Build();
|
||||
|
||||
@@ -13,7 +13,7 @@ var deploymentName = System.Environment.GetEnvironmentVariable("AZURE_OPENAI_DEP
|
||||
|
||||
var agent = new AzureOpenAIClient(new Uri(endpoint), new AzureCliCredential())
|
||||
.GetChatClient(deploymentName)
|
||||
.CreateAIAgent(
|
||||
.AsAIAgent(
|
||||
name: "VisionAgent",
|
||||
instructions: "You are a helpful agent that can analyze images");
|
||||
|
||||
|
||||
@@ -21,7 +21,7 @@ AIAgent weatherAgent = new AzureOpenAIClient(
|
||||
new Uri(endpoint),
|
||||
new AzureCliCredential())
|
||||
.GetChatClient(deploymentName)
|
||||
.CreateAIAgent(
|
||||
.AsAIAgent(
|
||||
instructions: "You answer questions about the weather.",
|
||||
name: "WeatherAgent",
|
||||
description: "An agent that answers questions about the weather.",
|
||||
@@ -32,7 +32,7 @@ AIAgent agent = new AzureOpenAIClient(
|
||||
new Uri(endpoint),
|
||||
new AzureCliCredential())
|
||||
.GetChatClient(deploymentName)
|
||||
.CreateAIAgent(instructions: "You are a helpful assistant who responds in French.", tools: [weatherAgent.AsAIFunction()]);
|
||||
.AsAIAgent(instructions: "You are a helpful assistant who responds in French.", tools: [weatherAgent.AsAIFunction()]);
|
||||
|
||||
// Invoke the agent and output the text result.
|
||||
Console.WriteLine(await agent.RunAsync("What is the weather like in Amsterdam?"));
|
||||
|
||||
+1
-1
@@ -23,7 +23,7 @@ AIAgent agent = new AzureOpenAIClient(
|
||||
new Uri(endpoint),
|
||||
new AzureCliCredential())
|
||||
.GetResponsesClient(deploymentName)
|
||||
.CreateAIAgent(
|
||||
.AsAIAgent(
|
||||
name: "SpaceNovelWriter",
|
||||
instructions: "You are a space novel writer. Always research relevant facts and generate character profiles for the main characters before writing novels." +
|
||||
"Write complete chapters without asking for approval or feedback. Do not ask the user about tone, style, pace, or format preferences - just write the novel based on the request.",
|
||||
|
||||
@@ -31,7 +31,7 @@ AIAgent agent = new AzureOpenAIClient(
|
||||
new Uri(endpoint),
|
||||
new AzureCliCredential())
|
||||
.GetChatClient(deploymentName)
|
||||
.CreateAIAgent(
|
||||
.AsAIAgent(
|
||||
instructions: "You are a helpful assistant that helps people find information.",
|
||||
name: "Assistant",
|
||||
tools: [.. serviceProvider.GetRequiredService<AgentPlugin>().AsAITools()],
|
||||
|
||||
@@ -20,7 +20,7 @@ AIAgent agent = new AzureOpenAIClient(
|
||||
new Uri(endpoint),
|
||||
new AzureCliCredential())
|
||||
.GetChatClient(deploymentName)
|
||||
.CreateAIAgent(new ChatClientAgentOptions
|
||||
.AsAIAgent(new ChatClientAgentOptions
|
||||
{
|
||||
ChatOptions = new() { Instructions = "You are good at telling jokes." },
|
||||
Name = "Joker",
|
||||
|
||||
@@ -14,7 +14,7 @@ AIAgent agent = new AzureOpenAIClient(
|
||||
new Uri(endpoint),
|
||||
new AzureCliCredential())
|
||||
.GetResponsesClient(deploymentName)
|
||||
.CreateAIAgent();
|
||||
.AsAIAgent();
|
||||
|
||||
// Enable background responses (only supported by OpenAI Responses at this time).
|
||||
AgentRunOptions options = new() { AllowBackgroundResponses = true };
|
||||
|
||||
@@ -27,7 +27,7 @@ AIAgent agent = new AzureOpenAIClient(
|
||||
new Uri(endpoint),
|
||||
new AzureCliCredential())
|
||||
.GetChatClient(deploymentName)
|
||||
.CreateAIAgent(instructions: "You answer questions related to GitHub repositories only.", tools: [.. mcpTools.Cast<AITool>()]);
|
||||
.AsAIAgent(instructions: "You answer questions related to GitHub repositories only.", tools: [.. mcpTools.Cast<AITool>()]);
|
||||
|
||||
// Invoke the agent and output the text result.
|
||||
Console.WriteLine(await agent.RunAsync("Summarize the last four commits to the microsoft/semantic-kernel repository?"));
|
||||
|
||||
@@ -50,7 +50,7 @@ AIAgent agent = new AzureOpenAIClient(
|
||||
new Uri(endpoint),
|
||||
new AzureCliCredential())
|
||||
.GetChatClient(deploymentName)
|
||||
.CreateAIAgent(instructions: "You answer questions related to the weather.", tools: [.. mcpTools]);
|
||||
.AsAIAgent(instructions: "You answer questions related to the weather.", tools: [.. mcpTools]);
|
||||
|
||||
// Invoke the agent and output the text result.
|
||||
Console.WriteLine(await agent.RunAsync("Get current weather alerts for New York?"));
|
||||
|
||||
+2
-2
@@ -31,7 +31,7 @@ AIAgent agent = new AzureOpenAIClient(
|
||||
new Uri(endpoint),
|
||||
new AzureCliCredential())
|
||||
.GetResponsesClient(deploymentName)
|
||||
.CreateAIAgent(
|
||||
.AsAIAgent(
|
||||
instructions: "You answer questions by searching the Microsoft Learn content only.",
|
||||
name: "MicrosoftLearnAgent",
|
||||
tools: [mcpTool]);
|
||||
@@ -58,7 +58,7 @@ AIAgent agentWithRequiredApproval = new AzureOpenAIClient(
|
||||
new Uri(endpoint),
|
||||
new AzureCliCredential())
|
||||
.GetResponsesClient(deploymentName)
|
||||
.CreateAIAgent(
|
||||
.AsAIAgent(
|
||||
instructions: "You answer questions by searching the Microsoft Learn content only.",
|
||||
name: "MicrosoftLearnAgentWithApproval",
|
||||
tools: [mcpToolWithApproval]);
|
||||
|
||||
@@ -27,11 +27,11 @@ public static class A2AAgentCardExtensions
|
||||
/// <param name="httpClient">The <see cref="HttpClient"/> to use for HTTP requests.</param>
|
||||
/// <param name="loggerFactory">The logger factory for enabling logging within the agent.</param>
|
||||
/// <returns>An <see cref="AIAgent"/> instance backed by the A2A agent.</returns>
|
||||
public static AIAgent GetAIAgent(this AgentCard card, HttpClient? httpClient = null, ILoggerFactory? loggerFactory = null)
|
||||
public static AIAgent AsAIAgent(this AgentCard card, HttpClient? httpClient = null, ILoggerFactory? loggerFactory = null)
|
||||
{
|
||||
// Create the A2A client using the agent URL from the card.
|
||||
var a2aClient = new A2AClient(new Uri(card.Url), httpClient);
|
||||
|
||||
return a2aClient.GetAIAgent(name: card.Name, description: card.Description, loggerFactory: loggerFactory);
|
||||
return a2aClient.AsAIAgent(name: card.Name, description: card.Description, loggerFactory: loggerFactory);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -42,6 +42,6 @@ public static class A2ACardResolverExtensions
|
||||
// Obtain the agent card from the resolver.
|
||||
var agentCard = await resolver.GetAgentCardAsync(cancellationToken).ConfigureAwait(false);
|
||||
|
||||
return agentCard.GetAIAgent(httpClient, loggerFactory);
|
||||
return agentCard.AsAIAgent(httpClient, loggerFactory);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -35,6 +35,6 @@ public static class A2AClientExtensions
|
||||
/// <param name="description">The description of the agent.</param>
|
||||
/// <param name="loggerFactory">Optional logger factory for enabling logging within the agent.</param>
|
||||
/// <returns>An <see cref="AIAgent"/> instance backed by the A2A agent.</returns>
|
||||
public static AIAgent GetAIAgent(this A2AClient client, string? id = null, string? name = null, string? description = null, ILoggerFactory? loggerFactory = null) =>
|
||||
public static AIAgent AsAIAgent(this A2AClient client, string? id = null, string? name = null, string? description = null, ILoggerFactory? loggerFactory = null) =>
|
||||
new A2AAgent(client, id, name, description, loggerFactory);
|
||||
}
|
||||
|
||||
@@ -31,7 +31,7 @@ public static class AnthropicBetaServiceExtensions
|
||||
/// <param name="loggerFactory">Optional logger factory for enabling logging within the agent.</param>
|
||||
/// <param name="services">An optional <see cref="IServiceProvider"/> to use for resolving services required by the <see cref="AIFunction"/> instances being invoked.</param>
|
||||
/// <returns>The created <see cref="ChatClientAgent"/> AI agent.</returns>
|
||||
public static ChatClientAgent CreateAIAgent(
|
||||
public static ChatClientAgent AsAIAgent(
|
||||
this IBetaService betaService,
|
||||
string model,
|
||||
string? instructions = null,
|
||||
@@ -81,7 +81,7 @@ public static class AnthropicBetaServiceExtensions
|
||||
/// <param name="services">An optional <see cref="IServiceProvider"/> to use for resolving services required by the <see cref="AIFunction"/> instances being invoked.</param>
|
||||
/// <returns>An <see cref="ChatClientAgent"/> instance backed by the Anthropic Chat Completion service.</returns>
|
||||
/// <exception cref="ArgumentNullException">Thrown when <paramref name="betaService"/> or <paramref name="options"/> is <see langword="null"/>.</exception>
|
||||
public static ChatClientAgent CreateAIAgent(
|
||||
public static ChatClientAgent AsAIAgent(
|
||||
this IBetaService betaService,
|
||||
ChatClientAgentOptions options,
|
||||
Func<IChatClient, IChatClient>? clientFactory = null,
|
||||
|
||||
@@ -31,7 +31,7 @@ public static class AnthropicClientExtensions
|
||||
/// <param name="loggerFactory">Optional logger factory for enabling logging within the agent.</param>
|
||||
/// <param name="services">An optional <see cref="IServiceProvider"/> to use for resolving services required by the <see cref="AIFunction"/> instances being invoked.</param>
|
||||
/// <returns>The created <see cref="ChatClientAgent"/> AI agent.</returns>
|
||||
public static ChatClientAgent CreateAIAgent(
|
||||
public static ChatClientAgent AsAIAgent(
|
||||
this IAnthropicClient client,
|
||||
string model,
|
||||
string? instructions = null,
|
||||
@@ -81,7 +81,7 @@ public static class AnthropicClientExtensions
|
||||
/// <param name="services">An optional <see cref="IServiceProvider"/> to use for resolving services required by the <see cref="AIFunction"/> instances being invoked.</param>
|
||||
/// <returns>An <see cref="ChatClientAgent"/> instance backed by the Anthropic Chat Completion service.</returns>
|
||||
/// <exception cref="ArgumentNullException">Thrown when <paramref name="client"/> or <paramref name="options"/> is <see langword="null"/>.</exception>
|
||||
public static ChatClientAgent CreateAIAgent(
|
||||
public static ChatClientAgent AsAIAgent(
|
||||
this IAnthropicClient client,
|
||||
ChatClientAgentOptions options,
|
||||
Func<IChatClient, IChatClient>? clientFactory = null,
|
||||
|
||||
+10
-10
@@ -19,7 +19,7 @@ public static class PersistentAgentsClientExtensions
|
||||
/// <param name="clientFactory">Provides a way to customize the creation of the underlying <see cref="IChatClient"/> used by the agent.</param>
|
||||
/// <param name="services">An optional <see cref="IServiceProvider"/> to use for resolving services required by the <see cref="AIFunction"/> instances being invoked.</param>
|
||||
/// <returns>A <see cref="ChatClientAgent"/> instance that can be used to perform operations on the persistent agent.</returns>
|
||||
public static ChatClientAgent GetAIAgent(
|
||||
public static ChatClientAgent AsAIAgent(
|
||||
this PersistentAgentsClient persistentAgentsClient,
|
||||
Response<PersistentAgent> persistentAgentResponse,
|
||||
ChatOptions? chatOptions = null,
|
||||
@@ -31,7 +31,7 @@ public static class PersistentAgentsClientExtensions
|
||||
throw new ArgumentNullException(nameof(persistentAgentResponse));
|
||||
}
|
||||
|
||||
return GetAIAgent(persistentAgentsClient, persistentAgentResponse.Value, chatOptions, clientFactory, services);
|
||||
return AsAIAgent(persistentAgentsClient, persistentAgentResponse.Value, chatOptions, clientFactory, services);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -43,7 +43,7 @@ public static class PersistentAgentsClientExtensions
|
||||
/// <param name="clientFactory">Provides a way to customize the creation of the underlying <see cref="IChatClient"/> used by the agent.</param>
|
||||
/// <param name="services">An optional <see cref="IServiceProvider"/> to use for resolving services required by the <see cref="AIFunction"/> instances being invoked.</param>
|
||||
/// <returns>A <see cref="ChatClientAgent"/> instance that can be used to perform operations on the persistent agent.</returns>
|
||||
public static ChatClientAgent GetAIAgent(
|
||||
public static ChatClientAgent AsAIAgent(
|
||||
this PersistentAgentsClient persistentAgentsClient,
|
||||
PersistentAgent persistentAgentMetadata,
|
||||
ChatOptions? chatOptions = null,
|
||||
@@ -112,7 +112,7 @@ public static class PersistentAgentsClientExtensions
|
||||
}
|
||||
|
||||
var persistentAgentResponse = persistentAgentsClient.Administration.GetAgent(agentId, cancellationToken);
|
||||
return persistentAgentsClient.GetAIAgent(persistentAgentResponse, chatOptions, clientFactory, services);
|
||||
return persistentAgentsClient.AsAIAgent(persistentAgentResponse, chatOptions, clientFactory, services);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -145,7 +145,7 @@ public static class PersistentAgentsClientExtensions
|
||||
}
|
||||
|
||||
var persistentAgentResponse = await persistentAgentsClient.Administration.GetAgentAsync(agentId, cancellationToken).ConfigureAwait(false);
|
||||
return persistentAgentsClient.GetAIAgent(persistentAgentResponse, chatOptions, clientFactory, services);
|
||||
return persistentAgentsClient.AsAIAgent(persistentAgentResponse, chatOptions, clientFactory, services);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -158,7 +158,7 @@ public static class PersistentAgentsClientExtensions
|
||||
/// <param name="services">An optional <see cref="IServiceProvider"/> to use for resolving services required by the <see cref="AIFunction"/> instances being invoked.</param>
|
||||
/// <returns>A <see cref="ChatClientAgent"/> instance that can be used to perform operations on the persistent agent.</returns>
|
||||
/// <exception cref="ArgumentNullException">Thrown when <paramref name="persistentAgentResponse"/> or <paramref name="options"/> is <see langword="null"/>.</exception>
|
||||
public static ChatClientAgent GetAIAgent(
|
||||
public static ChatClientAgent AsAIAgent(
|
||||
this PersistentAgentsClient persistentAgentsClient,
|
||||
Response<PersistentAgent> persistentAgentResponse,
|
||||
ChatClientAgentOptions options,
|
||||
@@ -170,7 +170,7 @@ public static class PersistentAgentsClientExtensions
|
||||
throw new ArgumentNullException(nameof(persistentAgentResponse));
|
||||
}
|
||||
|
||||
return GetAIAgent(persistentAgentsClient, persistentAgentResponse.Value, options, clientFactory, services);
|
||||
return AsAIAgent(persistentAgentsClient, persistentAgentResponse.Value, options, clientFactory, services);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -183,7 +183,7 @@ public static class PersistentAgentsClientExtensions
|
||||
/// <param name="services">An optional <see cref="IServiceProvider"/> to use for resolving services required by the <see cref="AIFunction"/> instances being invoked.</param>
|
||||
/// <returns>A <see cref="ChatClientAgent"/> instance that can be used to perform operations on the persistent agent.</returns>
|
||||
/// <exception cref="ArgumentNullException">Thrown when <paramref name="persistentAgentMetadata"/> or <paramref name="options"/> is <see langword="null"/>.</exception>
|
||||
public static ChatClientAgent GetAIAgent(
|
||||
public static ChatClientAgent AsAIAgent(
|
||||
this PersistentAgentsClient persistentAgentsClient,
|
||||
PersistentAgent persistentAgentMetadata,
|
||||
ChatClientAgentOptions options,
|
||||
@@ -268,7 +268,7 @@ public static class PersistentAgentsClientExtensions
|
||||
}
|
||||
|
||||
var persistentAgentResponse = persistentAgentsClient.Administration.GetAgent(agentId, cancellationToken);
|
||||
return persistentAgentsClient.GetAIAgent(persistentAgentResponse, options, clientFactory, services);
|
||||
return persistentAgentsClient.AsAIAgent(persistentAgentResponse, options, clientFactory, services);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -307,7 +307,7 @@ public static class PersistentAgentsClientExtensions
|
||||
}
|
||||
|
||||
var persistentAgentResponse = await persistentAgentsClient.Administration.GetAgentAsync(agentId, cancellationToken).ConfigureAwait(false);
|
||||
return persistentAgentsClient.GetAIAgent(persistentAgentResponse, options, clientFactory, services);
|
||||
return persistentAgentsClient.AsAIAgent(persistentAgentResponse, options, clientFactory, services);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
||||
@@ -91,7 +91,7 @@ public static partial class AzureAIProjectChatClientExtensions
|
||||
|
||||
AgentRecord agentRecord = GetAgentRecordByName(aiProjectClient, name, cancellationToken);
|
||||
|
||||
return GetAIAgent(
|
||||
return AsAIAgent(
|
||||
aiProjectClient,
|
||||
agentRecord,
|
||||
tools,
|
||||
@@ -125,7 +125,7 @@ public static partial class AzureAIProjectChatClientExtensions
|
||||
|
||||
AgentRecord agentRecord = await GetAgentRecordByNameAsync(aiProjectClient, name, cancellationToken).ConfigureAwait(false);
|
||||
|
||||
return GetAIAgent(
|
||||
return AsAIAgent(
|
||||
aiProjectClient,
|
||||
agentRecord,
|
||||
tools,
|
||||
@@ -143,7 +143,7 @@ public static partial class AzureAIProjectChatClientExtensions
|
||||
/// <param name="services">An optional <see cref="IServiceProvider"/> to use for resolving services required by the <see cref="AIFunction"/> instances being invoked.</param>
|
||||
/// <returns>A <see cref="ChatClientAgent"/> instance that can be used to perform operations based on the latest version of the Azure AI Agent.</returns>
|
||||
/// <exception cref="ArgumentNullException">Thrown when <paramref name="aiProjectClient"/> or <paramref name="agentRecord"/> is <see langword="null"/>.</exception>
|
||||
public static ChatClientAgent GetAIAgent(
|
||||
public static ChatClientAgent AsAIAgent(
|
||||
this AIProjectClient aiProjectClient,
|
||||
AgentRecord agentRecord,
|
||||
IList<AITool>? tools = null,
|
||||
@@ -174,7 +174,7 @@ public static partial class AzureAIProjectChatClientExtensions
|
||||
/// <param name="services">An optional <see cref="IServiceProvider"/> to use for resolving services required by the <see cref="AIFunction"/> instances being invoked.</param>
|
||||
/// <returns>A <see cref="ChatClientAgent"/> instance that can be used to perform operations based on the provided version of the Azure AI Agent.</returns>
|
||||
/// <exception cref="ArgumentNullException">Thrown when <paramref name="aiProjectClient"/> or <paramref name="agentVersion"/> is <see langword="null"/>.</exception>
|
||||
public static ChatClientAgent GetAIAgent(
|
||||
public static ChatClientAgent AsAIAgent(
|
||||
this AIProjectClient aiProjectClient,
|
||||
AgentVersion agentVersion,
|
||||
IList<AITool>? tools = null,
|
||||
|
||||
@@ -36,13 +36,13 @@ This package provides a `ConfigureDurableAgents` extension method on the `Functi
|
||||
// Invocable via HTTP via http://localhost:7071/api/agents/SpamDetectionAgent/run
|
||||
AIAgent spamDetector = new AzureOpenAIClient(new Uri(endpoint), new AzureCliCredential())
|
||||
.GetChatClient(deploymentName)
|
||||
.CreateAIAgent(
|
||||
.AsAIAgent(
|
||||
instructions: "You are a spam detection assistant that identifies spam emails.",
|
||||
name: "SpamDetectionAgent");
|
||||
|
||||
AIAgent emailAssistant = new AzureOpenAIClient(new Uri(endpoint), new AzureCliCredential())
|
||||
.GetChatClient(deploymentName)
|
||||
.CreateAIAgent(
|
||||
.AsAIAgent(
|
||||
instructions: "You are an email assistant that helps users draft responses to emails with professionalism.",
|
||||
name: "EmailAssistantAgent");
|
||||
|
||||
@@ -156,7 +156,7 @@ These tools are registered with the agent using the `tools` parameter when creat
|
||||
Tools tools = new();
|
||||
AIAgent agent = new AzureOpenAIClient(new Uri(endpoint), new AzureCliCredential())
|
||||
.GetChatClient(deploymentName)
|
||||
.CreateAIAgent(
|
||||
.AsAIAgent(
|
||||
instructions: "You are a content generation assistant that helps users generate content.",
|
||||
name: "ContentGenerationAgent",
|
||||
tools: [
|
||||
|
||||
+10
-10
@@ -30,7 +30,7 @@ public static class OpenAIAssistantClientExtensions
|
||||
/// <param name="services">An optional <see cref="IServiceProvider"/> to use for resolving services required by the <see cref="AIFunction"/> instances being invoked.</param>
|
||||
/// <returns>A <see cref="ChatClientAgent"/> instance that can be used to perform operations on the assistant.</returns>
|
||||
[Obsolete("The Assistants API has been deprecated. Please use the Responses API instead.")]
|
||||
public static ChatClientAgent GetAIAgent(
|
||||
public static ChatClientAgent AsAIAgent(
|
||||
this AssistantClient assistantClient,
|
||||
ClientResult<Assistant> assistantClientResult,
|
||||
ChatOptions? chatOptions = null,
|
||||
@@ -42,7 +42,7 @@ public static class OpenAIAssistantClientExtensions
|
||||
throw new ArgumentNullException(nameof(assistantClientResult));
|
||||
}
|
||||
|
||||
return assistantClient.GetAIAgent(assistantClientResult.Value, chatOptions, clientFactory, services);
|
||||
return assistantClient.AsAIAgent(assistantClientResult.Value, chatOptions, clientFactory, services);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -55,7 +55,7 @@ public static class OpenAIAssistantClientExtensions
|
||||
/// <param name="services">An optional <see cref="IServiceProvider"/> to use for resolving services required by the <see cref="AIFunction"/> instances being invoked.</param>
|
||||
/// <returns>A <see cref="ChatClientAgent"/> instance that can be used to perform operations on the assistant.</returns>
|
||||
[Obsolete("The Assistants API has been deprecated. Please use the Responses API instead.")]
|
||||
public static ChatClientAgent GetAIAgent(
|
||||
public static ChatClientAgent AsAIAgent(
|
||||
this AssistantClient assistantClient,
|
||||
Assistant assistantMetadata,
|
||||
ChatOptions? chatOptions = null,
|
||||
@@ -123,7 +123,7 @@ public static class OpenAIAssistantClientExtensions
|
||||
}
|
||||
|
||||
var assistant = assistantClient.GetAssistant(agentId, cancellationToken);
|
||||
return assistantClient.GetAIAgent(assistant, chatOptions, clientFactory, services);
|
||||
return assistantClient.AsAIAgent(assistant, chatOptions, clientFactory, services);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -156,7 +156,7 @@ public static class OpenAIAssistantClientExtensions
|
||||
}
|
||||
|
||||
var assistantResponse = await assistantClient.GetAssistantAsync(agentId, cancellationToken).ConfigureAwait(false);
|
||||
return assistantClient.GetAIAgent(assistantResponse, chatOptions, clientFactory, services);
|
||||
return assistantClient.AsAIAgent(assistantResponse, chatOptions, clientFactory, services);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -170,7 +170,7 @@ public static class OpenAIAssistantClientExtensions
|
||||
/// <returns>A <see cref="ChatClientAgent"/> instance that can be used to perform operations on the assistant.</returns>
|
||||
/// <exception cref="ArgumentNullException"><paramref name="assistantClientResult"/> or <paramref name="options"/> is <see langword="null"/>.</exception>
|
||||
[Obsolete("The Assistants API has been deprecated. Please use the Responses API instead.")]
|
||||
public static ChatClientAgent GetAIAgent(
|
||||
public static ChatClientAgent AsAIAgent(
|
||||
this AssistantClient assistantClient,
|
||||
ClientResult<Assistant> assistantClientResult,
|
||||
ChatClientAgentOptions options,
|
||||
@@ -182,7 +182,7 @@ public static class OpenAIAssistantClientExtensions
|
||||
throw new ArgumentNullException(nameof(assistantClientResult));
|
||||
}
|
||||
|
||||
return assistantClient.GetAIAgent(assistantClientResult.Value, options, clientFactory, services);
|
||||
return assistantClient.AsAIAgent(assistantClientResult.Value, options, clientFactory, services);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -196,7 +196,7 @@ public static class OpenAIAssistantClientExtensions
|
||||
/// <returns>A <see cref="ChatClientAgent"/> instance that can be used to perform operations on the assistant.</returns>
|
||||
/// <exception cref="ArgumentNullException"><paramref name="assistantMetadata"/> or <paramref name="options"/> is <see langword="null"/>.</exception>
|
||||
[Obsolete("The Assistants API has been deprecated. Please use the Responses API instead.")]
|
||||
public static ChatClientAgent GetAIAgent(
|
||||
public static ChatClientAgent AsAIAgent(
|
||||
this AssistantClient assistantClient,
|
||||
Assistant assistantMetadata,
|
||||
ChatClientAgentOptions options,
|
||||
@@ -282,7 +282,7 @@ public static class OpenAIAssistantClientExtensions
|
||||
}
|
||||
|
||||
var assistant = assistantClient.GetAssistant(agentId, cancellationToken);
|
||||
return assistantClient.GetAIAgent(assistant, options, clientFactory, services);
|
||||
return assistantClient.AsAIAgent(assistant, options, clientFactory, services);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -322,7 +322,7 @@ public static class OpenAIAssistantClientExtensions
|
||||
}
|
||||
|
||||
var assistantResponse = await assistantClient.GetAssistantAsync(agentId, cancellationToken).ConfigureAwait(false);
|
||||
return assistantClient.GetAIAgent(assistantResponse, options, clientFactory, services);
|
||||
return assistantClient.AsAIAgent(assistantResponse, options, clientFactory, services);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
||||
@@ -32,7 +32,7 @@ public static class OpenAIChatClientExtensions
|
||||
/// <param name="services">An optional <see cref="IServiceProvider"/> to use for resolving services required by the <see cref="AIFunction"/> instances being invoked.</param>
|
||||
/// <returns>An <see cref="ChatClientAgent"/> instance backed by the OpenAI Chat Completion service.</returns>
|
||||
/// <exception cref="ArgumentNullException">Thrown when <paramref name="client"/> is <see langword="null"/>.</exception>
|
||||
public static ChatClientAgent CreateAIAgent(
|
||||
public static ChatClientAgent AsAIAgent(
|
||||
this ChatClient client,
|
||||
string? instructions = null,
|
||||
string? name = null,
|
||||
@@ -41,7 +41,7 @@ public static class OpenAIChatClientExtensions
|
||||
Func<IChatClient, IChatClient>? clientFactory = null,
|
||||
ILoggerFactory? loggerFactory = null,
|
||||
IServiceProvider? services = null) =>
|
||||
client.CreateAIAgent(
|
||||
client.AsAIAgent(
|
||||
new ChatClientAgentOptions()
|
||||
{
|
||||
Name = name,
|
||||
@@ -66,7 +66,7 @@ public static class OpenAIChatClientExtensions
|
||||
/// <param name="services">An optional <see cref="IServiceProvider"/> to use for resolving services required by the <see cref="AIFunction"/> instances being invoked.</param>
|
||||
/// <returns>An <see cref="ChatClientAgent"/> instance backed by the OpenAI Chat Completion service.</returns>
|
||||
/// <exception cref="ArgumentNullException">Thrown when <paramref name="client"/> or <paramref name="options"/> is <see langword="null"/>.</exception>
|
||||
public static ChatClientAgent CreateAIAgent(
|
||||
public static ChatClientAgent AsAIAgent(
|
||||
this ChatClient client,
|
||||
ChatClientAgentOptions options,
|
||||
Func<IChatClient, IChatClient>? clientFactory = null,
|
||||
|
||||
@@ -32,7 +32,7 @@ public static class OpenAIResponseClientExtensions
|
||||
/// <param name="services">An optional <see cref="IServiceProvider"/> to use for resolving services required by the <see cref="AIFunction"/> instances being invoked.</param>
|
||||
/// <returns>An <see cref="ChatClientAgent"/> instance backed by the OpenAI Response service.</returns>
|
||||
/// <exception cref="ArgumentNullException">Thrown when <paramref name="client"/> is <see langword="null"/>.</exception>
|
||||
public static ChatClientAgent CreateAIAgent(
|
||||
public static ChatClientAgent AsAIAgent(
|
||||
this ResponsesClient client,
|
||||
string? instructions = null,
|
||||
string? name = null,
|
||||
@@ -44,7 +44,7 @@ public static class OpenAIResponseClientExtensions
|
||||
{
|
||||
Throw.IfNull(client);
|
||||
|
||||
return client.CreateAIAgent(
|
||||
return client.AsAIAgent(
|
||||
new ChatClientAgentOptions()
|
||||
{
|
||||
Name = name,
|
||||
@@ -70,7 +70,7 @@ public static class OpenAIResponseClientExtensions
|
||||
/// <param name="services">An optional <see cref="IServiceProvider"/> to use for resolving services required by the <see cref="AIFunction"/> instances being invoked.</param>
|
||||
/// <returns>An <see cref="ChatClientAgent"/> instance backed by the OpenAI Response service.</returns>
|
||||
/// <exception cref="ArgumentNullException">Thrown when <paramref name="client"/> or <paramref name="options"/> is <see langword="null"/>.</exception>
|
||||
public static ChatClientAgent CreateAIAgent(
|
||||
public static ChatClientAgent AsAIAgent(
|
||||
this ResponsesClient client,
|
||||
ChatClientAgentOptions options,
|
||||
Func<IChatClient, IChatClient>? clientFactory = null,
|
||||
|
||||
@@ -12,7 +12,7 @@ namespace Microsoft.Agents.AI.Purview;
|
||||
/// <summary>
|
||||
/// Service that runs jobs in background threads.
|
||||
/// </summary>
|
||||
internal sealed class BackgroundJobRunner
|
||||
internal sealed class BackgroundJobRunner : IBackgroundJobRunner
|
||||
{
|
||||
private readonly IChannelHandler _channelHandler;
|
||||
private readonly IPurviewClient _purviewClient;
|
||||
@@ -70,4 +70,12 @@ internal sealed class BackgroundJobRunner
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Shutdown the job runners.
|
||||
/// </summary>
|
||||
public async Task ShutdownAsync()
|
||||
{
|
||||
await this._channelHandler.StopAndWaitForCompletionAsync().ConfigureAwait(false);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,16 @@
|
||||
// Copyright (c) Microsoft. All rights reserved.
|
||||
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace Microsoft.Agents.AI.Purview;
|
||||
|
||||
/// <summary>
|
||||
/// An interface for a class that manages background jobs.
|
||||
/// </summary>
|
||||
internal interface IBackgroundJobRunner
|
||||
{
|
||||
/// <summary>
|
||||
/// Shutdown the background jobs.
|
||||
/// </summary>
|
||||
Task ShutdownAsync();
|
||||
}
|
||||
@@ -41,7 +41,7 @@ public static class PurviewExtensions
|
||||
services.AddSingleton<PurviewWrapper>();
|
||||
services.AddSingleton(Channel.CreateBounded<BackgroundJobBase>(purviewSettings.PendingBackgroundJobLimit));
|
||||
services.AddSingleton<IChannelHandler, ChannelHandler>();
|
||||
services.AddSingleton<BackgroundJobRunner>();
|
||||
services.AddSingleton<IBackgroundJobRunner, BackgroundJobRunner>();
|
||||
ServiceProvider serviceProvider = services.BuildServiceProvider();
|
||||
|
||||
return serviceProvider.GetRequiredService<PurviewWrapper>();
|
||||
|
||||
@@ -18,7 +18,7 @@ internal sealed class PurviewWrapper : IDisposable
|
||||
private readonly ILogger _logger;
|
||||
private readonly IScopedContentProcessor _scopedProcessor;
|
||||
private readonly PurviewSettings _purviewSettings;
|
||||
private readonly IChannelHandler _channelHandler;
|
||||
private readonly IBackgroundJobRunner _backgroundJobRunner;
|
||||
|
||||
/// <summary>
|
||||
/// Creates a new <see cref="PurviewWrapper"/> instance.
|
||||
@@ -26,13 +26,13 @@ internal sealed class PurviewWrapper : IDisposable
|
||||
/// <param name="scopedProcessor">The scoped processor used to orchestrate the calls to Purview.</param>
|
||||
/// <param name="purviewSettings">The settings for Purview integration.</param>
|
||||
/// <param name="logger">The logger used for logging.</param>
|
||||
/// <param name="channelHandler">The channel handler used to queue background jobs and add job runners.</param>
|
||||
public PurviewWrapper(IScopedContentProcessor scopedProcessor, PurviewSettings purviewSettings, ILogger logger, IChannelHandler channelHandler)
|
||||
/// <param name="backgroundJobRunner">The runner used to manage background jobs.</param>
|
||||
public PurviewWrapper(IScopedContentProcessor scopedProcessor, PurviewSettings purviewSettings, ILogger logger, IBackgroundJobRunner backgroundJobRunner)
|
||||
{
|
||||
this._scopedProcessor = scopedProcessor;
|
||||
this._purviewSettings = purviewSettings;
|
||||
this._logger = logger;
|
||||
this._channelHandler = channelHandler;
|
||||
this._backgroundJobRunner = backgroundJobRunner;
|
||||
}
|
||||
|
||||
private static string GetThreadIdFromAgentThread(AgentThread? thread, IEnumerable<ChatMessage> messages)
|
||||
@@ -203,7 +203,7 @@ internal sealed class PurviewWrapper : IDisposable
|
||||
public void Dispose()
|
||||
{
|
||||
#pragma warning disable VSTHRD002 // Need to wait for pending jobs to complete.
|
||||
this._channelHandler.StopAndWaitForCompletionAsync().GetAwaiter().GetResult();
|
||||
this._backgroundJobRunner.ShutdownAsync().GetAwaiter().GetResult();
|
||||
#pragma warning restore VSTHRD002 // Need to wait for pending jobs to complete.
|
||||
}
|
||||
}
|
||||
|
||||
@@ -186,7 +186,7 @@ AIAgent agent = new AzureOpenAIClient(
|
||||
new Uri(endpoint),
|
||||
new AzureCliCredential())
|
||||
.GetChatClient(deploymentName)
|
||||
.CreateAIAgent("You are a helpful assistant.")
|
||||
.AsAIAgent("You are a helpful assistant.")
|
||||
.AsBuilder()
|
||||
.WithPurview(browserCredential, new PurviewSettings("Agent Framework Test App"))
|
||||
.Build();
|
||||
|
||||
@@ -174,7 +174,7 @@ public sealed class AzureAgentProvider(Uri projectEndpoint, TokenCredential proj
|
||||
|
||||
AIProjectClient client = this.GetAgentClient();
|
||||
|
||||
agent = client.GetAIAgent(agentVersion, tools: null, clientFactory: null, services: null);
|
||||
agent = client.AsAIAgent(agentVersion, tools: null, clientFactory: null, services: null);
|
||||
|
||||
FunctionInvokingChatClient? functionInvokingClient = agent.GetService<FunctionInvokingChatClient>();
|
||||
if (functionInvokingClient is not null)
|
||||
|
||||
@@ -519,16 +519,16 @@ public sealed partial class ChatClientAgent : AIAgent
|
||||
{
|
||||
ChatOptions? requestChatOptions = (runOptions as ChatClientAgentRunOptions)?.ChatOptions?.Clone();
|
||||
|
||||
// If no agent chat options were provided, return the request chat options as is.
|
||||
// If no agent chat options were provided, return the request chat options with just agent run options overrides.
|
||||
if (this._agentOptions?.ChatOptions is null)
|
||||
{
|
||||
return GetContinuationTokenAndApplyBackgroundResponsesProperties(requestChatOptions, runOptions);
|
||||
return ApplyAgentRunOptionsOverrides(requestChatOptions, runOptions);
|
||||
}
|
||||
|
||||
// If no request chat options were provided, use the agent's chat options clone.
|
||||
// If no request chat options were provided, use the agent's chat options clone with agent run options overrides.
|
||||
if (requestChatOptions is null)
|
||||
{
|
||||
return GetContinuationTokenAndApplyBackgroundResponsesProperties(this._agentOptions?.ChatOptions.Clone(), runOptions);
|
||||
return ApplyAgentRunOptionsOverrides(this._agentOptions?.ChatOptions.Clone(), runOptions);
|
||||
}
|
||||
|
||||
// If both are present, we need to merge them.
|
||||
@@ -557,9 +557,9 @@ public sealed partial class ChatClientAgent : AIAgent
|
||||
// Merge only the additional properties from the agent if they are not already set in the request options.
|
||||
if (requestChatOptions.AdditionalProperties is not null && this._agentOptions.ChatOptions.AdditionalProperties is not null)
|
||||
{
|
||||
foreach (var propertyKey in this._agentOptions.ChatOptions.AdditionalProperties.Keys)
|
||||
foreach (var kvp in this._agentOptions.ChatOptions.AdditionalProperties)
|
||||
{
|
||||
_ = requestChatOptions.AdditionalProperties.TryAdd(propertyKey, this._agentOptions.ChatOptions.AdditionalProperties[propertyKey]);
|
||||
_ = requestChatOptions.AdditionalProperties.TryAdd(kvp.Key, kvp.Value);
|
||||
}
|
||||
}
|
||||
else
|
||||
@@ -624,9 +624,9 @@ public sealed partial class ChatClientAgent : AIAgent
|
||||
}
|
||||
}
|
||||
|
||||
return GetContinuationTokenAndApplyBackgroundResponsesProperties(requestChatOptions, runOptions);
|
||||
return ApplyAgentRunOptionsOverrides(requestChatOptions, runOptions);
|
||||
|
||||
static (ChatOptions?, ChatClientAgentContinuationToken?) GetContinuationTokenAndApplyBackgroundResponsesProperties(ChatOptions? chatOptions, AgentRunOptions? agentRunOptions)
|
||||
static (ChatOptions?, ChatClientAgentContinuationToken?) ApplyAgentRunOptionsOverrides(ChatOptions? chatOptions, AgentRunOptions? agentRunOptions)
|
||||
{
|
||||
if (agentRunOptions?.AllowBackgroundResponses is not null)
|
||||
{
|
||||
@@ -643,6 +643,17 @@ public sealed partial class ChatClientAgent : AIAgent
|
||||
chatOptions.ContinuationToken = agentContinuationToken!.InnerToken;
|
||||
}
|
||||
|
||||
// Add/Replace any additional properties from the AgentRunOptions, since they should always take precedence.
|
||||
if (agentRunOptions?.AdditionalProperties is { Count: > 0 })
|
||||
{
|
||||
chatOptions ??= new ChatOptions();
|
||||
chatOptions.AdditionalProperties ??= new();
|
||||
foreach (var kvp in agentRunOptions.AdditionalProperties)
|
||||
{
|
||||
chatOptions.AdditionalProperties[kvp.Key] = kvp.Value;
|
||||
}
|
||||
}
|
||||
|
||||
return (chatOptions, agentContinuationToken);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -49,7 +49,7 @@ public static class ChatClientBuilderExtensions
|
||||
IList<AITool>? tools = null,
|
||||
ILoggerFactory? loggerFactory = null,
|
||||
IServiceProvider? services = null) =>
|
||||
Throw.IfNull(builder).Build(services).CreateAIAgent(
|
||||
Throw.IfNull(builder).Build(services).AsAIAgent(
|
||||
instructions: instructions,
|
||||
name: name,
|
||||
description: description,
|
||||
@@ -78,7 +78,7 @@ public static class ChatClientBuilderExtensions
|
||||
ChatClientAgentOptions? options,
|
||||
ILoggerFactory? loggerFactory = null,
|
||||
IServiceProvider? services = null) =>
|
||||
Throw.IfNull(builder).Build(services).CreateAIAgent(
|
||||
Throw.IfNull(builder).Build(services).AsAIAgent(
|
||||
options: options,
|
||||
loggerFactory: loggerFactory,
|
||||
services: services);
|
||||
|
||||
@@ -20,7 +20,7 @@ public static class ChatClientExtensions
|
||||
/// </summary>
|
||||
/// <inheritdoc cref="ChatClientAgent(IChatClient, string?, string?, string?, IList{AITool}?, ILoggerFactory?, IServiceProvider?)"/>
|
||||
/// <returns>A new <see cref="ChatClientAgent"/> instance.</returns>
|
||||
public static ChatClientAgent CreateAIAgent(
|
||||
public static ChatClientAgent AsAIAgent(
|
||||
this IChatClient chatClient,
|
||||
string? instructions = null,
|
||||
string? name = null,
|
||||
@@ -42,7 +42,7 @@ public static class ChatClientExtensions
|
||||
/// </summary>
|
||||
/// <inheritdoc cref="ChatClientAgent(IChatClient, ChatClientAgentOptions?, ILoggerFactory?, IServiceProvider?)"/>
|
||||
/// <returns>A new <see cref="ChatClientAgent"/> instance.</returns>
|
||||
public static ChatClientAgent CreateAIAgent(
|
||||
public static ChatClientAgent AsAIAgent(
|
||||
this IChatClient chatClient,
|
||||
ChatClientAgentOptions? options,
|
||||
ILoggerFactory? loggerFactory = null,
|
||||
|
||||
+2
-2
@@ -34,7 +34,7 @@ public sealed class A2AAgentCardExtensionsTests
|
||||
public void GetAIAgent_ReturnsAIAgent()
|
||||
{
|
||||
// Act
|
||||
var agent = this._agentCard.GetAIAgent();
|
||||
var agent = this._agentCard.AsAIAgent();
|
||||
|
||||
// Assert
|
||||
Assert.NotNull(agent);
|
||||
@@ -56,7 +56,7 @@ public sealed class A2AAgentCardExtensionsTests
|
||||
Parts = [new TextPart { Text = "Response" }],
|
||||
});
|
||||
|
||||
var agent = this._agentCard.GetAIAgent(httpClient);
|
||||
var agent = this._agentCard.AsAIAgent(httpClient);
|
||||
|
||||
// Act
|
||||
await agent.RunAsync("Test input");
|
||||
|
||||
+1
-1
@@ -21,7 +21,7 @@ public sealed class A2AClientExtensionsTests
|
||||
const string TestDescription = "This is a test agent description";
|
||||
|
||||
// Act
|
||||
var agent = a2aClient.GetAIAgent(TestId, TestName, TestDescription);
|
||||
var agent = a2aClient.AsAIAgent(TestId, TestName, TestDescription);
|
||||
|
||||
// Assert
|
||||
Assert.NotNull(agent);
|
||||
|
||||
@@ -30,7 +30,7 @@ public sealed class AGUIAgentTests
|
||||
]);
|
||||
|
||||
var chatClient = new AGUIChatClient(httpClient, "http://localhost/agent", null, AGUIJsonSerializerContext.Default.Options);
|
||||
AIAgent agent = chatClient.CreateAIAgent(instructions: null, name: "agent1", description: "Test agent", tools: []);
|
||||
AIAgent agent = chatClient.AsAIAgent(instructions: null, name: "agent1", description: "Test agent", tools: []);
|
||||
List<ChatMessage> messages = [new ChatMessage(ChatRole.User, "Test")];
|
||||
|
||||
// Act
|
||||
@@ -55,7 +55,7 @@ public sealed class AGUIAgentTests
|
||||
]);
|
||||
|
||||
var chatClient = new AGUIChatClient(httpClient, "http://localhost/agent", null, AGUIJsonSerializerContext.Default.Options);
|
||||
AIAgent agent = chatClient.CreateAIAgent(instructions: null, name: "agent1", description: "Test agent", tools: []);
|
||||
AIAgent agent = chatClient.AsAIAgent(instructions: null, name: "agent1", description: "Test agent", tools: []);
|
||||
List<ChatMessage> messages = [new ChatMessage(ChatRole.User, "Test")];
|
||||
|
||||
// Act
|
||||
@@ -74,7 +74,7 @@ public sealed class AGUIAgentTests
|
||||
// Arrange
|
||||
using HttpClient httpClient = new();
|
||||
var chatClient = new AGUIChatClient(httpClient, "http://localhost/agent", null, AGUIJsonSerializerContext.Default.Options);
|
||||
AIAgent agent = chatClient.CreateAIAgent(instructions: "Test agent", name: "agent1");
|
||||
AIAgent agent = chatClient.AsAIAgent(instructions: "Test agent", name: "agent1");
|
||||
|
||||
// Act & Assert
|
||||
await Assert.ThrowsAsync<ArgumentNullException>(() => agent.RunAsync(messages: null!));
|
||||
@@ -91,7 +91,7 @@ public sealed class AGUIAgentTests
|
||||
]);
|
||||
|
||||
var chatClient = new AGUIChatClient(httpClient, "http://localhost/agent", null, AGUIJsonSerializerContext.Default.Options);
|
||||
AIAgent agent = chatClient.CreateAIAgent(instructions: "Test agent", name: "agent1");
|
||||
AIAgent agent = chatClient.AsAIAgent(instructions: "Test agent", name: "agent1");
|
||||
List<ChatMessage> messages = [new ChatMessage(ChatRole.User, "Test")];
|
||||
|
||||
// Act
|
||||
@@ -115,7 +115,7 @@ public sealed class AGUIAgentTests
|
||||
]);
|
||||
|
||||
var chatClient = new AGUIChatClient(httpClient, "http://localhost/agent", null, AGUIJsonSerializerContext.Default.Options);
|
||||
AIAgent agent = chatClient.CreateAIAgent(instructions: "Test agent", name: "agent1");
|
||||
AIAgent agent = chatClient.AsAIAgent(instructions: "Test agent", name: "agent1");
|
||||
List<ChatMessage> messages = [new ChatMessage(ChatRole.User, "Test")];
|
||||
|
||||
// Act
|
||||
@@ -139,7 +139,7 @@ public sealed class AGUIAgentTests
|
||||
// Arrange
|
||||
using HttpClient httpClient = new();
|
||||
var chatClient = new AGUIChatClient(httpClient, "http://localhost/agent", null, AGUIJsonSerializerContext.Default.Options);
|
||||
AIAgent agent = chatClient.CreateAIAgent(instructions: "Test agent", name: "agent1");
|
||||
AIAgent agent = chatClient.AsAIAgent(instructions: "Test agent", name: "agent1");
|
||||
|
||||
// Act & Assert
|
||||
await Assert.ThrowsAsync<ArgumentNullException>(async () =>
|
||||
@@ -162,7 +162,7 @@ public sealed class AGUIAgentTests
|
||||
]);
|
||||
|
||||
var chatClient = new AGUIChatClient(httpClient, "http://localhost/agent", null, AGUIJsonSerializerContext.Default.Options);
|
||||
AIAgent agent = chatClient.CreateAIAgent(instructions: "Test agent", name: "agent1");
|
||||
AIAgent agent = chatClient.AsAIAgent(instructions: "Test agent", name: "agent1");
|
||||
List<ChatMessage> messages = [new ChatMessage(ChatRole.User, "Test")];
|
||||
|
||||
// Act
|
||||
@@ -195,7 +195,7 @@ public sealed class AGUIAgentTests
|
||||
using HttpClient httpClient = new(handler);
|
||||
|
||||
var chatClient = new AGUIChatClient(httpClient, "http://localhost/agent", null, AGUIJsonSerializerContext.Default.Options);
|
||||
AIAgent agent = chatClient.CreateAIAgent(instructions: null, name: "agent1", description: "Test agent", tools: []);
|
||||
AIAgent agent = chatClient.AsAIAgent(instructions: null, name: "agent1", description: "Test agent", tools: []);
|
||||
List<ChatMessage> messages = [new ChatMessage(ChatRole.User, "Test")];
|
||||
|
||||
// Act
|
||||
@@ -227,7 +227,7 @@ public sealed class AGUIAgentTests
|
||||
]);
|
||||
|
||||
var chatClient = new AGUIChatClient(httpClient, "http://localhost/agent", null, AGUIJsonSerializerContext.Default.Options);
|
||||
AIAgent agent = chatClient.CreateAIAgent(instructions: null, name: "agent1", description: "Test agent", tools: []);
|
||||
AIAgent agent = chatClient.AsAIAgent(instructions: null, name: "agent1", description: "Test agent", tools: []);
|
||||
AgentThread thread = await agent.GetNewThreadAsync();
|
||||
List<ChatMessage> messages = [new ChatMessage(ChatRole.User, "Hello")];
|
||||
|
||||
@@ -249,7 +249,7 @@ public sealed class AGUIAgentTests
|
||||
// Arrange
|
||||
using var httpClient = new HttpClient();
|
||||
var chatClient = new AGUIChatClient(httpClient, "http://localhost/agent", null, AGUIJsonSerializerContext.Default.Options);
|
||||
AIAgent agent = chatClient.CreateAIAgent(instructions: null, name: "agent1", description: "Test agent", tools: []);
|
||||
AIAgent agent = chatClient.AsAIAgent(instructions: null, name: "agent1", description: "Test agent", tools: []);
|
||||
AgentThread originalThread = await agent.GetNewThreadAsync();
|
||||
JsonElement serialized = originalThread.Serialize();
|
||||
|
||||
@@ -301,7 +301,7 @@ public sealed class AGUIAgentTests
|
||||
]);
|
||||
|
||||
var chatClient = new AGUIChatClient(httpClient, "http://localhost/agent", null, AGUIJsonSerializerContext.Default.Options);
|
||||
AIAgent agent = chatClient.CreateAIAgent(instructions: null, name: "agent1", description: "Test agent", tools: [testTool]);
|
||||
AIAgent agent = chatClient.AsAIAgent(instructions: null, name: "agent1", description: "Test agent", tools: [testTool]);
|
||||
List<ChatMessage> messages = [new ChatMessage(ChatRole.User, "What's the weather?")];
|
||||
|
||||
// Act
|
||||
@@ -353,7 +353,7 @@ public sealed class AGUIAgentTests
|
||||
using HttpClient httpClient = new(handler);
|
||||
|
||||
var chatClient = new AGUIChatClient(httpClient, "http://localhost/agent", null, AGUIJsonSerializerContext.Default.Options);
|
||||
AIAgent agent = chatClient.CreateAIAgent(instructions: null, name: "agent1", description: "Test agent", tools: [tool1]); // Only tool1, not tool2
|
||||
AIAgent agent = chatClient.AsAIAgent(instructions: null, name: "agent1", description: "Test agent", tools: [tool1]); // Only tool1, not tool2
|
||||
List<ChatMessage> messages = [new ChatMessage(ChatRole.User, "Test")];
|
||||
|
||||
// Act
|
||||
@@ -403,7 +403,7 @@ public sealed class AGUIAgentTests
|
||||
]);
|
||||
|
||||
var chatClient = new AGUIChatClient(httpClient, "http://localhost/agent", null, AGUIJsonSerializerContext.Default.Options);
|
||||
AIAgent agent = chatClient.CreateAIAgent(instructions: null, name: "agent1", description: "Test agent", tools: [faultyTool]);
|
||||
AIAgent agent = chatClient.AsAIAgent(instructions: null, name: "agent1", description: "Test agent", tools: [faultyTool]);
|
||||
List<ChatMessage> messages = [new ChatMessage(ChatRole.User, "Test")];
|
||||
|
||||
// Act
|
||||
@@ -448,7 +448,7 @@ public sealed class AGUIAgentTests
|
||||
]);
|
||||
|
||||
var chatClient = new AGUIChatClient(httpClient, "http://localhost/agent", null, AGUIJsonSerializerContext.Default.Options);
|
||||
AIAgent agent = chatClient.CreateAIAgent(instructions: null, name: "agent1", description: "Test agent", tools: [tool1, tool2]);
|
||||
AIAgent agent = chatClient.AsAIAgent(instructions: null, name: "agent1", description: "Test agent", tools: [tool1, tool2]);
|
||||
List<ChatMessage> messages = [new ChatMessage(ChatRole.User, "Test")];
|
||||
|
||||
// Act
|
||||
@@ -486,7 +486,7 @@ public sealed class AGUIAgentTests
|
||||
]);
|
||||
|
||||
var chatClient = new AGUIChatClient(httpClient, "http://localhost/agent", null, AGUIJsonSerializerContext.Default.Options);
|
||||
AIAgent agent = chatClient.CreateAIAgent(instructions: null, name: "agent1", description: "Test agent", tools: [testTool]);
|
||||
AIAgent agent = chatClient.AsAIAgent(instructions: null, name: "agent1", description: "Test agent", tools: [testTool]);
|
||||
AgentThread thread = await agent.GetNewThreadAsync();
|
||||
List<ChatMessage> messages = [new ChatMessage(ChatRole.User, "Test")];
|
||||
|
||||
|
||||
+7
-7
@@ -34,7 +34,7 @@ public sealed class AnthropicBetaServiceExtensionsTests
|
||||
var testChatClient = new TestChatClient(chatClient.Beta.AsIChatClient());
|
||||
|
||||
// Act
|
||||
var agent = chatClient.Beta.CreateAIAgent(
|
||||
var agent = chatClient.Beta.AsAIAgent(
|
||||
model: "test-model",
|
||||
instructions: "Test instructions",
|
||||
name: "Test Agent",
|
||||
@@ -63,7 +63,7 @@ public sealed class AnthropicBetaServiceExtensionsTests
|
||||
TestChatClient? testChatClient = null;
|
||||
|
||||
// Act
|
||||
var agent = chatClient.Beta.CreateAIAgent(
|
||||
var agent = chatClient.Beta.AsAIAgent(
|
||||
model: "test-model",
|
||||
instructions: "Test instructions",
|
||||
clientFactory: (innerClient) =>
|
||||
@@ -95,7 +95,7 @@ public sealed class AnthropicBetaServiceExtensionsTests
|
||||
};
|
||||
|
||||
// Act
|
||||
var agent = chatClient.Beta.CreateAIAgent(
|
||||
var agent = chatClient.Beta.AsAIAgent(
|
||||
options,
|
||||
clientFactory: (innerClient) => testChatClient);
|
||||
|
||||
@@ -120,7 +120,7 @@ public sealed class AnthropicBetaServiceExtensionsTests
|
||||
var chatClient = new TestAnthropicChatClient();
|
||||
|
||||
// Act
|
||||
var agent = chatClient.Beta.CreateAIAgent(
|
||||
var agent = chatClient.Beta.AsAIAgent(
|
||||
model: "test-model",
|
||||
instructions: "Test instructions",
|
||||
name: "Test Agent");
|
||||
@@ -144,7 +144,7 @@ public sealed class AnthropicBetaServiceExtensionsTests
|
||||
var chatClient = new TestAnthropicChatClient();
|
||||
|
||||
// Act
|
||||
var agent = chatClient.Beta.CreateAIAgent(
|
||||
var agent = chatClient.Beta.AsAIAgent(
|
||||
model: "test-model",
|
||||
instructions: "Test instructions",
|
||||
name: "Test Agent",
|
||||
@@ -167,7 +167,7 @@ public sealed class AnthropicBetaServiceExtensionsTests
|
||||
{
|
||||
// Act & Assert
|
||||
var exception = Assert.Throws<ArgumentNullException>(() =>
|
||||
((IBetaService)null!).CreateAIAgent("test-model"));
|
||||
((IBetaService)null!).AsAIAgent("test-model"));
|
||||
|
||||
Assert.Equal("betaService", exception.ParamName);
|
||||
}
|
||||
@@ -183,7 +183,7 @@ public sealed class AnthropicBetaServiceExtensionsTests
|
||||
|
||||
// Act & Assert
|
||||
var exception = Assert.Throws<ArgumentNullException>(() =>
|
||||
chatClient.Beta.CreateAIAgent((ChatClientAgentOptions)null!));
|
||||
chatClient.Beta.AsAIAgent((ChatClientAgentOptions)null!));
|
||||
|
||||
Assert.Equal("options", exception.ParamName);
|
||||
}
|
||||
|
||||
+7
-7
@@ -101,7 +101,7 @@ public sealed class AnthropicClientExtensionsTests
|
||||
var testChatClient = new TestChatClient(chatClient.AsIChatClient());
|
||||
|
||||
// Act
|
||||
var agent = chatClient.CreateAIAgent(
|
||||
var agent = chatClient.AsAIAgent(
|
||||
model: "test-model",
|
||||
instructions: "Test instructions",
|
||||
name: "Test Agent",
|
||||
@@ -130,7 +130,7 @@ public sealed class AnthropicClientExtensionsTests
|
||||
TestChatClient? testChatClient = null;
|
||||
|
||||
// Act
|
||||
var agent = chatClient.CreateAIAgent(
|
||||
var agent = chatClient.AsAIAgent(
|
||||
model: "test-model",
|
||||
instructions: "Test instructions",
|
||||
clientFactory: (innerClient) =>
|
||||
@@ -162,7 +162,7 @@ public sealed class AnthropicClientExtensionsTests
|
||||
};
|
||||
|
||||
// Act
|
||||
var agent = chatClient.CreateAIAgent(
|
||||
var agent = chatClient.AsAIAgent(
|
||||
options,
|
||||
clientFactory: (innerClient) => testChatClient);
|
||||
|
||||
@@ -187,7 +187,7 @@ public sealed class AnthropicClientExtensionsTests
|
||||
var chatClient = new TestAnthropicChatClient();
|
||||
|
||||
// Act
|
||||
var agent = chatClient.CreateAIAgent(
|
||||
var agent = chatClient.AsAIAgent(
|
||||
model: "test-model",
|
||||
instructions: "Test instructions",
|
||||
name: "Test Agent");
|
||||
@@ -211,7 +211,7 @@ public sealed class AnthropicClientExtensionsTests
|
||||
var chatClient = new TestAnthropicChatClient();
|
||||
|
||||
// Act
|
||||
var agent = chatClient.CreateAIAgent(
|
||||
var agent = chatClient.AsAIAgent(
|
||||
model: "test-model",
|
||||
instructions: "Test instructions",
|
||||
name: "Test Agent",
|
||||
@@ -234,7 +234,7 @@ public sealed class AnthropicClientExtensionsTests
|
||||
{
|
||||
// Act & Assert
|
||||
var exception = Assert.Throws<ArgumentNullException>(() =>
|
||||
((TestAnthropicChatClient)null!).CreateAIAgent("test-model"));
|
||||
((TestAnthropicChatClient)null!).AsAIAgent("test-model"));
|
||||
|
||||
Assert.Equal("client", exception.ParamName);
|
||||
}
|
||||
@@ -250,7 +250,7 @@ public sealed class AnthropicClientExtensionsTests
|
||||
|
||||
// Act & Assert
|
||||
var exception = Assert.Throws<ArgumentNullException>(() =>
|
||||
chatClient.CreateAIAgent((ChatClientAgentOptions)null!));
|
||||
chatClient.AsAIAgent((ChatClientAgentOptions)null!));
|
||||
|
||||
Assert.Equal("options", exception.ParamName);
|
||||
}
|
||||
|
||||
+8
-8
@@ -42,7 +42,7 @@ public sealed class PersistentAgentsClientExtensionsTests
|
||||
|
||||
// Act & Assert - null agentId
|
||||
var exception1 = Assert.Throws<ArgumentException>(() =>
|
||||
mockClient.Object.GetAIAgent((string)null!));
|
||||
mockClient.Object.GetAIAgent(null!));
|
||||
Assert.Equal("agentId", exception1.ParamName);
|
||||
|
||||
// Act & Assert - empty agentId
|
||||
@@ -314,7 +314,7 @@ public sealed class PersistentAgentsClientExtensionsTests
|
||||
};
|
||||
|
||||
// Act
|
||||
var agent = client.GetAIAgent(response, options);
|
||||
var agent = client.AsAIAgent(response, options);
|
||||
|
||||
// Assert
|
||||
Assert.NotNull(agent);
|
||||
@@ -341,7 +341,7 @@ public sealed class PersistentAgentsClientExtensionsTests
|
||||
};
|
||||
|
||||
// Act
|
||||
var agent = client.GetAIAgent(persistentAgent, options);
|
||||
var agent = client.AsAIAgent(persistentAgent, options);
|
||||
|
||||
// Assert
|
||||
Assert.NotNull(agent);
|
||||
@@ -363,7 +363,7 @@ public sealed class PersistentAgentsClientExtensionsTests
|
||||
var options = new ChatClientAgentOptions(); // Empty options
|
||||
|
||||
// Act
|
||||
var agent = client.GetAIAgent(persistentAgent, options);
|
||||
var agent = client.AsAIAgent(persistentAgent, options);
|
||||
|
||||
// Assert
|
||||
Assert.NotNull(agent);
|
||||
@@ -443,7 +443,7 @@ public sealed class PersistentAgentsClientExtensionsTests
|
||||
};
|
||||
|
||||
// Act
|
||||
var agent = client.GetAIAgent(
|
||||
var agent = client.AsAIAgent(
|
||||
persistentAgent,
|
||||
options,
|
||||
clientFactory: (innerClient) => testChatClient);
|
||||
@@ -470,7 +470,7 @@ public sealed class PersistentAgentsClientExtensionsTests
|
||||
|
||||
// Act & Assert
|
||||
var exception = Assert.Throws<ArgumentNullException>(() =>
|
||||
client.GetAIAgent((Response<PersistentAgent>)null!, options));
|
||||
client.AsAIAgent(null!, options));
|
||||
|
||||
Assert.Equal("persistentAgentResponse", exception.ParamName);
|
||||
}
|
||||
@@ -487,7 +487,7 @@ public sealed class PersistentAgentsClientExtensionsTests
|
||||
|
||||
// Act & Assert
|
||||
var exception = Assert.Throws<ArgumentNullException>(() =>
|
||||
client.GetAIAgent((PersistentAgent)null!, options));
|
||||
client.AsAIAgent((PersistentAgent)null!, options));
|
||||
|
||||
Assert.Equal("persistentAgentMetadata", exception.ParamName);
|
||||
}
|
||||
@@ -504,7 +504,7 @@ public sealed class PersistentAgentsClientExtensionsTests
|
||||
|
||||
// Act & Assert
|
||||
var exception = Assert.Throws<ArgumentNullException>(() =>
|
||||
client.GetAIAgent(persistentAgent, (ChatClientAgentOptions)null!));
|
||||
client.AsAIAgent(persistentAgent, (ChatClientAgentOptions)null!));
|
||||
|
||||
Assert.Equal("options", exception.ParamName);
|
||||
}
|
||||
|
||||
+58
-58
@@ -25,13 +25,13 @@ namespace Microsoft.Agents.AI.AzureAI.UnitTests;
|
||||
/// </summary>
|
||||
public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
{
|
||||
#region GetAIAgent(AIProjectClient, AgentRecord) Tests
|
||||
#region AsAIAgent(AIProjectClient, AgentRecord) Tests
|
||||
|
||||
/// <summary>
|
||||
/// Verify that GetAIAgent throws ArgumentNullException when AIProjectClient is null.
|
||||
/// Verify that AsAIAgent throws ArgumentNullException when AIProjectClient is null.
|
||||
/// </summary>
|
||||
[Fact]
|
||||
public void GetAIAgent_WithAgentRecord_WithNullClient_ThrowsArgumentNullException()
|
||||
public void AsAIAgent_WithAgentRecord_WithNullClient_ThrowsArgumentNullException()
|
||||
{
|
||||
// Arrange
|
||||
AIProjectClient? client = null;
|
||||
@@ -39,39 +39,39 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
|
||||
// Act & Assert
|
||||
var exception = Assert.Throws<ArgumentNullException>(() =>
|
||||
client!.GetAIAgent(agentRecord));
|
||||
client!.AsAIAgent(agentRecord));
|
||||
|
||||
Assert.Equal("aiProjectClient", exception.ParamName);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Verify that GetAIAgent throws ArgumentNullException when agentRecord is null.
|
||||
/// Verify that AsAIAgent throws ArgumentNullException when agentRecord is null.
|
||||
/// </summary>
|
||||
[Fact]
|
||||
public void GetAIAgent_WithAgentRecord_WithNullAgentRecord_ThrowsArgumentNullException()
|
||||
public void AsAIAgent_WithAgentRecord_WithNullAgentRecord_ThrowsArgumentNullException()
|
||||
{
|
||||
// Arrange
|
||||
var mockClient = new Mock<AIProjectClient>();
|
||||
|
||||
// Act & Assert
|
||||
var exception = Assert.Throws<ArgumentNullException>(() =>
|
||||
mockClient.Object.GetAIAgent((AgentRecord)null!));
|
||||
mockClient.Object.AsAIAgent((AgentRecord)null!));
|
||||
|
||||
Assert.Equal("agentRecord", exception.ParamName);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Verify that GetAIAgent with AgentRecord creates a valid agent.
|
||||
/// Verify that AsAIAgent with AgentRecord creates a valid agent.
|
||||
/// </summary>
|
||||
[Fact]
|
||||
public void GetAIAgent_WithAgentRecord_CreatesValidAgent()
|
||||
public void AsAIAgent_WithAgentRecord_CreatesValidAgent()
|
||||
{
|
||||
// Arrange
|
||||
AIProjectClient client = this.CreateTestAgentClient();
|
||||
AgentRecord agentRecord = this.CreateTestAgentRecord();
|
||||
|
||||
// Act
|
||||
var agent = client.GetAIAgent(agentRecord);
|
||||
var agent = client.AsAIAgent(agentRecord);
|
||||
|
||||
// Assert
|
||||
Assert.NotNull(agent);
|
||||
@@ -79,10 +79,10 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Verify that GetAIAgent with AgentRecord and clientFactory applies the factory.
|
||||
/// Verify that AsAIAgent with AgentRecord and clientFactory applies the factory.
|
||||
/// </summary>
|
||||
[Fact]
|
||||
public void GetAIAgent_WithAgentRecord_WithClientFactory_AppliesFactoryCorrectly()
|
||||
public void AsAIAgent_WithAgentRecord_WithClientFactory_AppliesFactoryCorrectly()
|
||||
{
|
||||
// Arrange
|
||||
AIProjectClient client = this.CreateTestAgentClient();
|
||||
@@ -90,7 +90,7 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
TestChatClient? testChatClient = null;
|
||||
|
||||
// Act
|
||||
var agent = client.GetAIAgent(
|
||||
var agent = client.AsAIAgent(
|
||||
agentRecord,
|
||||
clientFactory: (innerClient) => testChatClient = new TestChatClient(innerClient));
|
||||
|
||||
@@ -103,13 +103,13 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
|
||||
#endregion
|
||||
|
||||
#region GetAIAgent(AIProjectClient, AgentVersion) Tests
|
||||
#region AsAIAgent(AIProjectClient, AgentVersion) Tests
|
||||
|
||||
/// <summary>
|
||||
/// Verify that GetAIAgent throws ArgumentNullException when AIProjectClient is null.
|
||||
/// Verify that AsAIAgent throws ArgumentNullException when AIProjectClient is null.
|
||||
/// </summary>
|
||||
[Fact]
|
||||
public void GetAIAgent_WithAgentVersion_WithNullClient_ThrowsArgumentNullException()
|
||||
public void AsAIAgent_WithAgentVersion_WithNullClient_ThrowsArgumentNullException()
|
||||
{
|
||||
// Arrange
|
||||
AIProjectClient? client = null;
|
||||
@@ -117,39 +117,39 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
|
||||
// Act & Assert
|
||||
var exception = Assert.Throws<ArgumentNullException>(() =>
|
||||
client!.GetAIAgent(agentVersion));
|
||||
client!.AsAIAgent(agentVersion));
|
||||
|
||||
Assert.Equal("aiProjectClient", exception.ParamName);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Verify that GetAIAgent throws ArgumentNullException when agentVersion is null.
|
||||
/// Verify that AsAIAgent throws ArgumentNullException when agentVersion is null.
|
||||
/// </summary>
|
||||
[Fact]
|
||||
public void GetAIAgent_WithAgentVersion_WithNullAgentVersion_ThrowsArgumentNullException()
|
||||
public void AsAIAgent_WithAgentVersion_WithNullAgentVersion_ThrowsArgumentNullException()
|
||||
{
|
||||
// Arrange
|
||||
var mockClient = new Mock<AIProjectClient>();
|
||||
|
||||
// Act & Assert
|
||||
var exception = Assert.Throws<ArgumentNullException>(() =>
|
||||
mockClient.Object.GetAIAgent((AgentVersion)null!));
|
||||
mockClient.Object.AsAIAgent((AgentVersion)null!));
|
||||
|
||||
Assert.Equal("agentVersion", exception.ParamName);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Verify that GetAIAgent with AgentVersion creates a valid agent.
|
||||
/// Verify that AsAIAgent with AgentVersion creates a valid agent.
|
||||
/// </summary>
|
||||
[Fact]
|
||||
public void GetAIAgent_WithAgentVersion_CreatesValidAgent()
|
||||
public void AsAIAgent_WithAgentVersion_CreatesValidAgent()
|
||||
{
|
||||
// Arrange
|
||||
AIProjectClient client = this.CreateTestAgentClient();
|
||||
AgentVersion agentVersion = this.CreateTestAgentVersion();
|
||||
|
||||
// Act
|
||||
var agent = client.GetAIAgent(agentVersion);
|
||||
var agent = client.AsAIAgent(agentVersion);
|
||||
|
||||
// Assert
|
||||
Assert.NotNull(agent);
|
||||
@@ -157,10 +157,10 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Verify that GetAIAgent with AgentVersion and clientFactory applies the factory.
|
||||
/// Verify that AsAIAgent with AgentVersion and clientFactory applies the factory.
|
||||
/// </summary>
|
||||
[Fact]
|
||||
public void GetAIAgent_WithAgentVersion_WithClientFactory_AppliesFactoryCorrectly()
|
||||
public void AsAIAgent_WithAgentVersion_WithClientFactory_AppliesFactoryCorrectly()
|
||||
{
|
||||
// Arrange
|
||||
AIProjectClient client = this.CreateTestAgentClient();
|
||||
@@ -168,7 +168,7 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
TestChatClient? testChatClient = null;
|
||||
|
||||
// Act
|
||||
var agent = client.GetAIAgent(
|
||||
var agent = client.AsAIAgent(
|
||||
agentVersion,
|
||||
clientFactory: (innerClient) => testChatClient = new TestChatClient(innerClient));
|
||||
|
||||
@@ -183,7 +183,7 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
/// Verify that GetAIAgent with requireInvocableTools=true enforces invocable tools.
|
||||
/// </summary>
|
||||
[Fact]
|
||||
public void GetAIAgent_WithAgentVersion_WithRequireInvocableToolsTrue_EnforcesInvocableTools()
|
||||
public void AsAIAgent_WithAgentVersion_WithRequireInvocableToolsTrue_EnforcesInvocableTools()
|
||||
{
|
||||
// Arrange
|
||||
AIProjectClient client = this.CreateTestAgentClient();
|
||||
@@ -194,7 +194,7 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
};
|
||||
|
||||
// Act
|
||||
var agent = client.GetAIAgent(agentVersion, tools: tools);
|
||||
var agent = client.AsAIAgent(agentVersion, tools: tools);
|
||||
|
||||
// Assert
|
||||
Assert.NotNull(agent);
|
||||
@@ -205,14 +205,14 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
/// Verify that GetAIAgent with requireInvocableTools=false allows declarative functions.
|
||||
/// </summary>
|
||||
[Fact]
|
||||
public void GetAIAgent_WithAgentVersion_WithRequireInvocableToolsFalse_AllowsDeclarativeFunctions()
|
||||
public void AsAIAgent_WithAgentVersion_WithRequireInvocableToolsFalse_AllowsDeclarativeFunctions()
|
||||
{
|
||||
// Arrange
|
||||
AIProjectClient client = this.CreateTestAgentClient();
|
||||
AgentVersion agentVersion = this.CreateTestAgentVersion();
|
||||
|
||||
// Act - should not throw even without tools when requireInvocableTools is false
|
||||
var agent = client.GetAIAgent(agentVersion);
|
||||
var agent = client.AsAIAgent(agentVersion);
|
||||
|
||||
// Assert
|
||||
Assert.NotNull(agent);
|
||||
@@ -374,7 +374,7 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
#region GetAIAgent(AIProjectClient, string) Tests
|
||||
|
||||
/// <summary>
|
||||
/// Verify that GetAIAgent throws ArgumentNullException when AIProjectClient is null.
|
||||
/// Verify that AsAIAgent throws ArgumentNullException when AIProjectClient is null.
|
||||
/// </summary>
|
||||
[Fact]
|
||||
public void GetAIAgent_ByName_WithNullClient_ThrowsArgumentNullException()
|
||||
@@ -390,7 +390,7 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Verify that GetAIAgent throws ArgumentNullException when name is null.
|
||||
/// Verify that AsAIAgent throws ArgumentNullException when name is null.
|
||||
/// </summary>
|
||||
[Fact]
|
||||
public void GetAIAgent_ByName_WithNullName_ThrowsArgumentNullException()
|
||||
@@ -406,7 +406,7 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Verify that GetAIAgent throws ArgumentException when name is empty.
|
||||
/// Verify that AsAIAgent throws ArgumentException when name is empty.
|
||||
/// </summary>
|
||||
[Fact]
|
||||
public void GetAIAgent_ByName_WithEmptyName_ThrowsArgumentException()
|
||||
@@ -422,7 +422,7 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Verify that GetAIAgent throws InvalidOperationException when agent is not found.
|
||||
/// Verify that AsAIAgent throws InvalidOperationException when agent is not found.
|
||||
/// </summary>
|
||||
[Fact]
|
||||
public void GetAIAgent_ByName_WithNonExistentAgent_ThrowsInvalidOperationException()
|
||||
@@ -505,13 +505,13 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
|
||||
#endregion
|
||||
|
||||
#region GetAIAgent(AIProjectClient, AgentRecord) with tools Tests
|
||||
#region AsAIAgent(AIProjectClient, AgentRecord) with tools Tests
|
||||
|
||||
/// <summary>
|
||||
/// Verify that GetAIAgent with additional tools when the definition has no tools does not throw and results in an agent with no tools.
|
||||
/// Verify that AsAIAgent with additional tools when the definition has no tools does not throw and results in an agent with no tools.
|
||||
/// </summary>
|
||||
[Fact]
|
||||
public void GetAIAgent_WithAgentRecordAndAdditionalTools_WhenDefinitionHasNoTools_ShouldNotThrow()
|
||||
public void AsAIAgent_WithAgentRecordAndAdditionalTools_WhenDefinitionHasNoTools_ShouldNotThrow()
|
||||
{
|
||||
// Arrange
|
||||
AIProjectClient client = this.CreateTestAgentClient();
|
||||
@@ -522,7 +522,7 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
};
|
||||
|
||||
// Act
|
||||
var agent = client.GetAIAgent(agentRecord, tools: tools);
|
||||
var agent = client.AsAIAgent(agentRecord, tools: tools);
|
||||
|
||||
// Assert
|
||||
Assert.NotNull(agent);
|
||||
@@ -536,17 +536,17 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Verify that GetAIAgent with null tools works correctly.
|
||||
/// Verify that AsAIAgent with null tools works correctly.
|
||||
/// </summary>
|
||||
[Fact]
|
||||
public void GetAIAgent_WithAgentRecordAndNullTools_WorksCorrectly()
|
||||
public void AsAIAgent_WithAgentRecordAndNullTools_WorksCorrectly()
|
||||
{
|
||||
// Arrange
|
||||
AIProjectClient client = this.CreateTestAgentClient();
|
||||
AgentRecord agentRecord = this.CreateTestAgentRecord();
|
||||
|
||||
// Act
|
||||
var agent = client.GetAIAgent(agentRecord, tools: null);
|
||||
var agent = client.AsAIAgent(agentRecord, tools: null);
|
||||
|
||||
// Assert
|
||||
Assert.NotNull(agent);
|
||||
@@ -1104,7 +1104,7 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
var shouldBeIgnoredTool = AIFunctionFactory.Create(() => "test", "additional_tool", "An additional test function that should be ignored");
|
||||
|
||||
// Act & Assert
|
||||
var agent = client.GetAIAgent(agentVersion, tools: [invocableInlineAITool, shouldBeIgnoredTool]);
|
||||
var agent = client.AsAIAgent(agentVersion, tools: [invocableInlineAITool, shouldBeIgnoredTool]);
|
||||
Assert.NotNull(agent);
|
||||
var version = agent.GetService<AgentVersion>();
|
||||
Assert.NotNull(version);
|
||||
@@ -1136,7 +1136,7 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
};
|
||||
|
||||
// Act
|
||||
var agent = client.GetAIAgent(agentRecord, tools: tools);
|
||||
var agent = client.AsAIAgent(agentRecord, tools: tools);
|
||||
|
||||
// Assert
|
||||
Assert.NotNull(agent);
|
||||
@@ -1632,7 +1632,7 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
#region AgentName Validation Tests
|
||||
|
||||
/// <summary>
|
||||
/// Verify that GetAIAgent throws ArgumentException when agent name is invalid.
|
||||
/// Verify that AsAIAgent throws ArgumentException when agent name is invalid.
|
||||
/// </summary>
|
||||
[Theory]
|
||||
[MemberData(nameof(InvalidAgentNameTestData.GetInvalidAgentNames), MemberType = typeof(InvalidAgentNameTestData))]
|
||||
@@ -1846,7 +1846,7 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
/// Verify that the underlying chat client created by extension methods can be wrapped with clientFactory.
|
||||
/// </summary>
|
||||
[Fact]
|
||||
public void GetAIAgent_WithClientFactory_WrapsUnderlyingChatClient()
|
||||
public void AsAIAgent_WithClientFactory_WrapsUnderlyingChatClient()
|
||||
{
|
||||
// Arrange
|
||||
AIProjectClient client = this.CreateTestAgentClient();
|
||||
@@ -1854,7 +1854,7 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
int factoryCallCount = 0;
|
||||
|
||||
// Act
|
||||
var agent = client.GetAIAgent(
|
||||
var agent = client.AsAIAgent(
|
||||
agentRecord,
|
||||
clientFactory: (innerClient) =>
|
||||
{
|
||||
@@ -1903,18 +1903,18 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
/// Verify that multiple clientFactory calls create independent wrapped clients.
|
||||
/// </summary>
|
||||
[Fact]
|
||||
public void GetAIAgent_MultipleCallsWithClientFactory_CreatesIndependentClients()
|
||||
public void AsAIAgent_MultipleCallsWithClientFactory_CreatesIndependentClients()
|
||||
{
|
||||
// Arrange
|
||||
AIProjectClient client = this.CreateTestAgentClient();
|
||||
AgentRecord agentRecord = this.CreateTestAgentRecord();
|
||||
|
||||
// Act
|
||||
var agent1 = client.GetAIAgent(
|
||||
var agent1 = client.AsAIAgent(
|
||||
agentRecord,
|
||||
clientFactory: (innerClient) => new TestChatClient(innerClient));
|
||||
|
||||
var agent2 = client.GetAIAgent(
|
||||
var agent2 = client.AsAIAgent(
|
||||
agentRecord,
|
||||
clientFactory: (innerClient) => new TestChatClient(innerClient));
|
||||
|
||||
@@ -2165,7 +2165,7 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
#region GetAIAgent(AIProjectClient, AgentReference) Tests
|
||||
|
||||
/// <summary>
|
||||
/// Verify that GetAIAgent throws ArgumentNullException when AIProjectClient is null.
|
||||
/// Verify that AsAIAgent throws ArgumentNullException when AIProjectClient is null.
|
||||
/// </summary>
|
||||
[Fact]
|
||||
public void GetAIAgent_WithAgentReference_WithNullClient_ThrowsArgumentNullException()
|
||||
@@ -2182,7 +2182,7 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Verify that GetAIAgent throws ArgumentNullException when agentReference is null.
|
||||
/// Verify that AsAIAgent throws ArgumentNullException when agentReference is null.
|
||||
/// </summary>
|
||||
[Fact]
|
||||
public void GetAIAgent_WithAgentReference_WithNullAgentReference_ThrowsArgumentNullException()
|
||||
@@ -2297,7 +2297,7 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
AgentRecord agentRecord = this.CreateTestAgentRecord();
|
||||
|
||||
// Act
|
||||
var agent = client.GetAIAgent(agentRecord);
|
||||
var agent = client.AsAIAgent(agentRecord);
|
||||
var retrievedRecord = agent.GetService<AgentRecord>();
|
||||
|
||||
// Assert
|
||||
@@ -2338,7 +2338,7 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
AgentVersion agentVersion = this.CreateTestAgentVersion();
|
||||
|
||||
// Act
|
||||
var agent = client.GetAIAgent(agentVersion);
|
||||
var agent = client.AsAIAgent(agentVersion);
|
||||
var retrievedVersion = agent.GetService<AgentVersion>();
|
||||
|
||||
// Assert
|
||||
@@ -2379,7 +2379,7 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
AgentRecord agentRecord = this.CreateTestAgentRecord();
|
||||
|
||||
// Act
|
||||
var agent = client.GetAIAgent(agentRecord);
|
||||
var agent = client.AsAIAgent(agentRecord);
|
||||
var metadata = agent.GetService<ChatClientMetadata>();
|
||||
|
||||
// Assert
|
||||
@@ -2402,7 +2402,7 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
AgentRecord agentRecord = this.CreateTestAgentRecord(definition);
|
||||
|
||||
// Act
|
||||
var agent = client.GetAIAgent(agentRecord);
|
||||
var agent = client.AsAIAgent(agentRecord);
|
||||
var metadata = agent.GetService<ChatClientMetadata>();
|
||||
|
||||
// Assert
|
||||
@@ -2423,7 +2423,7 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
AgentVersion agentVersion = this.CreateTestAgentVersion();
|
||||
|
||||
// Act
|
||||
var agent = client.GetAIAgent(agentVersion);
|
||||
var agent = client.AsAIAgent(agentVersion);
|
||||
var metadata = agent.GetService<ChatClientMetadata>();
|
||||
|
||||
// Assert
|
||||
@@ -2467,7 +2467,7 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
AgentRecord agentRecord = this.CreateTestAgentRecord();
|
||||
|
||||
// Act
|
||||
var agent = client.GetAIAgent(agentRecord);
|
||||
var agent = client.AsAIAgent(agentRecord);
|
||||
var retrievedReference = agent.GetService<AgentReference>();
|
||||
|
||||
// Assert
|
||||
@@ -2486,7 +2486,7 @@ public sealed class AzureAIProjectChatClientExtensionsTests
|
||||
AgentVersion agentVersion = this.CreateTestAgentVersion();
|
||||
|
||||
// Act
|
||||
var agent = client.GetAIAgent(agentVersion);
|
||||
var agent = client.AsAIAgent(agentVersion);
|
||||
var retrievedReference = agent.GetService<AgentReference>();
|
||||
|
||||
// Assert
|
||||
|
||||
@@ -41,7 +41,7 @@ public sealed class AgentEntityTests(ITestOutputHelper outputHelper) : IDisposab
|
||||
public async Task EntityNamePrefixAsync()
|
||||
{
|
||||
// Setup
|
||||
AIAgent simpleAgent = TestHelper.GetAzureOpenAIChatClient(s_configuration).CreateAIAgent(
|
||||
AIAgent simpleAgent = TestHelper.GetAzureOpenAIChatClient(s_configuration).AsAIAgent(
|
||||
name: "TestAgent",
|
||||
instructions: "You are a helpful assistant that always responds with a friendly greeting."
|
||||
);
|
||||
@@ -88,7 +88,7 @@ public sealed class AgentEntityTests(ITestOutputHelper outputHelper) : IDisposab
|
||||
public async Task RunAgentMethodNamesAllWorkAsync(string runAgentMethodName)
|
||||
{
|
||||
// Setup
|
||||
AIAgent simpleAgent = TestHelper.GetAzureOpenAIChatClient(s_configuration).CreateAIAgent(
|
||||
AIAgent simpleAgent = TestHelper.GetAzureOpenAIChatClient(s_configuration).AsAIAgent(
|
||||
name: "TestAgent",
|
||||
instructions: "You are a helpful assistant that always responds with a friendly greeting."
|
||||
);
|
||||
@@ -143,7 +143,7 @@ public sealed class AgentEntityTests(ITestOutputHelper outputHelper) : IDisposab
|
||||
public async Task OrchestrationIdSetDuringOrchestrationAsync()
|
||||
{
|
||||
// Arrange
|
||||
AIAgent simpleAgent = TestHelper.GetAzureOpenAIChatClient(s_configuration).CreateAIAgent(
|
||||
AIAgent simpleAgent = TestHelper.GetAzureOpenAIChatClient(s_configuration).AsAIAgent(
|
||||
name: "TestAgent",
|
||||
instructions: "You are a helpful assistant that always responds with a friendly greeting."
|
||||
);
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user