1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
use crate::error::LingerError;
use crate::RequestId;
use serde::{Deserialize, Serialize};
use serde_json::Value;
use std::collections::BTreeMap;
/// EN: Request body for `POST /v1/embeddings`.
/// 中文:`POST /v1/embeddings` 的请求体。
#[derive(Clone, Debug, Serialize, PartialEq)]
#[non_exhaustive]
pub struct CreateEmbeddingRequest {
/// EN: Model id used to create embeddings.
/// 中文:用于创建 embeddings 的模型 ID。
pub model: String,
/// EN: Input text or text array.
/// 中文:输入文本或文本数组。
pub input: EmbeddingInput,
/// EN: Optional embedding encoding format.
/// 中文:可选的 embedding 编码格式。
#[serde(skip_serializing_if = "Option::is_none")]
pub encoding_format: Option<EmbeddingEncodingFormat>,
/// EN: Optional output vector dimension count for supported models.
/// 中文:支持的模型可选输出向量维度数。
#[serde(skip_serializing_if = "Option::is_none")]
pub dimensions: Option<u32>,
/// EN: Optional end-user identifier.
/// 中文:可选的终端用户标识。
#[serde(skip_serializing_if = "Option::is_none")]
pub user: Option<String>,
/// EN: Forward-compatible optional fields not yet covered by handwritten types.
/// 中文:手写类型尚未覆盖的前向兼容可选字段。
#[serde(flatten)]
pub extra: BTreeMap<String, Value>,
}
impl CreateEmbeddingRequest {
/// EN: Starts building an embeddings request.
/// 中文:开始构建 embeddings 请求。
pub fn builder() -> CreateEmbeddingRequestBuilder {
CreateEmbeddingRequestBuilder::default()
}
}
/// EN: Builder for create-embedding requests.
/// 中文:创建 embedding 请求的构建器。
#[derive(Clone, Debug, Default)]
#[non_exhaustive]
pub struct CreateEmbeddingRequestBuilder {
model: Option<String>,
input: Option<EmbeddingInput>,
encoding_format: Option<EmbeddingEncodingFormat>,
dimensions: Option<u32>,
user: Option<String>,
extra: BTreeMap<String, Value>,
}
impl CreateEmbeddingRequestBuilder {
/// EN: Sets the embedding model id.
/// 中文:设置 embedding 模型 ID。
pub fn model(mut self, model: impl Into<String>) -> Self {
self.model = Some(model.into());
self
}
/// EN: Sets the embedding input.
/// 中文:设置 embedding 输入。
pub fn input(mut self, input: impl Into<EmbeddingInput>) -> Self {
self.input = Some(input.into());
self
}
/// EN: Sets the embedding encoding format.
/// 中文:设置 embedding 编码格式。
pub fn encoding_format(mut self, encoding_format: EmbeddingEncodingFormat) -> Self {
self.encoding_format = Some(encoding_format);
self
}
/// EN: Sets the output vector dimensions.
/// 中文:设置输出向量维度。
pub fn dimensions(mut self, dimensions: u32) -> Self {
self.dimensions = Some(dimensions);
self
}
/// EN: Sets the optional end-user identifier.
/// 中文:设置可选的终端用户标识。
pub fn user(mut self, user: impl Into<String>) -> Self {
self.user = Some(user.into());
self
}
/// EN: Adds a forward-compatible JSON field.
/// 中文:添加前向兼容的 JSON 字段。
pub fn extra(mut self, name: impl Into<String>, value: Value) -> Self {
self.extra.insert(name.into(), value);
self
}
/// EN: Builds and validates the request.
/// 中文:构建并校验请求。
pub fn build(self) -> Result<CreateEmbeddingRequest, LingerError> {
let model = self
.model
.filter(|value| !value.trim().is_empty())
.ok_or_else(|| LingerError::invalid_config("model is required"))?;
let input = self
.input
.ok_or_else(|| LingerError::invalid_config("input is required"))?;
if input.is_empty() {
return Err(LingerError::invalid_config("input must not be empty"));
}
Ok(CreateEmbeddingRequest {
model,
input,
encoding_format: self.encoding_format,
dimensions: self.dimensions,
user: self.user,
extra: self.extra,
})
}
}
/// EN: Embeddings API input value.
/// 中文:Embeddings API 输入值。
#[derive(Clone, Debug, Serialize, PartialEq, Eq)]
#[serde(untagged)]
#[non_exhaustive]
pub enum EmbeddingInput {
/// EN: Single text input.
/// 中文:单条文本输入。
Text(String),
/// EN: Multiple text inputs.
/// 中文:多条文本输入。
Texts(Vec<String>),
}
impl EmbeddingInput {
fn is_empty(&self) -> bool {
match self {
Self::Text(value) => value.is_empty(),
Self::Texts(values) => values.is_empty() || values.iter().any(String::is_empty),
}
}
}
impl From<&str> for EmbeddingInput {
fn from(value: &str) -> Self {
Self::Text(value.to_string())
}
}
impl From<String> for EmbeddingInput {
fn from(value: String) -> Self {
Self::Text(value)
}
}
impl From<Vec<String>> for EmbeddingInput {
fn from(value: Vec<String>) -> Self {
Self::Texts(value)
}
}
/// EN: Embedding encoding format.
/// 中文:Embedding 编码格式。
#[derive(Clone, Copy, Debug, Serialize, PartialEq, Eq)]
#[serde(rename_all = "snake_case")]
#[non_exhaustive]
pub enum EmbeddingEncodingFormat {
/// EN: Floating-point vector output.
/// 中文:浮点向量输出。
Float,
/// EN: Base64-encoded vector output.
/// 中文:Base64 编码的向量输出。
Base64,
}
/// EN: Response object returned by the Embeddings API.
/// 中文:Embeddings API 返回的响应对象。
#[derive(Clone, Debug, Deserialize, Serialize, PartialEq)]
#[non_exhaustive]
pub struct EmbeddingResponse {
/// EN: API list object type.
/// 中文:API 列表对象类型。
pub object: String,
/// EN: Embedding items.
/// 中文:Embedding 项。
#[serde(default)]
pub data: Vec<Embedding>,
/// EN: Model used to create the embeddings.
/// 中文:用于创建 embeddings 的模型。
pub model: String,
/// EN: Token usage.
/// 中文:Token 用量。
pub usage: EmbeddingUsage,
/// EN: OpenAI request id from response headers.
/// 中文:响应头中的 OpenAI 请求 ID。
#[serde(skip)]
request_id: Option<RequestId>,
}
impl EmbeddingResponse {
pub(crate) fn with_request_id(mut self, request_id: Option<RequestId>) -> Self {
self.request_id = request_id;
self
}
/// EN: Returns the OpenAI request id, when present.
/// 中文:返回 OpenAI 请求 ID,如存在。
pub fn request_id(&self) -> Option<&RequestId> {
self.request_id.as_ref()
}
}
/// EN: Single embedding item.
/// 中文:单个 embedding 项。
#[derive(Clone, Debug, Deserialize, Serialize, PartialEq)]
#[non_exhaustive]
pub struct Embedding {
/// EN: API object type.
/// 中文:API 对象类型。
pub object: String,
/// EN: Embedding vector.
/// 中文:Embedding 向量。
pub embedding: Vec<f32>,
/// EN: Index of this embedding in the response.
/// 中文:该 embedding 在响应中的索引。
pub index: u32,
}
/// EN: Token usage for an embeddings request.
/// 中文:Embeddings 请求的 token 用量。
#[derive(Clone, Debug, Deserialize, Serialize, PartialEq, Eq)]
#[non_exhaustive]
pub struct EmbeddingUsage {
/// EN: Prompt token count.
/// 中文:Prompt token 数量。
pub prompt_tokens: u64,
/// EN: Total token count.
/// 中文:总 token 数量。
pub total_tokens: u64,
}