@meridius-labs/apple-on-device-ai
Version:
TypeScript library for accessing Apple's on-device foundation models (Apple Intelligence) with full Vercel AI SDK compatibility
289 lines (286 loc) • 8.87 kB
TypeScript
import { ModelMessage } from "ai";
import { JSONSchema7 } from "json-schema";
import { z } from "zod";
import { LanguageModelV2, LanguageModelV2CallOptions, LanguageModelV2CallWarning, LanguageModelV2Content, LanguageModelV2FinishReason, LanguageModelV2ResponseMetadata, LanguageModelV2StreamPart, LanguageModelV2Usage, SharedV2Headers, SharedV2ProviderMetadata } from "@ai-sdk/provider";
//#region src/apple-ai.d.ts
/**
* Definition of an in-memory ("ephemeral") tool that can be exposed to the
* on-device model during a single request.
*
* • `schema` captures the expected argument structure using Zod.
* • `handler` is invoked with the validated, _typed_ argument object.
*
* By making the interface generic in `TSchema` (and, optionally, `TResult`) we
* propagate rich typings to call-sites instead of falling back to `unknown`.
*/
type EphemeralTool<TSchema extends JSONSchema7, TResult = unknown> = {
/** Unique, model-visible name */
name: string;
/** Optional human-oriented description */
description?: string;
/** JSON schema describing the tool arguments */
jsonSchema: TSchema;
/** Implementation invoked with a fully-parsed, type-safe argument object */
handler: (args: Record<string, unknown>) => PromiseLike<TResult>;
};
interface ChatMessage {
role: "system" | "user" | "assistant" | "tool" | "tool_calls";
content: string;
name?: string;
tool_call_id?: string;
tool_calls?: Array<{
id: string;
type: "function";
function: {
name: string;
arguments: string;
};
}>;
}
interface GenerationOptions {
temperature?: number;
maxTokens?: number;
}
interface ModelAvailability {
available: boolean;
reason: string;
}
interface ChatCompletionChunk {
id: string;
object: "chat.completion.chunk";
created: number;
model: string;
choices: {
index: number;
delta: {
role?: "assistant";
content?: string;
};
finish_reason: string | null;
}[];
}
interface ChatCompletionResponse {
id: string;
object: "chat.completion";
created: number;
model: string;
choices: {
index: number;
message: ChatMessage;
finish_reason: string;
}[];
}
/**
* Apple AI library for accessing on-device foundation models
*/
declare class AppleAISDK {
/** Check availability of Apple Intelligence */
checkAvailability(): Promise<ModelAvailability>;
/** Get supported languages */
getSupportedLanguages(): string[];
/** Generate a response for a prompt */
generateResponse(prompt: string, options?: GenerationOptions): Promise<string>;
/** Generate a response using conversation history */
generateResponseWithHistory(messages: ChatMessage[], options?: GenerationOptions): Promise<string>;
/**
* Stream chat completion as async generator yielding OpenAI-compatible chunks
*/
streamChatCompletion(messages: ChatMessage[], options?: GenerationOptions): AsyncIterableIterator<ChatCompletionChunk>;
/** Generate a structured object based on a Zod/JSON schema */
generateStructured<T = unknown>(params: {
prompt: string;
schemaJson: string;
temperature?: number;
maxTokens?: number;
}): Promise<{
text: string;
object: T;
}>;
}
declare const appleAISDK: AppleAISDK;
/**
* Unified structured generation that accepts either Zod schemas or JSON Schema
*/
declare function structured<T = unknown>(options: {
prompt: string;
schema: z.ZodType<T> | JSONSchema7;
temperature?: number;
maxTokens?: number;
}): Promise<{
text: string;
object: T;
}>;
/**
* @deprecated Don't use this function directly. It's used internally by the Vercel AI SDK.
* Stream chat that properly integrates with Vercel AI SDK's multi-step tool calling.
* This function emits tool-call events and ends the stream, allowing the SDK to
* orchestrate tool execution and restart generation with updated messages.
*
* Early termination is enabled by default when tools are present, saving compute
* resources by stopping the Swift streaming loop after tool calls complete.
*
*/
declare function _streamChatForVercelAISDK<TTools extends ReadonlyArray<EphemeralTool<JSONSchema7>>>(options: {
messages: ModelMessage[];
tools: TTools;
temperature?: number;
}): AsyncIterableIterator<{
type: "text";
text: string;
} | {
type: "tool-call";
toolCallId: string;
toolName: string;
args: Record<string, unknown>;
}>;
/**
* Unified generation function that exposes all capabilities
*/
declare function chat<T = unknown>(options: {
messages: ChatMessage[] | string;
tools?: EphemeralTool<JSONSchema7>[];
schema?: z.ZodType<T> | JSONSchema7;
temperature?: number;
maxTokens?: number;
/**
* If true, the generation will stop after the tool calls are complete.
* This is the default behavior for OpenAI.
* @default true
*/
stopAfterToolCalls?: boolean;
stream?: false;
}): Promise<{
text: string;
object?: T;
toolCalls?: any[];
}>;
declare function chat<T = unknown>(options: {
messages: ChatMessage[] | string;
tools?: EphemeralTool<JSONSchema7>[];
schema?: z.ZodType<T> | JSONSchema7;
temperature?: number;
maxTokens?: number;
/**
* If true, the generation will stop after the tool calls are complete.
* This is the default behavior for OpenAI.
* @default true
*/
stopAfterToolCalls?: boolean;
stream: true;
}): AsyncIterableIterator<string>;
//#endregion
//#region src/apple-ai-chat-model.d.ts
interface AppleAIChatConfig {
provider: string;
headers: Record<string, string>;
generateId: () => string;
}
declare class AppleAIChatLanguageModel implements LanguageModelV2 {
readonly specificationVersion = "v2";
readonly provider: string;
readonly modelId: string;
readonly defaultObjectGenerationMode = "json";
private readonly settings;
private readonly config;
supportsImageUrls: boolean;
supportsStructuredOutputs: boolean;
constructor(modelId: AppleAIModelId, settings: AppleAISettings, config: AppleAIChatConfig);
supportedUrls: Record<string, RegExp[]> | PromiseLike<Record<string, RegExp[]>>;
doGenerate(options: LanguageModelV2CallOptions): PromiseLike<{
content: Array<LanguageModelV2Content>;
finishReason: LanguageModelV2FinishReason;
usage: LanguageModelV2Usage;
providerMetadata?: SharedV2ProviderMetadata;
request?: {
body?: unknown;
};
response?: LanguageModelV2ResponseMetadata & {
headers?: SharedV2Headers;
body?: unknown;
};
warnings: Array<LanguageModelV2CallWarning>;
}>;
private generateResponse;
private handleStructuredGeneration;
private handleRegularGeneration;
supportsUrl?(_url: typeof URL): boolean;
doStream(options: LanguageModelV2CallOptions): Promise<{
stream: ReadableStream<LanguageModelV2StreamPart>;
}>;
private createToolEnabledStream;
private createRegularStream;
private createStreamFromEvents;
private createStreamFromChunks;
private finishStream;
private convertPromptToMessages;
private convertSystemMessage;
private convertUserMessage;
private convertAssistantMessage;
private convertToolMessage;
private convertFallbackMessage;
}
//#endregion
//#region src/apple-ai-provider.d.ts
type AppleAIModelId = "apple-on-device" | (string & {});
interface AppleAISettings {
temperature?: number;
maxTokens?: number;
}
interface AppleAIProvider {
(modelId: AppleAIModelId, settings?: AppleAISettings): AppleAIChatLanguageModel;
chat(modelId: AppleAIModelId, settings?: AppleAISettings): AppleAIChatLanguageModel;
}
interface AppleAIProviderSettings {
/**
* Custom headers to include in the requests.
*/
headers?: Record<string, string>;
/**
* Custom ID generation function
*/
generateId?: () => string;
}
/**
* Default Apple AI provider instance.
*/
declare const appleAI: AppleAIProvider;
//#endregion
//#region src/server/index.d.ts
interface ServerOptions {
host?: string;
port?: number;
https?: false | {
cert: string;
key: string;
port?: number;
};
bearerToken?: string;
onError?: (error: Error) => void;
}
/**
* Authentication middleware
*/
/**
* Start the OpenAI-compatible server
*/
declare function startServer(opts?: ServerOptions): Promise<{
urls: {
http: string;
https: string;
};
url: string;
stop: () => Promise<void>;
port: number;
httpsPort: number;
} | {
urls: {
http: string;
https: undefined;
};
url: string;
stop: () => Promise<void>;
port: number;
httpsPort?: undefined;
}>;
//#endregion
export { AppleAIChatConfig, AppleAIChatLanguageModel, AppleAIModelId, AppleAIProvider, AppleAIProviderSettings, AppleAISDK, AppleAISettings, ChatCompletionChunk, ChatCompletionResponse, ChatMessage, EphemeralTool, GenerationOptions, ModelAvailability, ServerOptions, _streamChatForVercelAISDK, appleAI, appleAISDK, chat, appleAI as createAppleAI, startServer, structured };