Skip to content

[dotnet-code] Simplify group chat dispatch internals #841

Description

@github-actions

Summary

Extracted the GroupChat host's next-agent selection and turn-token dispatch into an unexported dispatchNextAgent helper. This keeps the existing behavior intact while making the Go host structure closer to the .NET GroupChatHost flow, where history update, broadcast, selection, dispatch, and completion are separated into focused steps.

.NET Reference

  • dotnet/src/Microsoft.Agents.AI.Workflows/Specialized/GroupChatHost.cs - separates the group chat host turn flow into broadcast and completion helpers around the manager's next-agent selection and dispatch path.

Public API and Behavior

No public Go API changed. No intentional behavior change was made.

Tests

  • go test ./workflow/agentworkflow

Notes

Rejected sampled candidates:

  • dotnet/src/Microsoft.Agents.AI.Workflows/Specialized/HandoffStartExecutor.cs - no corresponding Go handoff workflow implementation was found in this checkout.
  • dotnet/src/Microsoft.Agents.AI.Workflows/Checkpointing/EdgeIdConverter.cs - the EdgeId dictionary-key converter pattern is .NET-specific; the Go workflow JSON paths use different marshal/unmarshal shapes.
  • dotnet/src/Microsoft.Agents.AI.Workflows.Declarative/ObjectModel/AddConversationMessageExecutor.cs - no narrow corresponding Go declarative executor surface was found for a safe production-code cleanup.

Open [dotnet-code] PRs checked before editing; none targeted GroupChat.

Generated by .NET-to-Go Code Portability Refactoring Agent · gpt55 · 80.9 AIC · ⌖ 17.6 AIC · ⊞ 23.2K ·


Note

This was originally intended as a pull request, but GitHub Actions is not permitted to create or approve pull requests in this repository.
The changes have been pushed to branch dotnet-code/groupchat-dispatch-helper-20260813223626-6a78effab0551cae.

Click here to create the pull request

To fix the permissions issue, go to SettingsActionsGeneral and enable Allow GitHub Actions to create and approve pull requests. See also: gh-aw FAQ

Show patch (58 lines)
From a97acca93bc321a9b2a787068386dbf297ee80a5 Mon Sep 17 00:00:00 2001
From: "github-actions[bot]" <github-actions[bot]@users.noreply.github.com>
Date: Thu, 13 Aug 2026 22:36:26 +0000
Subject: [PATCH] Simplify group chat dispatch internals

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
---
 workflow/agentworkflow/groupchat.go | 19 +++++++++++++++----
 1 file changed, 15 insertions(+), 4 deletions(-)

diff --git a/workflow/agentworkflow/groupchat.go b/workflow/agentworkflow/groupchat.go
index e2d2eb4d2..1a8fc471b 100644
--- a/workflow/agentworkflow/groupchat.go
+++ b/workflow/agentworkflow/groupchat.go
@@ -346,24 +346,35 @@ func (host *groupChatHostExecutor) handleTurn(ctx *workflow.Context, token workf
 		}
 	}
 
-	nextAgent, err := manager.SelectNextAgent(ctx, host.history)
+	dispatched, err := host.dispatchNextAgent(ctx, token, manager)
 	if err != nil {
 		return err
 	}
+	if dispatched {
+		return nil
+	}
+	return host.complete(ctx)
+}
+
+func (host *groupChatHostExecutor) dispatchNextAgent(ctx *workflow.Context, token workflow.TurnToken, manager *GroupChatManager) (bool, error) {
+	nextAgent, err := manager.SelectNextAgent(ctx, host.history)
+	if err != nil {
+		return false, err
+	}
 	if nextAgent == nil {
-		return host.complete(ctx)
+		return false, nil
 	}
 	nextBinding, ok := host.bindingForAgent(nextAgent)
 	if !ok {
 		// Selecting an agent that is not a participant ends the chat and
 		// yields the accumulated conversation, matching .NET GroupChatHost
 		// falling through to CompleteAsync on a lookup miss.
-		return host.complete(ctx)
+		return false, nil
 	}
 
 	host.iterationCount++
 	host.currentSpeakerExecutorID = nextBinding.ID
-	return ctx.SendMessage(nextBinding.ID, token)
+	return true, ctx.SendMessage(nextBinding.ID, token)
 }
 
 func (host *groupChatHostExecutor) shouldTerminate(ctx context.Context, manager *GroupChatManager) (bool, error) {
-- 
2.54.0

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions