mixedbread-ai-provider
Version:
Mixedbread AI Provider for running Mixedbread AI models with Vercel AI SDK
170 lines (165 loc) • 5.03 kB
JavaScript
// src/mixedbread-provider.ts
import {
loadApiKey,
withoutTrailingSlash
} from "@ai-sdk/provider-utils";
// src/mixedbread-embedding-model.ts
import {
TooManyEmbeddingValuesForCallError
} from "@ai-sdk/provider";
import {
combineHeaders,
createJsonResponseHandler,
parseProviderOptions,
postJsonToApi
} from "@ai-sdk/provider-utils";
import { z as z3 } from "zod/v4";
// src/mixedbread-error.ts
import { createJsonErrorResponseHandler } from "@ai-sdk/provider-utils";
import { z } from "zod/v4";
var mixedbreadErrorDataSchema = z.object({
error: z.object({
code: z.string().nullable(),
message: z.string(),
param: z.any().nullable(),
type: z.string()
})
});
var mixedbreadFailedResponseHandler = createJsonErrorResponseHandler({
errorSchema: mixedbreadErrorDataSchema,
errorToMessage: (data) => data.error.message
});
// src/mixedbread-embedding-options.ts
import { z as z2 } from "zod/v4";
var mixedbreadEmbeddingOptions = z2.object({
/**
* An optional prompt to provide context to the model. Refer to the model's documentation for more information.
* A string between 1 and 256 characters.
*/
prompt: z2.string().optional(),
/**
* Option to normalize the embeddings.
*/
normalized: z2.boolean().optional(),
/**
* The desired number of dimensions in the output vectors. Defaults to the model's maximum.
* A number between 1 and the model's maximum output dimensions.
* Only applicable for Matryoshka-based models.
*/
dimensions: z2.number().optional(),
/**
* The desired format for the embeddings. Defaults to "float".
* Options: float, float16, binary, ubinary, int8, uint8, base64.
*/
encodingFormat: z2.enum(["float", "float16", "binary", "ubinary", "int8", "uint8", "base64"]).optional()
});
// src/mixedbread-embedding-model.ts
var MixedbreadEmbeddingModel = class {
specificationVersion = "v2";
modelId;
config;
get provider() {
return this.config.provider;
}
get maxEmbeddingsPerCall() {
return 256;
}
get supportsParallelCalls() {
return true;
}
constructor(modelId, config) {
this.modelId = modelId;
this.config = config;
}
async doEmbed({
abortSignal,
values,
headers,
providerOptions
}) {
const embeddingOptions = await parseProviderOptions({
provider: "mixedbread",
providerOptions,
schema: mixedbreadEmbeddingOptions
});
if (values.length > this.maxEmbeddingsPerCall) {
throw new TooManyEmbeddingValuesForCallError({
maxEmbeddingsPerCall: this.maxEmbeddingsPerCall,
modelId: this.modelId,
provider: this.provider,
values
});
}
const {
responseHeaders,
value: response,
rawValue
} = await postJsonToApi({
abortSignal,
body: {
input: values,
model: this.modelId,
prompt: embeddingOptions?.prompt,
normalize: embeddingOptions?.normalized,
dimensions: embeddingOptions?.dimensions,
encoding_format: embeddingOptions?.encodingFormat
},
failedResponseHandler: mixedbreadFailedResponseHandler,
fetch: this.config.fetch,
headers: combineHeaders(this.config.headers(), headers),
successfulResponseHandler: createJsonResponseHandler(
mixedbreadTextEmbeddingResponseSchema
),
url: `${this.config.baseURL}/embeddings`
});
return {
embeddings: response.data.map((item) => item.embedding),
usage: response.usage ? { tokens: response.usage.total_tokens } : void 0,
response: { headers: responseHeaders, body: rawValue }
};
}
};
var mixedbreadTextEmbeddingResponseSchema = z3.object({
data: z3.array(z3.object({ embedding: z3.array(z3.number()) })),
usage: z3.object({ total_tokens: z3.number() }).nullish()
});
// src/mixedbread-provider.ts
function createMixedbread(options = {}) {
const baseURL = withoutTrailingSlash(options.baseURL) ?? "https://api.mixedbread.com/v1";
const getHeaders = () => ({
Authorization: `Bearer ${loadApiKey({
apiKey: options.apiKey,
environmentVariableName: "MIXEDBREAD_API_KEY",
description: "Mixedbread"
})}`,
...options.headers
});
const createEmbeddingModel = (modelId) => new MixedbreadEmbeddingModel(modelId, {
provider: "mixedbread.embedding",
baseURL,
headers: getHeaders,
fetch: options.fetch
});
const provider = function(modelId) {
if (new.target) {
throw new Error(
"The Mixedbread model function cannot be called with the new keyword."
);
}
return createEmbeddingModel(modelId);
};
provider.textEmbeddingModel = createEmbeddingModel;
provider.chat = provider.languageModel = () => {
throw new Error("languageModel method is not implemented.");
};
provider.imageModel = () => {
throw new Error("imageModel method is not implemented.");
};
return provider;
}
var mixedbread = createMixedbread();
export {
createMixedbread,
mixedbread
};
//# sourceMappingURL=index.mjs.map