// Copyright (c) Microsoft. All rights reserved. // This sample shows how to use File Search Tool with AI Agents. using Azure.AI.Projects; using Azure.AI.Projects.OpenAI; using Azure.Identity; using Microsoft.Agents.AI; using Microsoft.Extensions.AI; using OpenAI.Assistants; using OpenAI.Files; using OpenAI.Responses; string endpoint = Environment.GetEnvironmentVariable("AZURE_AI_PROJECT_ENDPOINT") ?? throw new InvalidOperationException("AZURE_AI_PROJECT_ENDPOINT is not set."); string deploymentName = Environment.GetEnvironmentVariable("AZURE_AI_MODEL_DEPLOYMENT_NAME") ?? "gpt-4o-mini"; const string AgentInstructions = "You are a helpful assistant that can search through uploaded files to answer questions."; // Get a client to create/retrieve/delete server side agents with Azure Foundry Agents. // 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. AIProjectClient aiProjectClient = new(new Uri(endpoint), new DefaultAzureCredential()); var projectOpenAIClient = aiProjectClient.GetProjectOpenAIClient(); var filesClient = projectOpenAIClient.GetProjectFilesClient(); var vectorStoresClient = projectOpenAIClient.GetProjectVectorStoresClient(); // 1. Create a temp file with test content and upload it. string searchFilePath = Path.Combine(Path.GetTempPath(), Path.GetRandomFileName() + "_lookup.txt"); File.WriteAllText( path: searchFilePath, contents: """ Employee Directory: - Alice Johnson, 28 years old, Software Engineer, Engineering Department - Bob Smith, 35 years old, Sales Manager, Sales Department - Carol Williams, 42 years old, HR Director, Human Resources Department - David Brown, 31 years old, Customer Support Lead, Support Department """ ); Console.WriteLine($"Uploading file: {searchFilePath}"); OpenAIFile uploadedFile = filesClient.UploadFile( filePath: searchFilePath, purpose: FileUploadPurpose.Assistants ); Console.WriteLine($"Uploaded file, file ID: {uploadedFile.Id}"); // 2. Create a vector store with the uploaded file. var vectorStoreResult = await vectorStoresClient.CreateVectorStoreAsync( options: new() { FileIds = { uploadedFile.Id }, Name = "EmployeeDirectory_VectorStore" } ); string vectorStoreId = vectorStoreResult.Value.Id; Console.WriteLine($"Created vector store, vector store ID: {vectorStoreId}"); AIAgent agent = await CreateAgentWithMEAI(); // AIAgent agent = await CreateAgentWithNativeSDK(); // Run the agent Console.WriteLine("\n--- Running File Search Agent ---"); AgentResponse response = await agent.RunAsync("Who is the youngest employee?"); Console.WriteLine($"Response: {response}"); // Getting any file citation annotations generated by the tool foreach (AIAnnotation annotation in response.Messages.SelectMany(m => m.Contents).SelectMany(c => c.Annotations ?? [])) { if (annotation.RawRepresentation is TextAnnotationUpdate citationAnnotation) { Console.WriteLine($$""" File Citation: File Id: {{citationAnnotation.OutputFileId}} Text to Replace: {{citationAnnotation.TextToReplace}} """); } } // Cleanup. Console.WriteLine("\n--- Cleanup ---"); await aiProjectClient.Agents.DeleteAgentAsync(agent.Name); await vectorStoresClient.DeleteVectorStoreAsync(vectorStoreId); await filesClient.DeleteFileAsync(uploadedFile.Id); File.Delete(searchFilePath); Console.WriteLine("Cleanup completed successfully."); // --- Agent Creation Options --- #pragma warning disable CS8321 // Local function is declared but never used // Option 1 - Using HostedFileSearchTool (MEAI + AgentFramework) async Task CreateAgentWithMEAI() { return await aiProjectClient.CreateAIAgentAsync( model: deploymentName, name: "FileSearchAgent-MEAI", instructions: AgentInstructions, tools: [new HostedFileSearchTool() { Inputs = [new HostedVectorStoreContent(vectorStoreId)] }]); } // Option 2 - Using PromptAgentDefinition with ResponseTool.CreateFileSearchTool (Native SDK) async Task CreateAgentWithNativeSDK() { return await aiProjectClient.CreateAIAgentAsync( name: "FileSearchAgent-NATIVE", creationOptions: new AgentVersionCreationOptions( new PromptAgentDefinition(model: deploymentName) { Instructions = AgentInstructions, Tools = { ResponseTool.CreateFileSearchTool(vectorStoreIds: [vectorStoreId]) } }) ); }