// TEMPLATE: EmbeddingService.cs // PURPOSE: Generates embeddings for RAG indexing and query, via IEmbeddingGenerator. // READS STANDARD: ai-agents-rag-custom-pgvector // PLACEHOLDERS: // {{PROJECT_NAMESPACE}} — root namespace of the project (e.g., MyProject) // LAST-VERIFIED: 2026-05-19 // // IMPORTANT — IEmbeddingGenerator registration (in Program.cs of the project): // The project must register IEmbeddingGenerator> in DI. // Example for OpenAI text-embedding-3-small (the canonical "embeddings" alias): // // builder.Services.AddSingleton>>(sp => // { // var cfg = sp.GetRequiredService(); // return new OpenAIClient(cfg["OpenAI:ApiKey"]!) // .GetEmbeddingClient("text-embedding-3-small") // .AsIEmbeddingGenerator(); // }); // // For other providers (Google, Anthropic, Ollama) adapt the client construction — // see ai-agents-providers-model-registry §providers for verified SDKs. using Microsoft.Extensions.AI; namespace {{PROJECT_NAMESPACE}}.AI; /// /// Generates text embeddings for RAG indexing and query. /// Wraps so the rest of the project /// does not take a direct dependency on the underlying provider SDK. /// public sealed class EmbeddingService(IEmbeddingGenerator> generator) { /// /// Generates an embedding vector for a single text (used at query time). /// /// The text to embed. /// Cancellation token. /// The embedding vector as of float. public async Task> EmbedAsync( string text, CancellationToken ct = default) { // GenerateAsync is the verified API: returns GeneratedEmbeddings>. // Each Embedding.Vector is a ReadOnlyMemory. // Source: Microsoft Learn — microsoft-extensions-ai (verified 2026-05-19). GeneratedEmbeddings> result = await generator.GenerateAsync([text], cancellationToken: ct); return result[0].Vector; } /// /// Generates embedding vectors for a batch of texts (used during document indexing). /// /// The texts to embed. /// Cancellation token. /// Embedding vectors in the same order as the input texts. public async Task>> EmbedBatchAsync( IReadOnlyList texts, CancellationToken ct = default) { GeneratedEmbeddings> result = await generator.GenerateAsync(texts, cancellationToken: ct); return [.. result.Select(e => e.Vector)]; } }