Udostępnij przez


Orkiestracja procesów programu Microsoft Agent Framework — przekazanie

Orkiestracja przekazywania umożliwia agentom transferowanie kontroli do siebie na podstawie kontekstu lub żądania użytkownika. Każdy agent może "przekazać" konwersację do innego agenta z odpowiednią wiedzą, zapewniając, że odpowiedni agent obsługuje każdą część zadania. Jest to szczególnie przydatne w przypadku obsługi klienta, systemów ekspertów lub dowolnego scenariusza wymagającego dynamicznego delegowania.

Wewnętrznie orkiestracja przekazywania jest implementowana przy użyciu topologii siatki, w której agenci są połączeni bezpośrednio bez orkiestratora. Każdy agent może zdecydować, kiedy przekazać konwersację na podstawie wstępnie zdefiniowanych reguł lub zawartości wiadomości.

Orkiestracja przekazywania

Uwaga / Notatka

Orkiestracja przekazywania obsługuje tylko Agent, a agenty muszą obsługiwać wykonywanie lokalnych narzędzi.

Różnice między przekazywaniem funkcji i wykorzystaniem agentów jako narzędzi

Chociaż agent jako narzędzie jest powszechnie uważany za wzorzec wieloagentowy i z pozoru może wydawać się podobny do przekazywania, istnieją fundamentalne różnice między nimi:

  • Przepływ sterowania: W koordynacji przekazywania kontrola jest jawnie przekazywana między agentami na podstawie zdefiniowanych reguł. Każdy agent może zdecydować się przekazać całe zadanie innemu agentowi. Nie ma urzędu centralnego zarządzającego przepływem pracy. Natomiast "agent-as-tools" obejmuje agenta podstawowego, który deleguje podzadania do innych agentów, a po zakończeniu zadania przez agenta kontrola powraca do agenta podstawowego.
  • Własność zadania: W przekazaniu agent odbierający przekazanie przejmuje pełną własność zadania. W koncepcji agenta jako narzędzia, agent główny zachowuje ogólną odpowiedzialność za zadanie, podczas gdy inni agenci są traktowani jako narzędzia wspomagające w realizacji określonych podzadań.
  • Zarządzanie kontekstem: W aranżacji przekazywania konwersacja jest całkowicie przekazywana innemu agentowi. Agent odbierający ma pełny kontekst tego, co zostało zrobione do tej pory. W podejściu agenta jako narzędzie, główny agent zarządza ogólnym kontekstem i może dostarczać tylko istotne informacje agentom narzędziowym zgodnie z potrzebami.

Czego nauczysz się

  • Jak utworzyć wyspecjalizowanych agentów dla różnych domen
  • Jak skonfigurować reguły przekazywania między agentami
  • Jak tworzyć interaktywne przepływy pracy przy użyciu dynamicznego routingu agentów
  • Jak obsługiwać konwersacje wieloetapowe z przełączaniem między agentami
  • Jak zaimplementować zatwierdzanie narzędzi dla operacji poufnych (HITL)
  • Jak używać punktowania w trwałych przepływach przekazywania zadań

W orkiestracji przekazywania agenci mogą przekazywać kontrolę między sobą na podstawie kontekstu, co pozwala na dynamiczne routowanie i obsługę przez specjalistów.

Konfigurowanie klienta usługi Azure OpenAI

using System;
using System.Collections.Generic;
using System.Threading.Tasks;
using Azure.AI.OpenAI;
using Azure.Identity;
using Microsoft.Agents.AI.Workflows;
using Microsoft.Extensions.AI;
using Microsoft.Agents.AI;

// 1) Set up the Azure OpenAI client
var endpoint = Environment.GetEnvironmentVariable("AZURE_OPENAI_ENDPOINT") ??
    throw new InvalidOperationException("AZURE_OPENAI_ENDPOINT is not set.");
var deploymentName = Environment.GetEnvironmentVariable("AZURE_OPENAI_DEPLOYMENT_NAME") ?? "gpt-4o-mini";
var client = new AzureOpenAIClient(new Uri(endpoint), new DefaultAzureCredential())
    .GetChatClient(deploymentName)
    .AsIChatClient();

Ostrzeżenie

DefaultAzureCredential jest wygodne do programowania, ale wymaga starannego rozważenia w środowisku produkcyjnym. W środowisku produkcyjnym rozważ użycie określonego poświadczenia (np. ManagedIdentityCredential), aby uniknąć problemów z opóźnieniami, niezamierzonego sondowania poświadczeń i potencjalnych zagrożeń bezpieczeństwa wynikających z mechanizmów awaryjnych.

Definiowanie wyspecjalizowanych agentów

Utwórz agentów specyficznych dla domeny i agenta klasyfikacji na potrzeby routingu:

// 2) Create specialized agents
ChatClientAgent historyTutor = new(client,
    "You provide assistance with historical queries. Explain important events and context clearly. Only respond about history.",
    "history_tutor",
    "Specialist agent for historical questions");

ChatClientAgent mathTutor = new(client,
    "You provide help with math problems. Explain your reasoning at each step and include examples. Only respond about math.",
    "math_tutor",
    "Specialist agent for math questions");

ChatClientAgent triageAgent = new(client,
    "You determine which agent to use based on the user's homework question. ALWAYS handoff to another agent.",
    "triage_agent",
    "Routes messages to the appropriate specialist agent");

Konfigurowanie reguł przekazywania

Określ, którzy agenci mogą przekazać innym agentom:

// 3) Build handoff workflow with routing rules
var workflow = AgentWorkflowBuilder.StartHandoffWith(triageAgent)
    .WithHandoffs(triageAgent, [mathTutor, historyTutor]) // Triage can route to either specialist
    .WithHandoff(mathTutor, triageAgent)                  // Math tutor can return to triage
    .WithHandoff(historyTutor, triageAgent)               // History tutor can return to triage
    .Build();

Uruchom interaktywny przepływ pracy przekazywania zadań

Obsługa rozmów wielotur za pomocą dynamicznego przełączania między agentami:

// 4) Process multi-turn conversations
List<ChatMessage> messages = new();

while (true)
{
    Console.Write("Q: ");
    string userInput = Console.ReadLine()!;
    messages.Add(new(ChatRole.User, userInput));

    // Execute workflow and process events
    StreamingRun run = await InProcessExecution.StreamAsync(workflow, messages);
    await run.TrySendMessageAsync(new TurnToken(emitEvents: true));

    List<ChatMessage> newMessages = new();
    await foreach (WorkflowEvent evt in run.WatchStreamAsync().ConfigureAwait(false))
    {
        if (evt is AgentResponseUpdateEvent e)
        {
            Console.WriteLine($"{e.ExecutorId}: {e.Data}");
        }
        else if (evt is WorkflowOutputEvent outputEvt)
        {
            newMessages = (List<ChatMessage>)outputEvt.Data!;
            break;
        }
    }

    // Add new messages to conversation history
    messages.AddRange(newMessages.Skip(messages.Count));
}

Przykładowa interakcja

Q: What is the derivative of x^2?
triage_agent: This is a math question. I'll hand this off to the math tutor.
math_tutor: The derivative of x^2 is 2x. Using the power rule, we bring down the exponent (2) and multiply it by the coefficient (1), then reduce the exponent by 1: d/dx(x^2) = 2x^(2-1) = 2x.

Q: Tell me about World War 2
triage_agent: This is a history question. I'll hand this off to the history tutor.
history_tutor: World War 2 was a global conflict from 1939 to 1945. It began when Germany invaded Poland and involved most of the world's nations. Key events included the Holocaust, Pearl Harbor attack, D-Day invasion, and ended with atomic bombs on Japan.

Q: Can you help me with calculus integration?
triage_agent: This is another math question. I'll route this to the math tutor.
math_tutor: I'd be happy to help with calculus integration! Integration is the reverse of differentiation. The basic power rule for integration is: ∫x^n dx = x^(n+1)/(n+1) + C, where C is the constant of integration.

Definiowanie kilku narzędzi do pokazu

@tool
def process_refund(order_number: Annotated[str, "Order number to process refund for"]) -> str:
    """Simulated function to process a refund for a given order number."""
    return f"Refund processed successfully for order {order_number}."

@tool
def check_order_status(order_number: Annotated[str, "Order number to check status for"]) -> str:
    """Simulated function to check the status of a given order number."""
    return f"Order {order_number} is currently being processed and will ship in 2 business days."

@tool
def process_return(order_number: Annotated[str, "Order number to process return for"]) -> str:
    """Simulated function to process a return for a given order number."""
    return f"Return initiated successfully for order {order_number}. You will receive return instructions via email."

Konfigurowanie klienta czatu

from agent_framework.azure import AzureOpenAIChatClient
from azure.identity import AzureCliCredential

# Initialize the Azure OpenAI chat client
chat_client = AzureOpenAIChatClient(credential=AzureCliCredential())

Definiowanie wyspecjalizowanych agentów

Utwórz agentów specyficznych dla domeny z koordynatorem routingu:

# Create triage/coordinator agent
triage_agent = chat_client.as_agent(
    instructions=(
        "You are frontline support triage. Route customer issues to the appropriate specialist agents "
        "based on the problem described."
    ),
    description="Triage agent that handles general inquiries.",
    name="triage_agent",
)

# Refund specialist: Handles refund requests
refund_agent = chat_client.as_agent(
    instructions="You process refund requests.",
    description="Agent that handles refund requests.",
    name="refund_agent",
    # In a real application, an agent can have multiple tools; here we keep it simple
    tools=[process_refund],
)

# Order/shipping specialist: Resolves delivery issues
order_agent = chat_client.as_agent(
    instructions="You handle order and shipping inquiries.",
    description="Agent that handles order tracking and shipping issues.",
    name="order_agent",
    # In a real application, an agent can have multiple tools; here we keep it simple
    tools=[check_order_status],
)

# Return specialist: Handles return requests
return_agent = chat_client.as_agent(
    instructions="You manage product return requests.",
    description="Agent that handles return processing.",
    name="return_agent",
    # In a real application, an agent can have multiple tools; here we keep it simple
    tools=[process_return],
)

Konfigurowanie reguł przekazywania

Skompiluj przepływ pracy przekazywania przy użyciu polecenia HandoffBuilder:

from agent_framework.orchestrations import HandoffBuilder

# Build the handoff workflow
workflow = (
    HandoffBuilder(
        name="customer_support_handoff",
        participants=[triage_agent, refund_agent, order_agent, return_agent],
        termination_condition=lambda conversation: len(conversation) > 0 and "welcome" in conversation[-1].text.lower(),
    )
    .with_start_agent(triage_agent) # Triage receives initial user input
    .build()
)

Domyślnie wszyscy agenci mogą przekazywać sobie nawzajem. Aby uzyskać bardziej zaawansowany routing, można skonfigurować przekazywanie połączeń:

workflow = (
    HandoffBuilder(
        name="customer_support_handoff",
        participants=[triage_agent, refund_agent, order_agent, return_agent],
        termination_condition=lambda conversation: len(conversation) > 0 and "welcome" in conversation[-1].text.lower(),
    )
    .with_start_agent(triage_agent) # Triage receives initial user input
    # Triage cannot route directly to refund agent
    .add_handoff(triage_agent, [order_agent, return_agent])
    # Only the return agent can handoff to refund agent - users wanting refunds after returns
    .add_handoff(return_agent, [refund_agent])
    # All specialists can handoff back to triage for further routing
    .add_handoff(order_agent, [triage_agent])
    .add_handoff(return_agent, [triage_agent])
    .add_handoff(refund_agent, [triage_agent])
    .build()
)

Uwaga / Notatka

Nawet w przypadku niestandardowych reguł przekazywania wszystkie moduły pozostają połączone w topologii sieciowej. Jest to spowodowane tym, że agenci muszą współużytkować kontekst ze sobą, aby zachować historię konwersacji (zobacz Synchronizacja kontekstu , aby uzyskać więcej szczegółów). Reguły przekazywania określają zaledwie, którzy agenci mogą następnie przejąć rozmowę.

Uruchom interakcję z agentem przekazywania połączeń

W przeciwieństwie do innych aranżacji przekazywanie jest interaktywne, ponieważ agent może nie zdecydować się przekazać po każdym kolei. Jeśli agent nie przekaże rozmowy, wymagana jest interwencja człowieka, aby kontynuować konwersację. Zobacz Tryb autonomiczny, aby pominąć to wymaganie. W innych aranżacjach po odpowiedzi agenta kontrolka przechodzi do orkiestratora lub następnego agenta.

Gdy agent w przepływie pracy przekazywania zdecyduje się nie przekazać (przekazanie jest wyzwalane przez specjalne wywołanie narzędzia), przepływ pracy emituje WorkflowEvent element z elementem type="request_info" i HandoffAgentUserRequest ładunek zawierający najnowsze komunikaty agenta. Użytkownik musi odpowiedzieć na to żądanie, aby kontynuować przepływ pracy.

from agent_framework import WorkflowEvent
from agent_framework.orchestrations import HandoffAgentUserRequest

# Start workflow with initial user message
events = [event async for event in workflow.run_stream("I need help with my order")]

# Process events and collect pending input requests
pending_requests = []
for event in events:
    if event.type == "request_info" and isinstance(event.data, HandoffAgentUserRequest):
        pending_requests.append(event)
        request_data = event.data
        print(f"Agent {event.executor_id} is awaiting your input")
        # The request contains the most recent messages generated by the
        # agent requesting input
        for msg in request_data.agent_response.messages[-3:]:
            print(f"{msg.author_name}: {msg.text}")

# Interactive loop: respond to requests
while pending_requests:
    user_input = input("You: ")

    # Send responses to all pending requests
    responses = {req.request_id: HandoffAgentUserRequest.create_response(user_input) for req in pending_requests}
    # You can also send a `HandoffAgentUserRequest.terminate()` to end the workflow early
    events = [event async for event in workflow.run(responses=responses)]

    # Process new events
    pending_requests = []
    for event in events:
        # Check for new input requests

Tryb autonomiczny

Orkiestracja handoff jest przeznaczona dla interaktywnych scenariuszy, w których wymagane są dane wejściowe od człowieka, gdy agent zdecyduje, aby nie przekazywać. Jednak jako funkcja eksperymentalna można włączyć "tryb autonomiczny", aby umożliwić kontynuowanie przepływu pracy bez interwencji człowieka. W tym trybie, gdy agent zdecyduje się nie przekazać, proces automatycznie wysyła domyślną odpowiedź (np.User did not respond. Continue assisting autonomously.) do agenta, pozwalając mu kontynuować rozmowę.

Tip

Dlaczego orkiestracja handoff jest z natury interaktywna? W przeciwieństwie do innych orkiestracji, w których istnieje tylko jedna ścieżka do podążania po odpowiedzi agenta (np. z powrotem do orkiestratora lub do następnego agenta), w orkiestracji typu Handoff agent ma możliwość przekazania kolejnego zadania innemu agentowi lub kontynuowania pomocy użytkownikowi. Ponieważ przekazywanie sterowania jest osiągane za pomocą wywołań narzędzi, jeśli agent nie wywołuje narzędzia przekazywania sterowania, ale zamiast tego generuje odpowiedź, przepływ pracy nie będzie wiedział, co zrobić dalej, dlatego zwróci się do użytkownika o dalsze dane wejściowe. Nie można także wymusić, aby agent zawsze przekazywał rozmowę, wymagając od niego użycia narzędzia do przekazywania, ponieważ inaczej agent nie będzie mógł wygenerować znaczących odpowiedzi.

Tryb autonomiczny jest włączony poprzez wywołanie with_autonomous_mode() na HandoffBuilder. Spowoduje to skonfigurowanie przepływu pracy w celu automatycznego odpowiadania na żądania wejściowe przy użyciu komunikatu domyślnego, dzięki czemu agent może kontynuować bez oczekiwania na dane wejściowe przez człowieka.

workflow = (
    HandoffBuilder(
        name="autonomous_customer_support",
        participants=[triage_agent, refund_agent, order_agent, return_agent],
    )
    .with_start_agent(triage_agent)
    .with_autonomous_mode()
    .build()
)

Możesz również włączyć tryb autonomiczny tylko dla podzestawu agentów, przekazując listę wystąpień agentów do with_autonomous_mode().

workflow = (
    HandoffBuilder(
        name="partially_autonomous_support",
        participants=[triage_agent, refund_agent, order_agent, return_agent],
    )
    .with_start_agent(triage_agent)
    .with_autonomous_mode(agents=[triage_agent])  # Only triage_agent runs autonomously
    .build()
)

Możesz dostosować domyślny komunikat odpowiedzi.

workflow = (
    HandoffBuilder(
        name="custom_autonomous_support",
        participants=[triage_agent, refund_agent, order_agent, return_agent],
    )
    .with_start_agent(triage_agent)
    .with_autonomous_mode(
        agents=[triage_agent],
        prompts={triage_agent.name: "Continue with your best judgment as the user is unavailable."},
    )
    .build()
)

Można dostosować liczbę rund, które agent może uruchomić autonomicznie przed koniecznością interakcji z człowiekiem. Może to uniemożliwić uruchamianie przepływu pracy na czas nieokreślony bez udziału użytkownika.

workflow = (
    HandoffBuilder(
        name="limited_autonomous_support",
        participants=[triage_agent, refund_agent, order_agent, return_agent],
    )
    .with_start_agent(triage_agent)
    .with_autonomous_mode(
        agents=[triage_agent],
        turn_limits={triage_agent.name: 3},  # Max 3 autonomous turns
    )
    .build()
)

Zaawansowane: zatwierdzanie narzędzi w przepływach pracy przekazywania

Przepływy pracy przekazywania mogą obejmować agentów z narzędziami, które wymagają zatwierdzenia przez człowieka przed wykonaniem. Jest to przydatne w przypadku poufnych operacji, takich jak przetwarzanie zwrotów, dokonywanie zakupów lub wykonywanie nieodwracalnych akcji.

Definiowanie narzędzi z wymaganym zatwierdzeniem

from typing import Annotated
from agent_framework import tool

@tool(approval_mode="always_require")
def process_refund(order_number: Annotated[str, "Order number to process refund for"]) -> str:
    """Simulated function to process a refund for a given order number."""
    return f"Refund processed successfully for order {order_number}."

Tworzenie agentów za pomocą narzędzi wymagających zatwierdzenia

from agent_framework import Agent
from agent_framework.azure import AzureOpenAIChatClient
from azure.identity import AzureCliCredential

client = AzureOpenAIChatClient(credential=AzureCliCredential())

triage_agent = chat_client.as_agent(
    instructions=(
        "You are frontline support triage. Route customer issues to the appropriate specialist agents "
        "based on the problem described."
    ),
    description="Triage agent that handles general inquiries.",
    name="triage_agent",
)

refund_agent = chat_client.as_agent(
    instructions="You process refund requests.",
    description="Agent that handles refund requests.",
    name="refund_agent",
    tools=[process_refund],
)

order_agent = chat_client.as_agent(
    instructions="You handle order and shipping inquiries.",
    description="Agent that handles order tracking and shipping issues.",
    name="order_agent",
    tools=[check_order_status],
)

Obsługa żądań zatwierdzenia zarówno danych wejściowych użytkownika, jak i narzędzi

from agent_framework import (
    FunctionApprovalRequestContent,
    WorkflowEvent,
)
from agent_framework.orchestrations import HandoffBuilder, HandoffAgentUserRequest

workflow = (
    HandoffBuilder(
        name="support_with_approvals",
        participants=[triage_agent, refund_agent, order_agent],
    )
    .with_start_agent(triage_agent)
    .build()
)

pending_requests: list[WorkflowEvent] = []

# Start workflow
async for event in workflow.run_stream("My order 12345 arrived damaged. I need a refund."):
    if event.type == "request_info":
        pending_requests.append(event)

# Process pending requests - could be user input OR tool approval
while pending_requests:
    responses: dict[str, object] = {}

    for request in pending_requests:
        if isinstance(request.data, HandoffAgentUserRequest):
            # Agent needs user input
            print(f"Agent {request.executor_id} asks:")
            for msg in request.data.agent_response.messages[-2:]:
                print(f"  {msg.author_name}: {msg.text}")

            user_input = input("You: ")
            responses[request.request_id] = HandoffAgentUserRequest.create_response(user_input)

        elif isinstance(request.data, FunctionApprovalRequestContent):
            # Agent wants to call a tool that requires approval
            func_call = request.data.function_call
            args = func_call.parse_arguments() or {}

            print(f"\nTool approval requested: {func_call.name}")
            print(f"Arguments: {args}")

            approval = input("Approve? (y/n): ").strip().lower() == "y"
            responses[request.request_id] = request.data.create_response(approved=approval)

    # Send all responses and collect new requests
    pending_requests = []
    async for event in workflow.run(responses=responses):
        if event.type == "request_info":
            pending_requests.append(event)
        elif event.type == "output":
            print("\nWorkflow completed!")

Z punktami kontrolnymi dla trwałych przepływów pracy

W przypadku długotrwałych przepływów pracy, w których zatwierdzenia narzędzi mogą wystąpić kilka godzin lub dni później, użyj tworzenia punktów kontrolnych:

from agent_framework import FileCheckpointStorage

storage = FileCheckpointStorage(storage_path="./checkpoints")

workflow = (
    HandoffBuilder(
        name="durable_support",
        participants=[triage_agent, refund_agent, order_agent],
        checkpoint_storage=storage,
    )
    .with_start_agent(triage_agent)
    .build()
)

# Initial run - workflow pauses when approval is needed
pending_requests = []
async for event in workflow.run_stream("I need a refund for order 12345"):
    if event.type == "request_info":
        pending_requests.append(event)

# Process can exit here - checkpoint is saved automatically

# Later: Resume from checkpoint and provide approval
checkpoints = await storage.list_checkpoints()
latest = sorted(checkpoints, key=lambda c: c.timestamp, reverse=True)[0]

# Step 1: Restore checkpoint to reload pending requests
restored_requests = []
async for event in workflow.run_stream(checkpoint_id=latest.checkpoint_id):
    if event.type == "request_info":
        restored_requests.append(event)

# Step 2: Send responses
responses = {}
for req in restored_requests:
    if isinstance(req.data, FunctionApprovalRequestContent):
        responses[req.request_id] = req.data.create_response(approved=True)
    elif isinstance(req.data, HandoffAgentUserRequest):
        responses[req.request_id] = HandoffAgentUserRequest.create_response("Yes, please process the refund.")

async for event in workflow.run(responses=responses):
    if event.type == "output":
        print("Refund workflow completed!")

Przykładowa interakcja

User: I need help with my order

triage_agent: I'd be happy to help you with your order. Could you please provide more details about the issue?

User: My order 1234 arrived damaged

triage_agent: I'm sorry to hear that your order arrived damaged. I will connect you with a specialist.

support_agent: I'm sorry about the damaged order. To assist you better, could you please:
- Describe the damage
- Would you prefer a replacement or refund?

User: I'd like a refund

triage_agent: I'll connect you with the refund specialist.

refund_agent: I'll process your refund for order 1234. Here's what will happen next:
1. Verification of the damaged items
2. Refund request submission
3. Return instructions if needed
4. Refund processing within 5-10 business days

Could you provide photos of the damage to expedite the process?

Synchronizacja kontekstu

Agenci w programie Agent Framework korzystają z sesji agentów (AgentSession) do zarządzania kontekstem. W orkiestracji Handoff agenci nie współużytkują tego samego wystąpienia sesji, uczestnicy są odpowiedzialni za zapewnienie spójności kontekstu. Aby to osiągnąć, uczestnicy są zaprojektowani do transmitowania odpowiedzi lub danych wejściowych użytkownika odebranych do wszystkich innych uczestników w przepływie pracy za każdym razem, gdy wygenerują odpowiedź, upewniając się, że wszyscy uczestnicy mają najnowszy kontekst na kolejną turę.

Synchronizacja kontekstu przekazywania

Uwaga / Notatka

Zawartość związana z narzędziami, w tym wywołania przekazywania narzędzi, nie jest udostępniana innym agentom. Tylko komunikaty użytkowników i agentów są synchronizowane między wszystkimi uczestnikami.

Tip

Agenci nie współdzielą tego samego wystąpienia sesji, ponieważ różne typy agentów mogą mieć odmienne implementacje AgentSession abstrakcji. Udostępnianie tego samego wystąpienia sesji może prowadzić do niespójności w sposobie, w jaki każdy agent przetwarza i utrzymuje kontekst.

Po rozgłaszaniu odpowiedzi uczestnik sprawdza, czy musi przekazać konwersację innemu agentowi. Jeśli tak, wysyła żądanie do wybranego agenta, aby przejąć konwersację. W przeciwnym razie żąda danych wejściowych użytkownika lub kontynuuje autonomicznie na podstawie konfiguracji przepływu pracy.

Kluczowe pojęcia

  • Routing dynamiczny: agenci mogą zdecydować, który agent powinien obsługiwać następną interakcję na podstawie kontekstu
  • AgentWorkflowBuilder.StartHandoffWith(): Definiuje początkowego agenta uruchamiającego przepływ pracy
  • WithHandoff() i WithHandoffs(): konfiguruje reguły przekazywania między określonymi agentami
  • Zachowywanie kontekstu: pełna historia konwersacji jest utrzymywana we wszystkich przekazywaniach
  • Obsługa konwersacji z wielokrotnymi etapami: wspiera ciągłe rozmowy z płynnym przełączaniem agentów
  • Specjalistyczna ekspertyza: Każdy agent koncentruje się na swojej dziedzinie, podczas współpracy przy przekazywaniu zadań
  • Routing dynamiczny: agenci mogą zdecydować, który agent powinien obsługiwać następną interakcję na podstawie kontekstu
  • HandoffBuilder: tworzy przepływy pracy z automatyczną rejestracją narzędzia przekazywania
  • with_start_agent(): definiuje, który agent najpierw odbiera dane wejściowe użytkownika
  • add_handoff(): Konfiguruje określone relacje przekazywania między agentami
  • Zachowywanie kontekstu: pełna historia konwersacji jest utrzymywana we wszystkich przekazywaniach
  • Cykl żądań/odpowiedzi: Przepływ pracy żąda danych wejściowych użytkownika, przetwarza odpowiedzi i kontynuuje do momentu spełnienia warunku zakończenia
  • Zatwierdzanie narzędzi: służy @tool(approval_mode="always_require") do obsługi operacji poufnych, które wymagają zatwierdzenia przez człowieka
  • FunctionApprovalRequestContent: wydawany, gdy agent wywołuje narzędzie wymagające zatwierdzenia; użyj create_response(approved=...) aby odpowiedzieć
  • Tworzenie punktów kontrolnych: służy with_checkpointing() do trwałych przepływów pracy, które mogą być wstrzymywane i wznawiane po ponownym uruchomieniu procesów
  • Specjalistyczna ekspertyza: Każdy agent koncentruje się na swojej dziedzinie, podczas współpracy przy przekazywaniu zadań

Dalsze kroki