openai/openai-dotnet

Public

mirrored from https://github.com/openai/openai-dotnetAvailable

CodeCommitsIssuesPull requestsActionsInsightsSecurity
OpenAI_2.2.0-beta.2

Branches

Tags

  • No tags available.
0Branches0Tags
Go to file
Add file
Code

Clone

HTTPS

Download ZIP

src/Custom/Embeddings/EmbeddingClient.cs

266lines · modeblame

9f9f2936Jose Arriaga Maldonado2 years ago1using System;
2using System.ClientModel;
3using System.ClientModel.Primitives;
4using System.Collections.Generic;
0e0c460cJose Arriaga Maldonado1 years ago5using System.IO;
9f9f2936Jose Arriaga Maldonado2 years ago6using System.Linq;
0e0c460cJose Arriaga Maldonado1 years ago7using System.Text.Json;
19a65a0aKrzysztof Cwalina2 years ago8using System.Threading;
9f9f2936Jose Arriaga Maldonado2 years ago9using System.Threading.Tasks;
10
11namespace OpenAI.Embeddings;
12
13a9c686Jose Arriaga Maldonado1 years ago13// CUSTOM:
14// - Renamed.
15// - Suppressed constructor that takes endpoint parameter; endpoint is now a property in the options class.
16// - Suppressed methods that only take the options parameter.
17/// <summary> The service client for OpenAI embedding operations. </summary>
9f9f2936Jose Arriaga Maldonado2 years ago18[CodeGenClient("Embeddings")]
19[CodeGenSuppress("EmbeddingClient", typeof(ClientPipeline), typeof(ApiKeyCredential), typeof(Uri))]
e0fee603Jose Arriaga Maldonado1 years ago20[CodeGenSuppress("CreateEmbeddingAsync", typeof(EmbeddingGenerationOptions), typeof(CancellationToken))]
21[CodeGenSuppress("CreateEmbedding", typeof(EmbeddingGenerationOptions), typeof(CancellationToken))]
9f9f2936Jose Arriaga Maldonado2 years ago22public partial class EmbeddingClient
23{
24private readonly string _model;
25
2ab1a942Jose Arriaga Maldonado1 years ago26// CUSTOM: Added as a convenience.
e0fee603Jose Arriaga Maldonado1 years ago27/// <summary> Initializes a new instance of <see cref="EmbeddingClient"/>. </summary>
2ab1a942Jose Arriaga Maldonado1 years ago28/// <param name="model"> The name of the model to use in requests sent to the service. To learn more about the available models, see <see href="https://platform.openai.com/docs/models"/>. </param>
29/// <param name="apiKey"> The API key to authenticate with the service. </param>
30/// <exception cref="ArgumentNullException"> <paramref name="model"/> or <paramref name="apiKey"/> is null. </exception>
31/// <exception cref="ArgumentException"> <paramref name="model"/> is an empty string, and was expected to be non-empty. </exception>
32public EmbeddingClient(string model, string apiKey) : this(model, new ApiKeyCredential(apiKey), new OpenAIClientOptions())
33{
34}
35
9f9f2936Jose Arriaga Maldonado2 years ago36// CUSTOM:
37// - Added `model` parameter.
13a9c686Jose Arriaga Maldonado1 years ago38// - Used a custom pipeline.
39// - Demoted the endpoint parameter to be a property in the options class.
e0fee603Jose Arriaga Maldonado1 years ago40/// <summary> Initializes a new instance of <see cref="EmbeddingClient"/>. </summary>
13a9c686Jose Arriaga Maldonado1 years ago41/// <param name="model"> The name of the model to use in requests sent to the service. To learn more about the available models, see <see href="https://platform.openai.com/docs/models"/>. </param>
42/// <param name="credential"> The API key to authenticate with the service. </param>
43/// <exception cref="ArgumentNullException"> <paramref name="model"/> or <paramref name="credential"/> is null. </exception>
44/// <exception cref="ArgumentException"> <paramref name="model"/> is an empty string, and was expected to be non-empty. </exception>
45public EmbeddingClient(string model, ApiKeyCredential credential) : this(model, credential, new OpenAIClientOptions())
46{
47}
9f9f2936Jose Arriaga Maldonado2 years ago48
49// CUSTOM:
50// - Added `model` parameter.
13a9c686Jose Arriaga Maldonado1 years ago51// - Used a custom pipeline.
52// - Demoted the endpoint parameter to be a property in the options class.
e0fee603Jose Arriaga Maldonado1 years ago53/// <summary> Initializes a new instance of <see cref="EmbeddingClient"/>. </summary>
13a9c686Jose Arriaga Maldonado1 years ago54/// <param name="model"> The name of the model to use in requests sent to the service. To learn more about the available models, see <see href="https://platform.openai.com/docs/models"/>. </param>
55/// <param name="credential"> The API key to authenticate with the service. </param>
56/// <param name="options"> The options to configure the client. </param>
57/// <exception cref="ArgumentNullException"> <paramref name="model"/> or <paramref name="credential"/> is null. </exception>
58/// <exception cref="ArgumentException"> <paramref name="model"/> is an empty string, and was expected to be non-empty. </exception>
59public EmbeddingClient(string model, ApiKeyCredential credential, OpenAIClientOptions options)
60{
61Argument.AssertNotNullOrEmpty(model, nameof(model));
62Argument.AssertNotNull(credential, nameof(credential));
63options ??= new OpenAIClientOptions();
9f9f2936Jose Arriaga Maldonado2 years ago64
13a9c686Jose Arriaga Maldonado1 years ago65_model = model;
e0fee603Jose Arriaga Maldonado1 years ago66Pipeline = OpenAIClient.CreatePipeline(credential, options);
13a9c686Jose Arriaga Maldonado1 years ago67_endpoint = OpenAIClient.GetEndpoint(options);
68}
69
70// CUSTOM:
71// - Added `model` parameter.
72// - Used a custom pipeline.
73// - Demoted the endpoint parameter to be a property in the options class.
74// - Made protected.
e0fee603Jose Arriaga Maldonado1 years ago75/// <summary> Initializes a new instance of <see cref="EmbeddingClient"/>. </summary>
13a9c686Jose Arriaga Maldonado1 years ago76/// <param name="pipeline"> The HTTP pipeline to send and receive REST requests and responses. </param>
77/// <param name="model"> The name of the model to use in requests sent to the service. To learn more about the available models, see <see href="https://platform.openai.com/docs/models"/>. </param>
78/// <param name="options"> The options to configure the client. </param>
79/// <exception cref="ArgumentNullException"> <paramref name="pipeline"/> or <paramref name="model"/> is null. </exception>
80/// <exception cref="ArgumentException"> <paramref name="model"/> is an empty string, and was expected to be non-empty. </exception>
81protected internal EmbeddingClient(ClientPipeline pipeline, string model, OpenAIClientOptions options)
9f9f2936Jose Arriaga Maldonado2 years ago82{
13a9c686Jose Arriaga Maldonado1 years ago83Argument.AssertNotNull(pipeline, nameof(pipeline));
9f9f2936Jose Arriaga Maldonado2 years ago84Argument.AssertNotNullOrEmpty(model, nameof(model));
13a9c686Jose Arriaga Maldonado1 years ago85options ??= new OpenAIClientOptions();
9f9f2936Jose Arriaga Maldonado2 years ago86
87_model = model;
e0fee603Jose Arriaga Maldonado1 years ago88Pipeline = pipeline;
13a9c686Jose Arriaga Maldonado1 years ago89_endpoint = OpenAIClient.GetEndpoint(options);
9f9f2936Jose Arriaga Maldonado2 years ago90}
91
92// CUSTOM: Added to simplify generating a single embedding from a string input.
13a9c686Jose Arriaga Maldonado1 years ago93/// <summary> Generates an embedding representing the text input. </summary>
94/// <param name="input"> The text input to generate an embedding for. </param>
95/// <param name="options"> The options to configure the embedding generation. </param>
96/// <param name="cancellationToken"> A token that can be used to cancel this method call. </param>
9f9f2936Jose Arriaga Maldonado2 years ago97/// <exception cref="ArgumentNullException"> <paramref name="input"/> is null. </exception>
98/// <exception cref="ArgumentException"> <paramref name="input"/> is an empty string, and was expected to be non-empty. </exception>
19ceae44ShivangiReja1 years ago99public virtual async Task<ClientResult<OpenAIEmbedding>> GenerateEmbeddingAsync(string input, EmbeddingGenerationOptions options = null, CancellationToken cancellationToken = default)
9f9f2936Jose Arriaga Maldonado2 years ago100{
101Argument.AssertNotNullOrEmpty(input, nameof(input));
102
103options ??= new();
0e0c460cJose Arriaga Maldonado1 years ago104CreateEmbeddingGenerationOptions(input, ref options);
9f9f2936Jose Arriaga Maldonado2 years ago105
e0fee603Jose Arriaga Maldonado1 years ago106using BinaryContent content = options;
19a65a0aKrzysztof Cwalina2 years ago107ClientResult result = await GenerateEmbeddingsAsync(content, cancellationToken.ToRequestOptions()).ConfigureAwait(false);
e0fee603Jose Arriaga Maldonado1 years ago108return ClientResult.FromValue(((OpenAIEmbeddingCollection)result).FirstOrDefault(), result.GetRawResponse());
9f9f2936Jose Arriaga Maldonado2 years ago109}
110
111// CUSTOM: Added to simplify generating a single embedding from a string input.
13a9c686Jose Arriaga Maldonado1 years ago112/// <summary> Generates an embedding representing the text input. </summary>
113/// <param name="input"> The text input to generate an embedding for. </param>
114/// <param name="options"> The options to configure the embedding generation. </param>
115/// <param name="cancellationToken"> A token that can be used to cancel this method call. </param>
9f9f2936Jose Arriaga Maldonado2 years ago116/// <exception cref="ArgumentNullException"> <paramref name="input"/> is null. </exception>
117/// <exception cref="ArgumentException"> <paramref name="input"/> is an empty string, and was expected to be non-empty. </exception>
19ceae44ShivangiReja1 years ago118public virtual ClientResult<OpenAIEmbedding> GenerateEmbedding(string input, EmbeddingGenerationOptions options = null, CancellationToken cancellationToken = default)
9f9f2936Jose Arriaga Maldonado2 years ago119{
120Argument.AssertNotNullOrEmpty(input, nameof(input));
121
122options ??= new();
0e0c460cJose Arriaga Maldonado1 years ago123CreateEmbeddingGenerationOptions(input, ref options);
9f9f2936Jose Arriaga Maldonado2 years ago124
e0fee603Jose Arriaga Maldonado1 years ago125using BinaryContent content = options;
19a65a0aKrzysztof Cwalina2 years ago126ClientResult result = GenerateEmbeddings(content, cancellationToken.ToRequestOptions());
e0fee603Jose Arriaga Maldonado1 years ago127return ClientResult.FromValue(((OpenAIEmbeddingCollection)result).FirstOrDefault(), result.GetRawResponse());
9f9f2936Jose Arriaga Maldonado2 years ago128}
129
130// CUSTOM: Added to simplify passing the input as a collection of strings instead of BinaryData.
13a9c686Jose Arriaga Maldonado1 years ago131/// <summary> Generates embeddings representing the text inputs. </summary>
132/// <param name="inputs"> The text inputs to generate embeddings for. </param>
133/// <param name="options"> The options to configure the embedding generation. </param>
134/// <param name="cancellationToken"> A token that can be used to cancel this method call. </param>
9f9f2936Jose Arriaga Maldonado2 years ago135/// <exception cref="ArgumentNullException"> <paramref name="inputs"/> is null. </exception>
136/// <exception cref="ArgumentException"> <paramref name="inputs"/> is an empty collection, and was expected to be non-empty. </exception>
19ceae44ShivangiReja1 years ago137public virtual async Task<ClientResult<OpenAIEmbeddingCollection>> GenerateEmbeddingsAsync(IEnumerable<string> inputs, EmbeddingGenerationOptions options = null, CancellationToken cancellationToken = default)
9f9f2936Jose Arriaga Maldonado2 years ago138{
139Argument.AssertNotNullOrEmpty(inputs, nameof(inputs));
140
141options ??= new();
0e0c460cJose Arriaga Maldonado1 years ago142CreateEmbeddingGenerationOptions(inputs, ref options);
9f9f2936Jose Arriaga Maldonado2 years ago143
e0fee603Jose Arriaga Maldonado1 years ago144using BinaryContent content = options;
19a65a0aKrzysztof Cwalina2 years ago145ClientResult result = await GenerateEmbeddingsAsync(content, cancellationToken.ToRequestOptions()).ConfigureAwait(false);
e0fee603Jose Arriaga Maldonado1 years ago146return ClientResult.FromValue((OpenAIEmbeddingCollection)result, result.GetRawResponse());
9f9f2936Jose Arriaga Maldonado2 years ago147
148}
149
150// CUSTOM: Added to simplify passing the input as a collection of strings instead of BinaryData.
13a9c686Jose Arriaga Maldonado1 years ago151/// <summary> Generates embeddings representing the text inputs. </summary>
152/// <param name="inputs"> The text inputs to generate embeddings for. </param>
153/// <param name="options"> The options to configure the embedding generation. </param>
154/// <param name="cancellationToken"> A token that can be used to cancel this method call. </param>
9f9f2936Jose Arriaga Maldonado2 years ago155/// <exception cref="ArgumentNullException"> <paramref name="inputs"/> is null. </exception>
156/// <exception cref="ArgumentException"> <paramref name="inputs"/> is an empty collection, and was expected to be non-empty. </exception>
19ceae44ShivangiReja1 years ago157public virtual ClientResult<OpenAIEmbeddingCollection> GenerateEmbeddings(IEnumerable<string> inputs, EmbeddingGenerationOptions options = null, CancellationToken cancellationToken = default)
9f9f2936Jose Arriaga Maldonado2 years ago158{
159Argument.AssertNotNullOrEmpty(inputs, nameof(inputs));
160
161options ??= new();
0e0c460cJose Arriaga Maldonado1 years ago162CreateEmbeddingGenerationOptions(inputs, ref options);
9f9f2936Jose Arriaga Maldonado2 years ago163
e0fee603Jose Arriaga Maldonado1 years ago164using BinaryContent content = options;
19a65a0aKrzysztof Cwalina2 years ago165ClientResult result = GenerateEmbeddings(content, cancellationToken.ToRequestOptions());
e0fee603Jose Arriaga Maldonado1 years ago166return ClientResult.FromValue((OpenAIEmbeddingCollection)result, result.GetRawResponse());
9f9f2936Jose Arriaga Maldonado2 years ago167}
168
a330c2e7Jose Arriaga Maldonado1 years ago169// CUSTOM: Added to simplify passing the input as a collection of ReadOnlyMemory tokens instead of BinaryData.
0e0c460cJose Arriaga Maldonado1 years ago170/// <summary> Generates embeddings representing the tokenized text inputs. </summary>
171/// <param name="inputs"> The tokenized text inputs to generate embeddings for. </param>
13a9c686Jose Arriaga Maldonado1 years ago172/// <param name="options"> The options to configure the embedding generation. </param>
173/// <param name="cancellationToken"> A token that can be used to cancel this method call. </param>
9f9f2936Jose Arriaga Maldonado2 years ago174/// <exception cref="ArgumentNullException"> <paramref name="inputs"/> is null. </exception>
175/// <exception cref="ArgumentException"> <paramref name="inputs"/> is an empty collection, and was expected to be non-empty. </exception>
a330c2e7Jose Arriaga Maldonado1 years ago176public virtual async Task<ClientResult<OpenAIEmbeddingCollection>> GenerateEmbeddingsAsync(IEnumerable<ReadOnlyMemory<int>> inputs, EmbeddingGenerationOptions options = null, CancellationToken cancellationToken = default)
9f9f2936Jose Arriaga Maldonado2 years ago177{
178Argument.AssertNotNullOrEmpty(inputs, nameof(inputs));
179
180options ??= new();
0e0c460cJose Arriaga Maldonado1 years ago181CreateEmbeddingGenerationOptions(inputs, ref options);
9f9f2936Jose Arriaga Maldonado2 years ago182
e0fee603Jose Arriaga Maldonado1 years ago183using BinaryContent content = options;
19a65a0aKrzysztof Cwalina2 years ago184ClientResult result = await GenerateEmbeddingsAsync(content, cancellationToken.ToRequestOptions()).ConfigureAwait(false);
e0fee603Jose Arriaga Maldonado1 years ago185return ClientResult.FromValue((OpenAIEmbeddingCollection)result, result.GetRawResponse());
9f9f2936Jose Arriaga Maldonado2 years ago186}
187
a330c2e7Jose Arriaga Maldonado1 years ago188// CUSTOM: Added to simplify passing the input as a collection of ReadOnlyMemory of tokens instead of BinaryData.
0e0c460cJose Arriaga Maldonado1 years ago189/// <summary> Generates embeddings representing the tokenized text inputs. </summary>
190/// <param name="inputs"> The tokenized text inputs to generate embeddings for. </param>
13a9c686Jose Arriaga Maldonado1 years ago191/// <param name="options"> The options to configure the embedding generation. </param>
192/// <param name="cancellationToken"> A token that can be used to cancel this method call. </param>
9f9f2936Jose Arriaga Maldonado2 years ago193/// <exception cref="ArgumentNullException"> <paramref name="inputs"/> is null. </exception>
194/// <exception cref="ArgumentException"> <paramref name="inputs"/> is an empty collection, and was expected to be non-empty. </exception>
a330c2e7Jose Arriaga Maldonado1 years ago195public virtual ClientResult<OpenAIEmbeddingCollection> GenerateEmbeddings(IEnumerable<ReadOnlyMemory<int>> inputs, EmbeddingGenerationOptions options = null, CancellationToken cancellationToken = default)
9f9f2936Jose Arriaga Maldonado2 years ago196{
197Argument.AssertNotNullOrEmpty(inputs, nameof(inputs));
198
199options ??= new();
0e0c460cJose Arriaga Maldonado1 years ago200CreateEmbeddingGenerationOptions(inputs, ref options);
9f9f2936Jose Arriaga Maldonado2 years ago201
e0fee603Jose Arriaga Maldonado1 years ago202using BinaryContent content = options;
19a65a0aKrzysztof Cwalina2 years ago203ClientResult result = GenerateEmbeddings(content, cancellationToken.ToRequestOptions());
e0fee603Jose Arriaga Maldonado1 years ago204return ClientResult.FromValue((OpenAIEmbeddingCollection)result, result.GetRawResponse());
9f9f2936Jose Arriaga Maldonado2 years ago205}
206
0e0c460cJose Arriaga Maldonado1 years ago207private void CreateEmbeddingGenerationOptions(string input, ref EmbeddingGenerationOptions options)
208{
209using MemoryStream stream = new();
210using Utf8JsonWriter writer = new(stream);
211
212writer.WriteStringValue(input);
213writer.Flush();
214
215options.Input = BinaryData.FromBytes(stream.ToArray());
216options.Model = _model;
217options.EncodingFormat = InternalCreateEmbeddingRequestEncodingFormat.Base64;
218}
219
220private void CreateEmbeddingGenerationOptions(IEnumerable<string> inputs, ref EmbeddingGenerationOptions options)
221{
222using MemoryStream stream = new();
223using Utf8JsonWriter writer = new(stream);
224
225writer.WriteStartArray();
226
227foreach (string input in inputs)
228{
229writer.WriteStringValue(input);
230}
231
232writer.WriteEndArray();
233writer.Flush();
234
235options.Input = BinaryData.FromBytes(stream.ToArray());
236options.Model = _model;
237options.EncodingFormat = InternalCreateEmbeddingRequestEncodingFormat.Base64;
238}
239
240private void CreateEmbeddingGenerationOptions(IEnumerable<ReadOnlyMemory<int>> inputs, ref EmbeddingGenerationOptions options)
9f9f2936Jose Arriaga Maldonado2 years ago241{
0e0c460cJose Arriaga Maldonado1 years ago242using MemoryStream stream = new();
243using Utf8JsonWriter writer = new(stream);
244
245writer.WriteStartArray();
246
247foreach (ReadOnlyMemory<int> input in inputs)
248{
249writer.WriteStartArray();
250
251foreach (int tokenId in input.ToArray())
252{
253writer.WriteNumberValue(tokenId);
254}
255
256writer.WriteEndArray();
257}
258
259writer.WriteEndArray();
260writer.Flush();
261
262options.Input = BinaryData.FromBytes(stream.ToArray());
9f9f2936Jose Arriaga Maldonado2 years ago263options.Model = _model;
0c0bc808Jose Arriaga Maldonado2 years ago264options.EncodingFormat = InternalCreateEmbeddingRequestEncodingFormat.Base64;
9f9f2936Jose Arriaga Maldonado2 years ago265}
266}