From 026dc1dd402c0b1c77425b4640a62941769925e8 Mon Sep 17 00:00:00 2001
From: westey <164392973+westey-m@users.noreply.github.com>
Date: Fri, 28 Mar 2025 19:37:15 +0000
Subject: [PATCH] .Net: Removing groupchat from samples that have a single
 agent and aren't demonstrating a groupchat concept (#11261)

### Motivation and Context

Addressing Feedback from bugbash

### Description

Removing groupchat from samples that have a single agent and aren't
demonstrating a groupchat concept

### Contribution Checklist

<!-- Before submitting this PR, please make sure: -->

- [ ] The code builds clean without any errors or warnings
- [ ] The PR follows the [SK Contribution
Guidelines](https://github.com/microsoft/semantic-kernel/blob/main/CONTRIBUTING.md)
and the [pre-submission formatting
script](https://github.com/microsoft/semantic-kernel/blob/main/CONTRIBUTING.md#development-scripts)
raises no violations
- [ ] All unit tests pass, and I have added new tests where possible
- [ ] I didn't break anyone :smile:

Co-authored-by: Mark Wallace <127216156+markwallace-microsoft@users.noreply.github.com>
---
 .../Agents/AzureAIAgent_FileManipulation.cs   | 10 +-
 .../ChatCompletion_FunctionTermination.cs     | 94 -------------------
 .../Agents/ChatCompletion_HistoryReducer.cs   | 68 --------------
 .../Agents/OpenAIAssistant_ChartMaker.cs      | 14 ++-
 .../OpenAIAssistant_FileManipulation.cs       | 14 ++-
 .../Agents/OpenAIAssistant_FunctionFilters.cs | 20 ++--
 6 files changed, 29 insertions(+), 191 deletions(-)

diff --git a/dotnet/samples/Concepts/Agents/AzureAIAgent_FileManipulation.cs b/dotnet/samples/Concepts/Agents/AzureAIAgent_FileManipulation.cs
index cf55801420df..120af824229c 100644
--- a/dotnet/samples/Concepts/Agents/AzureAIAgent_FileManipulation.cs
+++ b/dotnet/samples/Concepts/Agents/AzureAIAgent_FileManipulation.cs
@@ -1,7 +1,6 @@
 // Copyright (c) Microsoft. All rights reserved.
 using Azure.AI.Projects;
 using Microsoft.SemanticKernel;
-using Microsoft.SemanticKernel.Agents;
 using Microsoft.SemanticKernel.Agents.AzureAI;
 using Microsoft.SemanticKernel.ChatCompletion;
 using Resources;
@@ -33,9 +32,7 @@ public async Task AnalyzeCSVFileUsingAzureAIAgentAsync()
                     }
                 });
         AzureAIAgent agent = new(definition, this.AgentsClient);
-
-        // Create a chat for agent interaction.
-        AgentGroupChat chat = new();
+        AzureAIAgentThread thread = new(this.AgentsClient);
 
         // Respond to user input
         try
@@ -46,19 +43,18 @@ public async Task AnalyzeCSVFileUsingAzureAIAgentAsync()
         }
         finally
         {
+            await thread.DeleteAsync();
             await this.AgentsClient.DeleteAgentAsync(agent.Id);
             await this.AgentsClient.DeleteFileAsync(fileInfo.Id);
-            await chat.ResetAsync();
         }
 
         // Local function to invoke agent and display the conversation messages.
         async Task InvokeAgentAsync(string input)
         {
             ChatMessageContent message = new(AuthorRole.User, input);
-            chat.AddChatMessage(new(AuthorRole.User, input));
             this.WriteAgentChatMessage(message);
 
-            await foreach (ChatMessageContent response in chat.InvokeAsync(agent))
+            await foreach (ChatMessageContent response in agent.InvokeAsync(message, thread))
             {
                 this.WriteAgentChatMessage(response);
                 await this.DownloadContentAsync(response);
diff --git a/dotnet/samples/Concepts/Agents/ChatCompletion_FunctionTermination.cs b/dotnet/samples/Concepts/Agents/ChatCompletion_FunctionTermination.cs
index 0aea67e8f806..0a7960e743c6 100644
--- a/dotnet/samples/Concepts/Agents/ChatCompletion_FunctionTermination.cs
+++ b/dotnet/samples/Concepts/Agents/ChatCompletion_FunctionTermination.cs
@@ -53,47 +53,6 @@ async Task InvokeAgentAsync(string input)
         }
     }
 
-    [Fact]
-    public async Task UseAutoFunctionInvocationFilterWithAgentChatAsync()
-    {
-        // Define the agent
-        ChatCompletionAgent agent =
-            new()
-            {
-                Instructions = "Answer questions about the menu.",
-                Kernel = CreateKernelWithFilter(),
-                Arguments = new KernelArguments(new PromptExecutionSettings() { FunctionChoiceBehavior = FunctionChoiceBehavior.Auto() }),
-            };
-
-        KernelPlugin plugin = KernelPluginFactory.CreateFromType<MenuPlugin>();
-        agent.Kernel.Plugins.Add(plugin);
-
-        // Create a chat for agent interaction.
-        AgentGroupChat chat = new();
-
-        // Respond to user input, invoking functions where appropriate.
-        await InvokeAgentAsync("Hello");
-        await InvokeAgentAsync("What is the special soup?");
-        await InvokeAgentAsync("What is the special drink?");
-        await InvokeAgentAsync("Thank you");
-
-        // Display the entire chat history.
-        WriteChatHistory(await chat.GetChatMessagesAsync().ToArrayAsync());
-
-        // Local function to invoke agent and display the conversation messages.
-        async Task InvokeAgentAsync(string input)
-        {
-            ChatMessageContent message = new(AuthorRole.User, input);
-            chat.AddChatMessage(message);
-            this.WriteAgentChatMessage(message);
-
-            await foreach (ChatMessageContent response in chat.InvokeAsync(agent))
-            {
-                this.WriteAgentChatMessage(response);
-            }
-        }
-    }
-
     [Fact]
     public async Task UseAutoFunctionInvocationFilterWithStreamingAgentInvocationAsync()
     {
@@ -156,59 +115,6 @@ async Task InvokeAgentAsync(string input)
         }
     }
 
-    [Fact]
-    public async Task UseAutoFunctionInvocationFilterWithStreamingAgentChatAsync()
-    {
-        // Define the agent
-        ChatCompletionAgent agent =
-            new()
-            {
-                Instructions = "Answer questions about the menu.",
-                Kernel = CreateKernelWithFilter(),
-                Arguments = new KernelArguments(new PromptExecutionSettings() { FunctionChoiceBehavior = FunctionChoiceBehavior.Auto() }),
-            };
-
-        KernelPlugin plugin = KernelPluginFactory.CreateFromType<MenuPlugin>();
-        agent.Kernel.Plugins.Add(plugin);
-
-        // Create a chat for agent interaction.
-        AgentGroupChat chat = new();
-
-        // Respond to user input, invoking functions where appropriate.
-        await InvokeAgentAsync("Hello");
-        await InvokeAgentAsync("What is the special soup?");
-        await InvokeAgentAsync("What is the special drink?");
-        await InvokeAgentAsync("Thank you");
-
-        // Display the entire chat history.
-        WriteChatHistory(await chat.GetChatMessagesAsync().ToArrayAsync());
-
-        // Local function to invoke agent and display the conversation messages.
-        async Task InvokeAgentAsync(string input)
-        {
-            ChatMessageContent message = new(AuthorRole.User, input);
-            chat.AddChatMessage(message);
-            this.WriteAgentChatMessage(message);
-
-            bool isFirst = false;
-            await foreach (StreamingChatMessageContent response in chat.InvokeStreamingAsync(agent))
-            {
-                if (string.IsNullOrEmpty(response.Content))
-                {
-                    continue;
-                }
-
-                if (!isFirst)
-                {
-                    Console.WriteLine($"\n# {response.Role} - {response.AuthorName ?? "*"}:");
-                    isFirst = true;
-                }
-
-                Console.WriteLine($"\t > streamed: '{response.Content}'");
-            }
-        }
-    }
-
     private void WriteChatHistory(IEnumerable<ChatMessageContent> chat)
     {
         Console.WriteLine("================================");
diff --git a/dotnet/samples/Concepts/Agents/ChatCompletion_HistoryReducer.cs b/dotnet/samples/Concepts/Agents/ChatCompletion_HistoryReducer.cs
index ec014236add3..6c0268c7b4ef 100644
--- a/dotnet/samples/Concepts/Agents/ChatCompletion_HistoryReducer.cs
+++ b/dotnet/samples/Concepts/Agents/ChatCompletion_HistoryReducer.cs
@@ -41,32 +41,6 @@ public async Task SummarizedAgentReductionAsync()
         await InvokeAgentAsync(agent, 50);
     }
 
-    /// <summary>
-    /// Demonstrate the use of <see cref="ChatHistoryTruncationReducer"/> when using
-    /// <see cref="AgentGroupChat"/> to invoke a <see cref="ChatCompletionAgent"/>.
-    /// </summary>
-    [Fact]
-    public async Task TruncatedChatReductionAsync()
-    {
-        // Define the agent
-        ChatCompletionAgent agent = CreateTruncatingAgent(10, 10);
-
-        await InvokeChatAsync(agent, 50);
-    }
-
-    /// <summary>
-    /// Demonstrate the use of <see cref="ChatHistorySummarizationReducer"/> when using
-    /// <see cref="AgentGroupChat"/> to invoke a <see cref="ChatCompletionAgent"/>.
-    /// </summary>
-    [Fact]
-    public async Task SummarizedChatReductionAsync()
-    {
-        // Define the agent
-        ChatCompletionAgent agent = CreateSummarizingAgent(10, 10);
-
-        await InvokeChatAsync(agent, 50);
-    }
-
     // Proceed with dialog by directly invoking the agent and explicitly managing the history.
     private async Task InvokeAgentAsync(ChatCompletionAgent agent, int messageCount)
     {
@@ -105,48 +79,6 @@ private async Task InvokeAgentAsync(ChatCompletionAgent agent, int messageCount)
         }
     }
 
-    // Proceed with dialog with AgentGroupChat.
-    private async Task InvokeChatAsync(ChatCompletionAgent agent, int messageCount)
-    {
-        AgentGroupChat chat = new();
-
-        int lastHistoryCount = 0;
-
-        int index = 1;
-        while (index <= messageCount)
-        {
-            // Provide user input
-            chat.AddChatMessage(new ChatMessageContent(AuthorRole.User, $"{index}"));
-            Console.WriteLine($"# {AuthorRole.User}: '{index}'");
-
-            // Invoke and display assistant response
-            await foreach (ChatMessageContent message in chat.InvokeAsync(agent))
-            {
-                Console.WriteLine($"# {message.Role} - {message.AuthorName ?? "*"}: '{message.Content}'");
-            }
-
-            index += 2;
-
-            // Display the message count of the chat-history for visibility into reduction
-            // Note: Messages provided in descending order (newest first)
-            ChatMessageContent[] history = await chat.GetChatMessagesAsync(agent).ToArrayAsync();
-            Console.WriteLine($"@ Message Count: {history.Length}\n");
-
-            // Display summary messages (if present) if reduction has occurred
-            if (history.Length < lastHistoryCount)
-            {
-                int summaryIndex = history.Length - 1;
-                while (history[summaryIndex].Metadata?.ContainsKey(ChatHistorySummarizationReducer.SummaryMetadataKey) ?? false)
-                {
-                    Console.WriteLine($"\tSummary: {history[summaryIndex].Content}");
-                    --summaryIndex;
-                }
-            }
-
-            lastHistoryCount = history.Length;
-        }
-    }
-
     private ChatCompletionAgent CreateSummarizingAgent(int reducerMessageCount, int reducerThresholdCount)
     {
         Kernel kernel = this.CreateKernelWithChatCompletion();
diff --git a/dotnet/samples/Concepts/Agents/OpenAIAssistant_ChartMaker.cs b/dotnet/samples/Concepts/Agents/OpenAIAssistant_ChartMaker.cs
index f23e7ab952b7..9ca9a8077410 100644
--- a/dotnet/samples/Concepts/Agents/OpenAIAssistant_ChartMaker.cs
+++ b/dotnet/samples/Concepts/Agents/OpenAIAssistant_ChartMaker.cs
@@ -27,9 +27,7 @@ await this.AssistantClient.CreateAssistantAsync(
 
         // Create the agent
         OpenAIAssistantAgent agent = new(assistant, this.AssistantClient);
-
-        // Create a chat for agent interaction.
-        AgentGroupChat chat = new();
+        AgentThread? agentThread = null;
 
         // Respond to user input
         try
@@ -50,6 +48,11 @@ Sum      426  1622     856 2904
         }
         finally
         {
+            if (agentThread is not null)
+            {
+                await agentThread.DeleteAsync();
+            }
+
             await this.AssistantClient.DeleteAssistantAsync(agent.Id);
         }
 
@@ -57,13 +60,14 @@ Sum      426  1622     856 2904
         async Task InvokeAgentAsync(string input)
         {
             ChatMessageContent message = new(AuthorRole.User, input);
-            chat.AddChatMessage(message);
             this.WriteAgentChatMessage(message);
 
-            await foreach (ChatMessageContent response in chat.InvokeAsync(agent))
+            await foreach (AgentResponseItem<ChatMessageContent> response in agent.InvokeAsync(message))
             {
                 this.WriteAgentChatMessage(response);
                 await this.DownloadResponseImageAsync(response);
+
+                agentThread = response.Thread;
             }
         }
     }
diff --git a/dotnet/samples/Concepts/Agents/OpenAIAssistant_FileManipulation.cs b/dotnet/samples/Concepts/Agents/OpenAIAssistant_FileManipulation.cs
index 915861ab2a99..0c4afbf13750 100644
--- a/dotnet/samples/Concepts/Agents/OpenAIAssistant_FileManipulation.cs
+++ b/dotnet/samples/Concepts/Agents/OpenAIAssistant_FileManipulation.cs
@@ -29,9 +29,7 @@ await this.AssistantClient.CreateAssistantAsync(
 
         // Create the agent
         OpenAIAssistantAgent agent = new(assistant, this.AssistantClient);
-
-        // Create a chat for agent interaction.
-        AgentGroupChat chat = new();
+        AgentThread? agentThread = null;
 
         // Respond to user input
         try
@@ -42,6 +40,11 @@ await this.AssistantClient.CreateAssistantAsync(
         }
         finally
         {
+            if (agentThread is not null)
+            {
+                await agentThread.DeleteAsync();
+            }
+
             await this.AssistantClient.DeleteAssistantAsync(agent.Id);
             await this.Client.DeleteFileAsync(fileId);
         }
@@ -50,13 +53,14 @@ await this.AssistantClient.CreateAssistantAsync(
         async Task InvokeAgentAsync(string input)
         {
             ChatMessageContent message = new(AuthorRole.User, input);
-            chat.AddChatMessage(new(AuthorRole.User, input));
             this.WriteAgentChatMessage(message);
 
-            await foreach (ChatMessageContent response in chat.InvokeAsync(agent))
+            await foreach (AgentResponseItem<ChatMessageContent> response in agent.InvokeAsync(message))
             {
                 this.WriteAgentChatMessage(response);
                 await this.DownloadResponseContentAsync(response);
+
+                agentThread = response.Thread;
             }
         }
     }
diff --git a/dotnet/samples/Concepts/Agents/OpenAIAssistant_FunctionFilters.cs b/dotnet/samples/Concepts/Agents/OpenAIAssistant_FunctionFilters.cs
index a1493025b5a4..39fd09435868 100644
--- a/dotnet/samples/Concepts/Agents/OpenAIAssistant_FunctionFilters.cs
+++ b/dotnet/samples/Concepts/Agents/OpenAIAssistant_FunctionFilters.cs
@@ -62,46 +62,42 @@ public async Task UseAutoFunctionInvocationFilterWithStreamingAgentInvocationAsy
 
     private async Task InvokeAssistantAsync(OpenAIAssistantAgent agent)
     {
-        // Create a thread for the agent conversation.
-        AgentGroupChat chat = new();
+        OpenAIAssistantAgentThread agentThread = new(this.AssistantClient);
 
         try
         {
             // Respond to user input, invoking functions where appropriate.
             ChatMessageContent message = new(AuthorRole.User, "What is the special soup?");
-            chat.AddChatMessage(message);
-            await chat.InvokeAsync(agent).ToArrayAsync();
+            await agent.InvokeAsync(message, agentThread).ToArrayAsync();
 
             // Display the entire chat history.
-            ChatMessageContent[] history = await chat.GetChatMessagesAsync().Reverse().ToArrayAsync();
+            ChatMessageContent[] history = await agentThread.GetMessagesAsync(MessageCollectionOrder.Ascending).ToArrayAsync();
             this.WriteChatHistory(history);
         }
         finally
         {
-            await chat.ResetAsync();
+            await agentThread.DeleteAsync();
             await this.AssistantClient.DeleteAssistantAsync(agent.Id);
         }
     }
 
     private async Task InvokeAssistantStreamingAsync(OpenAIAssistantAgent agent)
     {
-        // Create a thread for the agent conversation.
-        AgentGroupChat chat = new();
+        OpenAIAssistantAgentThread agentThread = new(this.AssistantClient);
 
         try
         {
             // Respond to user input, invoking functions where appropriate.
             ChatMessageContent message = new(AuthorRole.User, "What is the special soup?");
-            chat.AddChatMessage(message);
-            await chat.InvokeStreamingAsync(agent).ToArrayAsync();
+            await agent.InvokeStreamingAsync(message, agentThread).ToArrayAsync();
 
             // Display the entire chat history.
-            ChatMessageContent[] history = await chat.GetChatMessagesAsync().Reverse().ToArrayAsync();
+            ChatMessageContent[] history = await agentThread.GetMessagesAsync(MessageCollectionOrder.Ascending).ToArrayAsync();
             this.WriteChatHistory(history);
         }
         finally
         {
-            await chat.ResetAsync();
+            await agentThread.DeleteAsync();
             await this.AssistantClient.DeleteAssistantAsync(agent.Id);
         }
     }