@effect/ai-openai 4.0.0-beta.6 → 4.0.0-beta.60
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/Generated.d.ts +66011 -38686
- package/dist/Generated.d.ts.map +1 -1
- package/dist/Generated.js +1 -1
- package/dist/Generated.js.map +1 -1
- package/dist/OpenAiClient.d.ts +63 -17
- package/dist/OpenAiClient.d.ts.map +1 -1
- package/dist/OpenAiClient.js +210 -33
- package/dist/OpenAiClient.js.map +1 -1
- package/dist/OpenAiClientGenerated.d.ts +91 -0
- package/dist/OpenAiClientGenerated.d.ts.map +1 -0
- package/dist/OpenAiClientGenerated.js +84 -0
- package/dist/OpenAiClientGenerated.js.map +1 -0
- package/dist/OpenAiConfig.d.ts +2 -2
- package/dist/OpenAiConfig.d.ts.map +1 -1
- package/dist/OpenAiConfig.js +3 -3
- package/dist/OpenAiConfig.js.map +1 -1
- package/dist/OpenAiEmbeddingModel.d.ts +85 -0
- package/dist/OpenAiEmbeddingModel.d.ts.map +1 -0
- package/dist/OpenAiEmbeddingModel.js +119 -0
- package/dist/OpenAiEmbeddingModel.js.map +1 -0
- package/dist/OpenAiError.d.ts +22 -32
- package/dist/OpenAiError.d.ts.map +1 -1
- package/dist/OpenAiLanguageModel.d.ts +43 -49
- package/dist/OpenAiLanguageModel.d.ts.map +1 -1
- package/dist/OpenAiLanguageModel.js +296 -152
- package/dist/OpenAiLanguageModel.js.map +1 -1
- package/dist/OpenAiSchema.d.ts +1920 -0
- package/dist/OpenAiSchema.d.ts.map +1 -0
- package/dist/OpenAiSchema.js +536 -0
- package/dist/OpenAiSchema.js.map +1 -0
- package/dist/OpenAiTool.d.ts +8 -7
- package/dist/OpenAiTool.d.ts.map +1 -1
- package/dist/OpenAiTool.js +2 -1
- package/dist/OpenAiTool.js.map +1 -1
- package/dist/index.d.ts +18 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +18 -0
- package/dist/index.js.map +1 -1
- package/dist/internal/errors.js +4 -4
- package/dist/internal/errors.js.map +1 -1
- package/package.json +3 -3
- package/src/Generated.ts +7416 -4257
- package/src/OpenAiClient.ts +377 -81
- package/src/OpenAiClientGenerated.ts +202 -0
- package/src/OpenAiConfig.ts +3 -3
- package/src/OpenAiEmbeddingModel.ts +203 -0
- package/src/OpenAiError.ts +24 -32
- package/src/OpenAiLanguageModel.ts +420 -144
- package/src/OpenAiSchema.ts +875 -0
- package/src/OpenAiTool.ts +2 -1
- package/src/index.ts +21 -0
- package/src/internal/errors.ts +6 -4
|
@@ -0,0 +1,202 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @since 1.0.0
|
|
3
|
+
*/
|
|
4
|
+
import * as Array from "effect/Array"
|
|
5
|
+
import type * as Config from "effect/Config"
|
|
6
|
+
import * as Context from "effect/Context"
|
|
7
|
+
import * as Effect from "effect/Effect"
|
|
8
|
+
import { identity } from "effect/Function"
|
|
9
|
+
import * as Function from "effect/Function"
|
|
10
|
+
import * as Layer from "effect/Layer"
|
|
11
|
+
import * as Predicate from "effect/Predicate"
|
|
12
|
+
import * as Redacted from "effect/Redacted"
|
|
13
|
+
import * as Headers from "effect/unstable/http/Headers"
|
|
14
|
+
import * as HttpClient from "effect/unstable/http/HttpClient"
|
|
15
|
+
import * as HttpClientRequest from "effect/unstable/http/HttpClientRequest"
|
|
16
|
+
import * as Generated from "./Generated.ts"
|
|
17
|
+
import { OpenAiConfig } from "./OpenAiConfig.ts"
|
|
18
|
+
|
|
19
|
+
// =============================================================================
|
|
20
|
+
// Service Identifier
|
|
21
|
+
// =============================================================================
|
|
22
|
+
|
|
23
|
+
/**
|
|
24
|
+
* Service identifier for the generated OpenAI client.
|
|
25
|
+
*
|
|
26
|
+
* @since 1.0.0
|
|
27
|
+
* @category service
|
|
28
|
+
*/
|
|
29
|
+
export class OpenAiClientGenerated extends Context.Service<OpenAiClientGenerated, Generated.OpenAiClient>()(
|
|
30
|
+
"@effect/ai-openai/OpenAiClientGenerated"
|
|
31
|
+
) {}
|
|
32
|
+
|
|
33
|
+
// =============================================================================
|
|
34
|
+
// Options
|
|
35
|
+
// =============================================================================
|
|
36
|
+
|
|
37
|
+
/**
|
|
38
|
+
* Options for configuring the generated OpenAI client.
|
|
39
|
+
*
|
|
40
|
+
* @since 1.0.0
|
|
41
|
+
* @category models
|
|
42
|
+
*/
|
|
43
|
+
export type Options = {
|
|
44
|
+
/**
|
|
45
|
+
* The OpenAI API key.
|
|
46
|
+
*/
|
|
47
|
+
readonly apiKey?: Redacted.Redacted<string> | undefined
|
|
48
|
+
|
|
49
|
+
/**
|
|
50
|
+
* The base URL for the OpenAI API.
|
|
51
|
+
*
|
|
52
|
+
* @default "https://api.openai.com/v1"
|
|
53
|
+
*/
|
|
54
|
+
readonly apiUrl?: string | undefined
|
|
55
|
+
|
|
56
|
+
/**
|
|
57
|
+
* Optional organization ID for multi-org accounts.
|
|
58
|
+
*/
|
|
59
|
+
readonly organizationId?: Redacted.Redacted<string> | undefined
|
|
60
|
+
|
|
61
|
+
/**
|
|
62
|
+
* Optional project ID for project-scoped requests.
|
|
63
|
+
*/
|
|
64
|
+
readonly projectId?: Redacted.Redacted<string> | undefined
|
|
65
|
+
|
|
66
|
+
/**
|
|
67
|
+
* Optional transformer for the HTTP client.
|
|
68
|
+
*/
|
|
69
|
+
readonly transformClient?: ((client: HttpClient.HttpClient) => HttpClient.HttpClient) | undefined
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
const RedactedOpenAiHeaders = {
|
|
73
|
+
OpenAiOrganization: "OpenAI-Organization",
|
|
74
|
+
OpenAiProject: "OpenAI-Project"
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
// =============================================================================
|
|
78
|
+
// Constructor
|
|
79
|
+
// =============================================================================
|
|
80
|
+
|
|
81
|
+
/**
|
|
82
|
+
* Creates a generated OpenAI client service with the given options.
|
|
83
|
+
*
|
|
84
|
+
* @since 1.0.0
|
|
85
|
+
* @category constructors
|
|
86
|
+
*/
|
|
87
|
+
export const make = Effect.fnUntraced(
|
|
88
|
+
function*(options: Options): Effect.fn.Return<Generated.OpenAiClient, never, HttpClient.HttpClient> {
|
|
89
|
+
const baseClient = yield* HttpClient.HttpClient
|
|
90
|
+
const apiUrl = options.apiUrl ?? "https://api.openai.com/v1"
|
|
91
|
+
|
|
92
|
+
const httpClient = baseClient.pipe(
|
|
93
|
+
HttpClient.mapRequest(Function.flow(
|
|
94
|
+
HttpClientRequest.prependUrl(apiUrl),
|
|
95
|
+
options.apiKey
|
|
96
|
+
? HttpClientRequest.bearerToken(Redacted.value(options.apiKey))
|
|
97
|
+
: identity,
|
|
98
|
+
options.organizationId
|
|
99
|
+
? HttpClientRequest.setHeader(
|
|
100
|
+
RedactedOpenAiHeaders.OpenAiOrganization,
|
|
101
|
+
Redacted.value(options.organizationId)
|
|
102
|
+
)
|
|
103
|
+
: identity,
|
|
104
|
+
options.projectId
|
|
105
|
+
? HttpClientRequest.setHeader(
|
|
106
|
+
RedactedOpenAiHeaders.OpenAiProject,
|
|
107
|
+
Redacted.value(options.projectId)
|
|
108
|
+
)
|
|
109
|
+
: identity,
|
|
110
|
+
HttpClientRequest.acceptJson
|
|
111
|
+
)),
|
|
112
|
+
options.transformClient
|
|
113
|
+
? options.transformClient
|
|
114
|
+
: identity
|
|
115
|
+
)
|
|
116
|
+
|
|
117
|
+
return Generated.make(httpClient, {
|
|
118
|
+
transformClient: Effect.fnUntraced(function*(client) {
|
|
119
|
+
const config = yield* OpenAiConfig.getOrUndefined
|
|
120
|
+
if (Predicate.isNotUndefined(config?.transformClient)) {
|
|
121
|
+
return config.transformClient(client)
|
|
122
|
+
}
|
|
123
|
+
return client
|
|
124
|
+
})
|
|
125
|
+
})
|
|
126
|
+
},
|
|
127
|
+
Effect.updateService(
|
|
128
|
+
Headers.CurrentRedactedNames,
|
|
129
|
+
Array.appendAll(Object.values(RedactedOpenAiHeaders))
|
|
130
|
+
)
|
|
131
|
+
)
|
|
132
|
+
|
|
133
|
+
// =============================================================================
|
|
134
|
+
// Layers
|
|
135
|
+
// =============================================================================
|
|
136
|
+
|
|
137
|
+
/**
|
|
138
|
+
* Creates a layer for the generated OpenAI client with the given options.
|
|
139
|
+
*
|
|
140
|
+
* @since 1.0.0
|
|
141
|
+
* @category layers
|
|
142
|
+
*/
|
|
143
|
+
export const layer = (options: Options): Layer.Layer<OpenAiClientGenerated, never, HttpClient.HttpClient> =>
|
|
144
|
+
Layer.effect(OpenAiClientGenerated, make(options))
|
|
145
|
+
|
|
146
|
+
/**
|
|
147
|
+
* Creates a layer for the generated OpenAI client, loading the requisite
|
|
148
|
+
* configuration via Effect's `Config` module.
|
|
149
|
+
*
|
|
150
|
+
* @since 1.0.0
|
|
151
|
+
* @category layers
|
|
152
|
+
*/
|
|
153
|
+
export const layerConfig = (options?: {
|
|
154
|
+
/**
|
|
155
|
+
* The config value to load for the API key.
|
|
156
|
+
*/
|
|
157
|
+
readonly apiKey?: Config.Config<Redacted.Redacted<string> | undefined> | undefined
|
|
158
|
+
|
|
159
|
+
/**
|
|
160
|
+
* The config value to load for the API URL.
|
|
161
|
+
*/
|
|
162
|
+
readonly apiUrl?: Config.Config<string> | undefined
|
|
163
|
+
|
|
164
|
+
/**
|
|
165
|
+
* The config value to load for the organization ID.
|
|
166
|
+
*/
|
|
167
|
+
readonly organizationId?: Config.Config<Redacted.Redacted<string> | undefined> | undefined
|
|
168
|
+
|
|
169
|
+
/**
|
|
170
|
+
* The config value to load for the project ID.
|
|
171
|
+
*/
|
|
172
|
+
readonly projectId?: Config.Config<Redacted.Redacted<string> | undefined> | undefined
|
|
173
|
+
|
|
174
|
+
/**
|
|
175
|
+
* Optional transformer for the HTTP client.
|
|
176
|
+
*/
|
|
177
|
+
readonly transformClient?: ((client: HttpClient.HttpClient) => HttpClient.HttpClient) | undefined
|
|
178
|
+
}): Layer.Layer<OpenAiClientGenerated, Config.ConfigError, HttpClient.HttpClient> =>
|
|
179
|
+
Layer.effect(
|
|
180
|
+
OpenAiClientGenerated,
|
|
181
|
+
Effect.gen(function*() {
|
|
182
|
+
const apiKey = Predicate.isNotUndefined(options?.apiKey)
|
|
183
|
+
? yield* options.apiKey :
|
|
184
|
+
undefined
|
|
185
|
+
const apiUrl = Predicate.isNotUndefined(options?.apiUrl)
|
|
186
|
+
? yield* options.apiUrl :
|
|
187
|
+
undefined
|
|
188
|
+
const organizationId = Predicate.isNotUndefined(options?.organizationId)
|
|
189
|
+
? yield* options.organizationId
|
|
190
|
+
: undefined
|
|
191
|
+
const projectId = Predicate.isNotUndefined(options?.projectId)
|
|
192
|
+
? yield* options.projectId :
|
|
193
|
+
undefined
|
|
194
|
+
return yield* make({
|
|
195
|
+
apiKey,
|
|
196
|
+
apiUrl,
|
|
197
|
+
organizationId,
|
|
198
|
+
projectId,
|
|
199
|
+
transformClient: options?.transformClient
|
|
200
|
+
})
|
|
201
|
+
})
|
|
202
|
+
)
|
package/src/OpenAiConfig.ts
CHANGED
|
@@ -1,16 +1,16 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* @since 1.0.0
|
|
3
3
|
*/
|
|
4
|
+
import * as Context from "effect/Context"
|
|
4
5
|
import * as Effect from "effect/Effect"
|
|
5
6
|
import { dual } from "effect/Function"
|
|
6
|
-
import * as ServiceMap from "effect/ServiceMap"
|
|
7
7
|
import type { HttpClient } from "effect/unstable/http/HttpClient"
|
|
8
8
|
|
|
9
9
|
/**
|
|
10
10
|
* @since 1.0.0
|
|
11
11
|
* @category services
|
|
12
12
|
*/
|
|
13
|
-
export class OpenAiConfig extends
|
|
13
|
+
export class OpenAiConfig extends Context.Service<
|
|
14
14
|
OpenAiConfig,
|
|
15
15
|
OpenAiConfig.Service
|
|
16
16
|
>()("@effect/ai-openai/OpenAiConfig") {
|
|
@@ -18,7 +18,7 @@ export class OpenAiConfig extends ServiceMap.Service<
|
|
|
18
18
|
* @since 1.0.0
|
|
19
19
|
*/
|
|
20
20
|
static readonly getOrUndefined: Effect.Effect<typeof OpenAiConfig.Service | undefined> = Effect.map(
|
|
21
|
-
Effect.
|
|
21
|
+
Effect.context<never>(),
|
|
22
22
|
(context) => context.mapUnsafe.get(OpenAiConfig.key)
|
|
23
23
|
)
|
|
24
24
|
}
|
|
@@ -0,0 +1,203 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* OpenAI Embedding Model implementation.
|
|
3
|
+
*
|
|
4
|
+
* Provides an EmbeddingModel implementation for OpenAI's embeddings API.
|
|
5
|
+
*
|
|
6
|
+
* @since 1.0.0
|
|
7
|
+
*/
|
|
8
|
+
import * as Context from "effect/Context"
|
|
9
|
+
import * as Effect from "effect/Effect"
|
|
10
|
+
import { dual } from "effect/Function"
|
|
11
|
+
import * as Layer from "effect/Layer"
|
|
12
|
+
import type { Simplify } from "effect/Types"
|
|
13
|
+
import * as AiError from "effect/unstable/ai/AiError"
|
|
14
|
+
import * as EmbeddingModel from "effect/unstable/ai/EmbeddingModel"
|
|
15
|
+
import * as AiModel from "effect/unstable/ai/Model"
|
|
16
|
+
import { OpenAiClient } from "./OpenAiClient.ts"
|
|
17
|
+
import type * as OpenAiSchema from "./OpenAiSchema.ts"
|
|
18
|
+
|
|
19
|
+
/**
|
|
20
|
+
* @since 1.0.0
|
|
21
|
+
* @category models
|
|
22
|
+
*/
|
|
23
|
+
export type Model = "text-embedding-ada-002" | "text-embedding-3-small" | "text-embedding-3-large"
|
|
24
|
+
|
|
25
|
+
/**
|
|
26
|
+
* Service definition for OpenAI embedding model configuration.
|
|
27
|
+
*
|
|
28
|
+
* @since 1.0.0
|
|
29
|
+
* @category services
|
|
30
|
+
*/
|
|
31
|
+
export class Config extends Context.Service<
|
|
32
|
+
Config,
|
|
33
|
+
Simplify<
|
|
34
|
+
& Partial<
|
|
35
|
+
Omit<
|
|
36
|
+
typeof OpenAiSchema.CreateEmbeddingRequest.Encoded,
|
|
37
|
+
"input"
|
|
38
|
+
>
|
|
39
|
+
>
|
|
40
|
+
& {
|
|
41
|
+
readonly [x: string]: unknown
|
|
42
|
+
}
|
|
43
|
+
>
|
|
44
|
+
>()("@effect/ai-openai/OpenAiEmbeddingModel/Config") {}
|
|
45
|
+
|
|
46
|
+
/**
|
|
47
|
+
* @since 1.0.0
|
|
48
|
+
* @category constructors
|
|
49
|
+
*/
|
|
50
|
+
export const model = (
|
|
51
|
+
model: (string & {}) | Model,
|
|
52
|
+
options: {
|
|
53
|
+
readonly dimensions: number
|
|
54
|
+
readonly config?: Omit<typeof Config.Service, "model" | "dimensions">
|
|
55
|
+
}
|
|
56
|
+
): AiModel.Model<"openai", EmbeddingModel.EmbeddingModel | EmbeddingModel.Dimensions, OpenAiClient> =>
|
|
57
|
+
AiModel.make(
|
|
58
|
+
"openai",
|
|
59
|
+
model,
|
|
60
|
+
Layer.merge(
|
|
61
|
+
layer({
|
|
62
|
+
model,
|
|
63
|
+
config: {
|
|
64
|
+
...options.config,
|
|
65
|
+
dimensions: options.dimensions
|
|
66
|
+
}
|
|
67
|
+
}),
|
|
68
|
+
Layer.succeed(EmbeddingModel.Dimensions, options.dimensions)
|
|
69
|
+
)
|
|
70
|
+
)
|
|
71
|
+
|
|
72
|
+
/**
|
|
73
|
+
* Creates an OpenAI embedding model service.
|
|
74
|
+
*
|
|
75
|
+
* @since 1.0.0
|
|
76
|
+
* @category constructors
|
|
77
|
+
*/
|
|
78
|
+
export const make = Effect.fnUntraced(function*({ model, config: providerConfig }: {
|
|
79
|
+
readonly model: (string & {}) | Model
|
|
80
|
+
readonly config?: Omit<typeof Config.Service, "model"> | undefined
|
|
81
|
+
}): Effect.fn.Return<EmbeddingModel.Service, never, OpenAiClient> {
|
|
82
|
+
const client = yield* OpenAiClient
|
|
83
|
+
|
|
84
|
+
const makeConfig = Effect.gen(function*() {
|
|
85
|
+
const services = yield* Effect.context<never>()
|
|
86
|
+
return { model, ...providerConfig, ...services.mapUnsafe.get(Config.key) }
|
|
87
|
+
})
|
|
88
|
+
|
|
89
|
+
return yield* EmbeddingModel.make({
|
|
90
|
+
embedMany: Effect.fnUntraced(function*({ inputs }) {
|
|
91
|
+
const config = yield* makeConfig
|
|
92
|
+
const response = yield* client.createEmbedding({ ...config, input: inputs })
|
|
93
|
+
return yield* mapProviderResponse(inputs.length, response)
|
|
94
|
+
})
|
|
95
|
+
})
|
|
96
|
+
})
|
|
97
|
+
|
|
98
|
+
/**
|
|
99
|
+
* Creates a layer for the OpenAI embedding model.
|
|
100
|
+
*
|
|
101
|
+
* @since 1.0.0
|
|
102
|
+
* @category layers
|
|
103
|
+
*/
|
|
104
|
+
export const layer = (options: {
|
|
105
|
+
readonly model: (string & {}) | Model
|
|
106
|
+
readonly config?: Omit<typeof Config.Service, "model"> | undefined
|
|
107
|
+
}): Layer.Layer<EmbeddingModel.EmbeddingModel, never, OpenAiClient> =>
|
|
108
|
+
Layer.effect(EmbeddingModel.EmbeddingModel, make(options))
|
|
109
|
+
|
|
110
|
+
/**
|
|
111
|
+
* Provides config overrides for OpenAI embedding model operations.
|
|
112
|
+
*
|
|
113
|
+
* @since 1.0.0
|
|
114
|
+
* @category configuration
|
|
115
|
+
*/
|
|
116
|
+
export const withConfigOverride: {
|
|
117
|
+
/**
|
|
118
|
+
* Provides config overrides for OpenAI embedding model operations.
|
|
119
|
+
*
|
|
120
|
+
* @since 1.0.0
|
|
121
|
+
* @category configuration
|
|
122
|
+
*/
|
|
123
|
+
(overrides: typeof Config.Service): <A, E, R>(self: Effect.Effect<A, E, R>) => Effect.Effect<A, E, Exclude<R, Config>>
|
|
124
|
+
/**
|
|
125
|
+
* Provides config overrides for OpenAI embedding model operations.
|
|
126
|
+
*
|
|
127
|
+
* @since 1.0.0
|
|
128
|
+
* @category configuration
|
|
129
|
+
*/
|
|
130
|
+
<A, E, R>(self: Effect.Effect<A, E, R>, overrides: typeof Config.Service): Effect.Effect<A, E, Exclude<R, Config>>
|
|
131
|
+
} = dual<
|
|
132
|
+
/**
|
|
133
|
+
* Provides config overrides for OpenAI embedding model operations.
|
|
134
|
+
*
|
|
135
|
+
* @since 1.0.0
|
|
136
|
+
* @category configuration
|
|
137
|
+
*/
|
|
138
|
+
(overrides: typeof Config.Service) => <A, E, R>(self: Effect.Effect<A, E, R>) => Effect.Effect<A, E, Exclude<R, Config>>,
|
|
139
|
+
/**
|
|
140
|
+
* Provides config overrides for OpenAI embedding model operations.
|
|
141
|
+
*
|
|
142
|
+
* @since 1.0.0
|
|
143
|
+
* @category configuration
|
|
144
|
+
*/
|
|
145
|
+
<A, E, R>(self: Effect.Effect<A, E, R>, overrides: typeof Config.Service) => Effect.Effect<A, E, Exclude<R, Config>>
|
|
146
|
+
>(2, (self, overrides) =>
|
|
147
|
+
Effect.flatMap(
|
|
148
|
+
Effect.serviceOption(Config),
|
|
149
|
+
(config) =>
|
|
150
|
+
Effect.provideService(self, Config, {
|
|
151
|
+
...(config._tag === "Some" ? config.value : {}),
|
|
152
|
+
...overrides
|
|
153
|
+
})
|
|
154
|
+
))
|
|
155
|
+
|
|
156
|
+
const mapProviderResponse = (
|
|
157
|
+
inputLength: number,
|
|
158
|
+
response: typeof OpenAiSchema.CreateEmbeddingResponse.Type
|
|
159
|
+
): Effect.Effect<EmbeddingModel.ProviderResponse, AiError.AiError> => {
|
|
160
|
+
if (response.data.length !== inputLength) {
|
|
161
|
+
return Effect.fail(
|
|
162
|
+
invalidOutput("Provider returned " + response.data.length + " embeddings but expected " + inputLength)
|
|
163
|
+
)
|
|
164
|
+
}
|
|
165
|
+
|
|
166
|
+
const results = new Array<Array<number>>(inputLength)
|
|
167
|
+
const seen = new Set<number>()
|
|
168
|
+
|
|
169
|
+
for (const entry of response.data) {
|
|
170
|
+
if (!Number.isInteger(entry.index) || entry.index < 0 || entry.index >= inputLength) {
|
|
171
|
+
return Effect.fail(invalidOutput("Provider returned invalid embedding index: " + entry.index))
|
|
172
|
+
}
|
|
173
|
+
if (seen.has(entry.index)) {
|
|
174
|
+
return Effect.fail(invalidOutput("Provider returned duplicate embedding index: " + entry.index))
|
|
175
|
+
}
|
|
176
|
+
if (!Array.isArray(entry.embedding)) {
|
|
177
|
+
return Effect.fail(invalidOutput("Provider returned non-vector embedding at index " + entry.index))
|
|
178
|
+
}
|
|
179
|
+
|
|
180
|
+
seen.add(entry.index)
|
|
181
|
+
results[entry.index] = [...entry.embedding]
|
|
182
|
+
}
|
|
183
|
+
|
|
184
|
+
if (seen.size !== inputLength) {
|
|
185
|
+
return Effect.fail(
|
|
186
|
+
invalidOutput("Provider returned embeddings for " + seen.size + " inputs but expected " + inputLength)
|
|
187
|
+
)
|
|
188
|
+
}
|
|
189
|
+
|
|
190
|
+
return Effect.succeed({
|
|
191
|
+
results,
|
|
192
|
+
usage: {
|
|
193
|
+
inputTokens: response.usage?.prompt_tokens
|
|
194
|
+
}
|
|
195
|
+
})
|
|
196
|
+
}
|
|
197
|
+
|
|
198
|
+
const invalidOutput = (description: string): AiError.AiError =>
|
|
199
|
+
AiError.make({
|
|
200
|
+
module: "OpenAiEmbeddingModel",
|
|
201
|
+
method: "embedMany",
|
|
202
|
+
reason: new AiError.InvalidOutputError({ description })
|
|
203
|
+
})
|
package/src/OpenAiError.ts
CHANGED
|
@@ -57,51 +57,43 @@ export type OpenAiRateLimitMetadata = OpenAiErrorMetadata & {
|
|
|
57
57
|
}
|
|
58
58
|
|
|
59
59
|
declare module "effect/unstable/ai/AiError" {
|
|
60
|
-
export interface
|
|
61
|
-
readonly
|
|
62
|
-
readonly openai?: OpenAiRateLimitMetadata | null
|
|
63
|
-
}
|
|
60
|
+
export interface RateLimitErrorMetadata {
|
|
61
|
+
readonly openai?: OpenAiRateLimitMetadata | null
|
|
64
62
|
}
|
|
65
63
|
|
|
66
|
-
export interface
|
|
67
|
-
readonly
|
|
68
|
-
readonly openai?: OpenAiErrorMetadata | null
|
|
69
|
-
}
|
|
64
|
+
export interface QuotaExhaustedErrorMetadata {
|
|
65
|
+
readonly openai?: OpenAiErrorMetadata | null
|
|
70
66
|
}
|
|
71
67
|
|
|
72
|
-
export interface
|
|
73
|
-
readonly
|
|
74
|
-
readonly openai?: OpenAiErrorMetadata | null
|
|
75
|
-
}
|
|
68
|
+
export interface AuthenticationErrorMetadata {
|
|
69
|
+
readonly openai?: OpenAiErrorMetadata | null
|
|
76
70
|
}
|
|
77
71
|
|
|
78
|
-
export interface
|
|
79
|
-
readonly
|
|
80
|
-
readonly openai?: OpenAiErrorMetadata | null
|
|
81
|
-
}
|
|
72
|
+
export interface ContentPolicyErrorMetadata {
|
|
73
|
+
readonly openai?: OpenAiErrorMetadata | null
|
|
82
74
|
}
|
|
83
75
|
|
|
84
|
-
export interface
|
|
85
|
-
readonly
|
|
86
|
-
readonly openai?: OpenAiErrorMetadata | null
|
|
87
|
-
}
|
|
76
|
+
export interface InvalidRequestErrorMetadata {
|
|
77
|
+
readonly openai?: OpenAiErrorMetadata | null
|
|
88
78
|
}
|
|
89
79
|
|
|
90
|
-
export interface
|
|
91
|
-
readonly
|
|
92
|
-
readonly openai?: OpenAiErrorMetadata | null
|
|
93
|
-
}
|
|
80
|
+
export interface InternalProviderErrorMetadata {
|
|
81
|
+
readonly openai?: OpenAiErrorMetadata | null
|
|
94
82
|
}
|
|
95
83
|
|
|
96
|
-
export interface
|
|
97
|
-
readonly
|
|
98
|
-
readonly openai?: OpenAiErrorMetadata | null
|
|
99
|
-
}
|
|
84
|
+
export interface InvalidOutputErrorMetadata {
|
|
85
|
+
readonly openai?: OpenAiErrorMetadata | null
|
|
100
86
|
}
|
|
101
87
|
|
|
102
|
-
export interface
|
|
103
|
-
readonly
|
|
104
|
-
|
|
105
|
-
|
|
88
|
+
export interface StructuredOutputErrorMetadata {
|
|
89
|
+
readonly openai?: OpenAiErrorMetadata | null
|
|
90
|
+
}
|
|
91
|
+
|
|
92
|
+
export interface UnsupportedSchemaErrorMetadata {
|
|
93
|
+
readonly openai?: OpenAiErrorMetadata | null
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
export interface UnknownErrorMetadata {
|
|
97
|
+
readonly openai?: OpenAiErrorMetadata | null
|
|
106
98
|
}
|
|
107
99
|
}
|