Hinweis
Für den Zugriff auf diese Seite ist eine Autorisierung erforderlich. Sie können versuchen, sich anzumelden oder das Verzeichnis zu wechseln.
Für den Zugriff auf diese Seite ist eine Autorisierung erforderlich. Sie können versuchen, das Verzeichnis zu wechseln.
Azure KI-Suche versorgt Agenten im Agent Framework mit Inhalten aus einem Suchindex als Grundlage. In Python unterstützt AzureAISearchContextProvider semantisches und agentisches Retrieval. Verbinden Sie in .NET einen Azure KI-Suche Client mit TextSearchProvider.
Diese Integration verwendet das RAG-Muster: Sie ruft relevante externe Inhalte vor dem Modellaufruf ab, ohne diesen Inhalt als Unterhaltungsspeicher zu behandeln.
Azure KI-Suche mit TextSearchProvider verbinden
Erstellen Sie SearchClient, ordnen Sie Suchtreffer TextSearchProvider.TextSearchResult zu und binden Sie den Anbieter über AIContextProviders an.
string projectEndpoint = System.Environment.GetEnvironmentVariable("FOUNDRY_PROJECT_ENDPOINT")
?? throw new InvalidOperationException("FOUNDRY_PROJECT_ENDPOINT is not set.");
string deploymentName = FirstNonBlank(
System.Environment.GetEnvironmentVariable("AZURE_AI_MODEL_DEPLOYMENT_NAME"),
System.Environment.GetEnvironmentVariable("FOUNDRY_MODEL"),
"gpt-4o")!;
string searchEndpoint = FirstNonBlank(System.Environment.GetEnvironmentVariable("AZURE_SEARCH_ENDPOINT"))
?? throw new InvalidOperationException("AZURE_SEARCH_ENDPOINT is not set.");
string searchIndexName = FirstNonBlank(System.Environment.GetEnvironmentVariable("AZURE_SEARCH_INDEX_NAME"))
?? throw new InvalidOperationException("AZURE_SEARCH_INDEX_NAME is not set.");
// WARNING: DefaultAzureCredential is convenient for development but requires careful consideration in production.
// In production, consider using a specific credential (e.g., ManagedIdentityCredential) to avoid
// latency issues, unintended credential probing, and potential security risks from fallback mechanisms.
// Use a chained credential. Try a temporary dev token first (for local Docker debugging),
// then fall back to DefaultAzureCredential (for local dev via dotnet run / managed identity in
// production). The dev credential is scope aware so a single instance serves both Foundry and
// Azure AI Search clients (each Azure SDK client requests a token for its own audience).
var credential = new DefaultAzureCredential();
// Connect to the pre-provisioned search index. The caller is expected to have created the
// index and populated it with documents matching the schema (id / content / sourceName /
// sourceLink) before running this sample. See README.md for an example provisioning script.
var searchClient = new SearchClient(new Uri(searchEndpoint), searchIndexName, credential);
TextSearchProviderOptions textSearchOptions = new()
{
SearchTime = TextSearchProviderOptions.TextSearchBehavior.BeforeAIInvoke,
RecentMessageMemoryLimit = 6,
};
AIAgent agent = new AIProjectClient(new Uri(projectEndpoint), credential)
.AsAIAgent(new ChatClientAgentOptions
{
Name = System.Environment.GetEnvironmentVariable("AGENT_NAME") ?? "hosted-azure-search-rag",
ChatOptions = new ChatOptions
{
ModelId = deploymentName,
Instructions = "You are a helpful support specialist for Contoso Outdoors. " +
"Answer questions using the provided context and cite the source document when available.",
},
AIContextProviders = [new TextSearchProvider(CreateSearchAdapter(searchClient), textSearchOptions)]
});
// Host the agent as a Foundry Hosted Agent using the Responses API.
// the provider will inject into the model context.
static Func<string, CancellationToken, Task<IEnumerable<TextSearchProvider.TextSearchResult>>>
CreateSearchAdapter(SearchClient client, int top = 3) =>
async (query, cancellationToken) =>
{
var options = new SearchOptions { Size = top };
Response<SearchResults<SearchDocument>> response =
await client.SearchAsync<SearchDocument>(query, options, cancellationToken).ConfigureAwait(false);
var results = new List<TextSearchProvider.TextSearchResult>();
await foreach (SearchResult<SearchDocument> hit in response.Value.GetResultsAsync().WithCancellation(cancellationToken).ConfigureAwait(false))
{
results.Add(new TextSearchProvider.TextSearchResult
{
SourceName = hit.Document.TryGetValue("sourceName", out var name) ? name?.ToString() ?? string.Empty : string.Empty,
SourceLink = hit.Document.TryGetValue("sourceLink", out var link) ? link?.ToString() ?? string.Empty : string.Empty,
Text = hit.Document.TryGetValue("content", out var content) ? content?.ToString() ?? string.Empty : string.Empty,
RawRepresentation = hit
});
}
return results;
};
Das Beispiel hostet den daraus resultierenden Agenten in Foundry, aber der Suchadapter funktioniert auch mit einem regulären ChatClientAgent.
Installieren der Pakete
pip install agent-framework-azure-ai-search agent-framework-foundry --pre
Verwenden Sie semantischen Abruf.
Der semantische Modus führt die Suche nach einem vorhandenen Index durch und kann Schlüsselwort- und Vektorabrufe kombinieren.
credential = AzureCliCredential()
# Get configuration from environment
search_endpoint = os.environ["AZURE_SEARCH_ENDPOINT"]
search_key = os.environ.get("AZURE_SEARCH_API_KEY")
index_name = os.environ["AZURE_SEARCH_INDEX_NAME"]
project_endpoint = os.environ["FOUNDRY_PROJECT_ENDPOINT"]
model_deployment = os.environ.get("FOUNDRY_MODEL", "gpt-4o")
openai_endpoint = os.environ.get("AZURE_OPENAI_ENDPOINT")
embedding_deployment = os.environ.get("AZURE_OPENAI_EMBEDDING_MODEL")
embedding_client = None
if openai_endpoint and embedding_deployment:
embedding_client = OpenAIEmbeddingClient(
azure_endpoint=openai_endpoint,
model=embedding_deployment,
credential=credential,
)
# Create Azure AI Search context provider with semantic mode (recommended, fast)
print("Using SEMANTIC mode (hybrid search + semantic ranking, fast)\n")
search_provider = AzureAISearchContextProvider(
source_id="search_provider",
endpoint=search_endpoint,
index_name=index_name,
api_key=search_key, # Use api_key for API key auth, or credential for managed identity
credential=credential if not search_key else None,
mode="semantic", # Default mode
top_k=3, # Retrieve top 3 most relevant documents
embedding_function=embedding_client, # Provide embedding function for hybrid search
vector_field_name="DescriptionVector"
if embedding_client
else None, # Set vector field for hybrid search if using embeddings
)
# Create agent with search context provider
async with (
search_provider,
Agent(
client=FoundryChatClient(
project_endpoint=project_endpoint,
model=model_deployment,
credential=credential,
),
name="SearchAgent",
instructions=(
"You are a helpful assistant. Use the provided context from the "
"knowledge base to answer questions accurately."
),
context_providers=[search_provider],
) as agent,
):
print("=== Azure AI Agent with Search Context (Semantic Mode) ===\n")
for user_input in USER_INPUTS:
print(f"User: {user_input}")
print("Agent: ", end="", flush=True)
# Stream response
async for chunk in agent.run(user_input, stream=True):
if chunk.text:
print(chunk.text, end="", flush=True)
print("\n")
Nutzen Sie den agentischen Abruf
Der Agentenmodus verwendet eine Knowledge Base von Azure KI-Suche für die Abfrageplanung und den mehrstufigen Abruf.
# Agentic mode requires exactly ONE of: knowledge_base_name OR index_name
# Option 1: Use existing Knowledge Base (recommended)
knowledge_base_name = os.environ.get("AZURE_SEARCH_KNOWLEDGE_BASE_NAME")
# Option 2: Auto-create KB from index (requires azure_openai_resource_url)
index_name = os.environ.get("AZURE_SEARCH_INDEX_NAME")
azure_openai_resource_url = os.environ.get("AZURE_OPENAI_RESOURCE_URL")
# Create Azure AI Search context provider with agentic mode (recommended for accuracy)
print("Using AGENTIC mode (Knowledge Bases with query planning, recommended)\n")
print("This mode is slightly slower but provides more accurate results.\n")
# Configure based on whether using existing KB or auto-creating from index
if knowledge_base_name:
# Use existing Knowledge Base - simplest approach
search_provider = AzureAISearchContextProvider(
source_id="search_provider",
endpoint=search_endpoint,
api_key=search_key,
credential=AzureCliCredential() if not search_key else None,
mode="agentic",
knowledge_base_name=knowledge_base_name,
# Optional: Configure retrieval behavior. "answer_synthesis" output mode and
# "medium"/"low" reasoning effort require the preview build of azure-search-documents
# (`pip install --pre azure-search-documents`); the provider auto-detects the build.
knowledge_base_output_mode="extractive_data", # or "answer_synthesis" (preview build only)
retrieval_reasoning_effort="minimal", # or "medium", "low" (preview build only)
)
else:
# Auto-create Knowledge Base from index
if not index_name:
raise ValueError("Set AZURE_SEARCH_KNOWLEDGE_BASE_NAME or AZURE_SEARCH_INDEX_NAME")
if not azure_openai_resource_url:
raise ValueError("AZURE_OPENAI_RESOURCE_URL required when using index_name")
search_provider = AzureAISearchContextProvider(
source_id="search_provider",
endpoint=search_endpoint,
index_name=index_name,
api_key=search_key,
credential=AzureCliCredential() if not search_key else None,
mode="agentic",
azure_openai_resource_url=azure_openai_resource_url,
model=model_deployment,
# Optional: Configure retrieval behavior. "answer_synthesis" output mode and
# "medium"/"low" reasoning effort require the preview build of azure-search-documents
# (`pip install --pre azure-search-documents`); the provider auto-detects the build.
knowledge_base_output_mode="extractive_data", # or "answer_synthesis" (preview build only)
retrieval_reasoning_effort="minimal", # or "medium", "low" (preview build only)
top_k=3,
)
# Create agent with search context provider
async with (
search_provider,
Agent(
client=FoundryChatClient(
project_endpoint=project_endpoint,
model=model_deployment,
credential=AzureCliCredential(),
),
name="SearchAgent",
instructions=(
"You are a helpful assistant with advanced reasoning capabilities. "
"Use the provided context from the knowledge base to answer complex "
"questions that may require synthesizing information from multiple sources."
),
context_providers=[search_provider],
) as agent,
):
print("=== Azure AI Agent with Search Context (Agentic Mode) ===\n")
for user_input in USER_INPUTS:
print(f"User: {user_input}")
print("Agent: ", end="", flush=True)
# Stream response
async for chunk in agent.run(user_input, stream=True):
if chunk.text:
print(chunk.text, end="", flush=True)
for content in chunk.contents:
if content.annotations:
print(f"\n[Sources: {content.annotations}]", end="", flush=True)
print("\n")
Einige agentenbasierte Ausgabe- und Reasoning-Optionen erfordern das Vorschaupaket azure-search-documents.
Weiterleiten der Anruferidentität für den Abruf von Berechtigungen
Festlegen query_source_credential=caller_credential , wenn eine Wissensquelle Berechtigungen auf Dokumentebene und Abrufergebnisse verwendet, müssen für jeden Aufrufer sicherheitskürzungen sein. Übergeben Sie die Synchronisierung oder asynchrone Azure Tokenanmeldeinformationen des angemeldeten Aufrufers getrennt von den Anwendungsanmeldeinformationen, die eine Verbindung mit Azure KI-Suche herstellen.
Für jeden agentischen Abruf fordert der Anbieter ein Token für https://search.azure.com/.default. Er leitet die Microsoft Entra Identität des Aufrufers im x-ms-query-source-authorization Header weiter, sodass Azure KI-Suche die indizierten Berechtigungen erzwingen können.
Für diese Option ist ein Vorschaubuild azure-search-documents , eine Version 12.1.0b1 oder höher innerhalb des unterstützten 12.x-Bereichs erforderlich:
pip install --pre "azure-search-documents>=12.1.0b1,<13"
Das Agent Framework schlägt fehl, wenn das installierte SDK keine Abfragequellautorisierung unterstützt. Es löst eine vor ValueError dem Senden einer Abrufanforderung aus. Tokenerwerbsfehler beenden auch den Abruf; Der Anbieter wird nicht ohne die Identität des Anrufers wiederholt.
Note
Azure KI-Suche verfügt derzeit nicht über eine dedizierte Agent Framework Go-Integration. Implementieren Sie den Abruf als benutzerdefiniertes Tool oder Kontextanbieter, oder lesen Sie das Agent Framework Go-Repository für den neuesten Status.
Produktionsüberlegungen
- Bevorzugen Sie Microsoft Entra Authentifizierung oder verwaltete Identität gegenüber Suchschlüsseln.
- Wenden Sie mandantenbezogene Filter und Indexisolation an.
- Behandeln Sie abgerufene Inhalte als nicht vertrauenswürdig und mindern Sie das Risiko indirekter Prompt-Injection.
- Bewahren Sie Quellmetadaten auf, wenn der Agent Dokumente zitieren soll.