[{"data":1,"prerenderedAt":-1},["ShallowReactive",2],{"project-10787":3},{"id":4,"name":5,"fullName":6,"owner":7,"repo":5,"description":8,"homepage":9,"htmlUrl":10,"language":11,"languages":10,"totalLinesOfCode":10,"stars":12,"forks":13,"watchers":14,"openIssues":15,"contributorsCount":16,"subscribersCount":16,"size":16,"stars1d":16,"stars7d":16,"stars30d":17,"stars90d":16,"forks30d":16,"starsTrendScore":16,"compositeScore":18,"rankGlobal":10,"rankLanguage":10,"license":19,"archived":20,"fork":20,"defaultBranch":21,"hasWiki":20,"hasPages":20,"topics":22,"createdAt":10,"pushedAt":10,"updatedAt":43,"readmeContent":44,"aiSummary":45,"trendingCount":16,"starSnapshotCount":16,"syncStatus":46,"lastSyncTime":47,"discoverSource":48},10787,"modelfusion","vercel\u002Fmodelfusion","vercel","The TypeScript library for building AI applications.","https:\u002F\u002Fmodelfusion.dev",null,"TypeScript",1319,97,12,33,0,1,34.07,"MIT License",false,"main",[23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42],"ai","artificial-intelligence","chatbot","claude","dall-e","embedding","gpt-3","huggingface","javascript","js","llamacpp","llm","mistral","multi-modal","ollama","openai","stable-diffusion","ts","typescript","whisper","2026-06-11 04:04:00","# ModelFusion\n\n> ### The TypeScript library for building AI applications.\n\n[![NPM Version](https:\u002F\u002Fimg.shields.io\u002Fnpm\u002Fv\u002Fmodelfusion?color=33cd56&logo=npm)](https:\u002F\u002Fwww.npmjs.com\u002Fpackage\u002Fmodelfusion)\n[![MIT License](https:\u002F\u002Fimg.shields.io\u002Fgithub\u002Flicense\u002Flgrammel\u002Fmodelfusion)](https:\u002F\u002Fopensource.org\u002Flicenses\u002FMIT)\n[![Docs](https:\u002F\u002Fimg.shields.io\u002Fbadge\u002Fdocs-modelfusion.dev-blue)](https:\u002F\u002Fmodelfusion.dev)\n[![Created by Lars Grammel](https:\u002F\u002Fimg.shields.io\u002Fbadge\u002Fcreated%20by-@lgrammel-4BBAAB.svg)](https:\u002F\u002Ftwitter.com\u002Flgrammel)\n\n[Introduction](#introduction) | [Quick Install](#quick-install) | [Usage](#usage-examples) | [Documentation](#documentation) | [Examples](#more-examples) | [Contributing](#contributing) | [modelfusion.dev](https:\u002F\u002Fmodelfusion.dev)\n\n## Introduction\n\n> [!IMPORTANT]\n> [ModelFusion has joined Vercel](https:\u002F\u002Fvercel.com\u002Fblog\u002Fvercel-ai-sdk-3-1-modelfusion-joins-the-team) and is being integrated into the [Vercel AI SDK](https:\u002F\u002Fsdk.vercel.ai\u002Fdocs\u002Fintroduction). We are bringing the best parts of modelfusion to the Vercel AI SDK, starting with text generation, structured object generation, and tool calls. Please check out the AI SDK for the latest developments.\n\n**ModelFusion** is an abstraction layer for integrating AI models into JavaScript and TypeScript applications, unifying the API for common operations such as **text streaming**, **object generation**, and **tool usage**. It provides features to support production environments, including observability hooks, logging, and automatic retries. You can use ModelFusion to build AI applications, chatbots, and agents.\n\n- **Vendor-neutral**: ModelFusion is a non-commercial open source project that is community-driven. You can use it with any supported provider.\n- **Multi-modal**: ModelFusion supports a wide range of models including text generation, image generation, vision, text-to-speech, speech-to-text, and embedding models.\n- **Type inference and validation**: ModelFusion infers TypeScript types wherever possible and validates model responses.\n- **Observability and logging**: ModelFusion provides an observer framework and logging support.\n- **Resilience and robustness**: ModelFusion ensures seamless operation through automatic retries, throttling, and error handling mechanisms.\n- **Built for production**: ModelFusion is fully tree-shakeable, can be used in serverless environments, and only uses a minimal set of dependencies.\n\n## Quick Install\n\n```sh\nnpm install modelfusion\n```\n\nOr use a starter template:\n\n- [ModelFusion terminal app starter](https:\u002F\u002Fgithub.com\u002Flgrammel\u002Fmodelfusion-terminal-app-starter)\n- [Next.js, Vercel AI SDK, Llama.cpp & ModelFusion starter](https:\u002F\u002Fgithub.com\u002Flgrammel\u002Fmodelfusion-llamacpp-nextjs-starter)\n- [Next.js, Vercel AI SDK, Ollama & ModelFusion starter](https:\u002F\u002Fgithub.com\u002Flgrammel\u002Fmodelfusion-ollama-nextjs-starter)\n\n## Usage Examples\n\n> [!TIP]\n> The basic examples are a great way to get started and to explore in parallel with the [documentation](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ffunction\u002F). You can find them in the [examples\u002Fbasic](https:\u002F\u002Fgithub.com\u002Flgrammel\u002Fmodelfusion\u002Ftree\u002Fmain\u002Fexamples\u002Fbasic) folder.\n\nYou can provide API keys for the different [integrations](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002F) using environment variables (e.g., `OPENAI_API_KEY`) or pass them into the model constructors as options.\n\n### [Generate Text](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ffunction\u002Fgenerate-text)\n\nGenerate text using a language model and a prompt. You can stream the text if it is supported by the model. You can use images for multi-modal prompting if the model supports it (e.g. with [llama.cpp](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fllamacpp)).\nYou can use [prompt styles](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ffunction\u002Fgenerate-text#prompt-styles) to use text, instruction, or chat prompts.\n\n#### generateText\n\n```ts\nimport { generateText, openai } from \"modelfusion\";\n\nconst text = await generateText({\n  model: openai.CompletionTextGenerator({ model: \"gpt-3.5-turbo-instruct\" }),\n  prompt: \"Write a short story about a robot learning to love:\\n\\n\",\n});\n```\n\nProviders: [OpenAI](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fopenai), [OpenAI compatible](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fopenaicompatible), [Llama.cpp](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fllamacpp), [Ollama](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Follama), [Mistral](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fmistral), [Hugging Face](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fhuggingface), [Cohere](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fcohere)\n\n#### streamText\n\n```ts\nimport { streamText, openai } from \"modelfusion\";\n\nconst textStream = await streamText({\n  model: openai.CompletionTextGenerator({ model: \"gpt-3.5-turbo-instruct\" }),\n  prompt: \"Write a short story about a robot learning to love:\\n\\n\",\n});\n\nfor await (const textPart of textStream) {\n  process.stdout.write(textPart);\n}\n```\n\nProviders: [OpenAI](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fopenai), [OpenAI compatible](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fopenaicompatible), [Llama.cpp](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fllamacpp), [Ollama](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Follama), [Mistral](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fmistral), [Cohere](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fcohere)\n\n#### streamText with multi-modal prompt\n\nMulti-modal vision models such as GPT 4 Vision can process images as part of the prompt.\n\n```ts\nimport { streamText, openai } from \"modelfusion\";\nimport { readFileSync } from \"fs\";\n\nconst image = readFileSync(\".\u002Fimage.png\");\n\nconst textStream = await streamText({\n  model: openai\n    .ChatTextGenerator({ model: \"gpt-4-vision-preview\" })\n    .withInstructionPrompt(),\n\n  prompt: {\n    instruction: [\n      { type: \"text\", text: \"Describe the image in detail.\" },\n      { type: \"image\", image, mimeType: \"image\u002Fpng\" },\n    ],\n  },\n});\n\nfor await (const textPart of textStream) {\n  process.stdout.write(textPart);\n}\n```\n\nProviders: [OpenAI](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fopenai), [OpenAI compatible](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fopenaicompatible), [Llama.cpp](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fllamacpp), [Ollama](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Follama)\n\n### [Generate Object](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ffunction\u002Fgenerate-object)\n\nGenerate typed objects using a language model and a schema.\n\n#### generateObject\n\nGenerate an object that matches a schema.\n\n```ts\nimport {\n  ollama,\n  zodSchema,\n  generateObject,\n  jsonObjectPrompt,\n} from \"modelfusion\";\n\nconst sentiment = await generateObject({\n  model: ollama\n    .ChatTextGenerator({\n      model: \"openhermes2.5-mistral\",\n      maxGenerationTokens: 1024,\n      temperature: 0,\n    })\n    .asObjectGenerationModel(jsonObjectPrompt.instruction()),\n\n  schema: zodSchema(\n    z.object({\n      sentiment: z\n        .enum([\"positive\", \"neutral\", \"negative\"])\n        .describe(\"Sentiment.\"),\n    })\n  ),\n\n  prompt: {\n    system:\n      \"You are a sentiment evaluator. \" +\n      \"Analyze the sentiment of the following product review:\",\n    instruction:\n      \"After I opened the package, I was met by a very unpleasant smell \" +\n      \"that did not disappear even after washing. Never again!\",\n  },\n});\n```\n\nProviders: [OpenAI](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fopenai), [Ollama](https:\u002F\u002Fmodelfusion.dev\u002F\u002Fintegration\u002Fmodel-provider\u002Follama), [Llama.cpp](https:\u002F\u002Fmodelfusion.dev\u002F\u002Fintegration\u002Fmodel-provider\u002Fllama.cpp)\n\n#### streamObject\n\nStream a object that matches a schema. Partial objects before the final part are untyped JSON.\n\n```ts\nimport { zodSchema, openai, streamObject } from \"modelfusion\";\n\nconst objectStream = await streamObject({\n  model: openai\n    .ChatTextGenerator(\u002F* ... *\u002F)\n    .asFunctionCallObjectGenerationModel({\n      fnName: \"generateCharacter\",\n      fnDescription: \"Generate character descriptions.\",\n    })\n    .withTextPrompt(),\n\n  schema: zodSchema(\n    z.object({\n      characters: z.array(\n        z.object({\n          name: z.string(),\n          class: z\n            .string()\n            .describe(\"Character class, e.g. warrior, mage, or thief.\"),\n          description: z.string(),\n        })\n      ),\n    })\n  ),\n\n  prompt: \"Generate 3 character descriptions for a fantasy role playing game.\",\n});\n\nfor await (const { partialObject } of objectStream) {\n  console.clear();\n  console.log(partialObject);\n}\n```\n\nProviders: [OpenAI](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fopenai), [Ollama](https:\u002F\u002Fmodelfusion.dev\u002F\u002Fintegration\u002Fmodel-provider\u002Follama), [Llama.cpp](https:\u002F\u002Fmodelfusion.dev\u002F\u002Fintegration\u002Fmodel-provider\u002Fllama.cpp)\n\n### [Generate Image](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ffunction\u002Fgenerate-image)\n\nGenerate an image from a prompt.\n\n```ts\nimport { generateImage, openai } from \"modelfusion\";\n\nconst image = await generateImage({\n  model: openai.ImageGenerator({ model: \"dall-e-3\", size: \"1024x1024\" }),\n  prompt:\n    \"the wicked witch of the west in the style of early 19th century painting\",\n});\n```\n\nProviders: [OpenAI (Dall·E)](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fopenai), [Stability AI](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fstability), [Automatic1111](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fautomatic1111)\n\n### [Generate Speech](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ffunction\u002Fgenerate-speech)\n\nSynthesize speech (audio) from text. Also called TTS (text-to-speech).\n\n#### generateSpeech\n\n`generateSpeech` synthesizes speech from text.\n\n```ts\nimport { generateSpeech, lmnt } from \"modelfusion\";\n\n\u002F\u002F `speech` is a Uint8Array with MP3 audio data\nconst speech = await generateSpeech({\n  model: lmnt.SpeechGenerator({\n    voice: \"034b632b-df71-46c8-b440-86a42ffc3cf3\", \u002F\u002F Henry\n  }),\n  text:\n    \"Good evening, ladies and gentlemen! Exciting news on the airwaves tonight \" +\n    \"as The Rolling Stones unveil 'Hackney Diamonds,' their first collection of \" +\n    \"fresh tunes in nearly twenty years, featuring the illustrious Lady Gaga, the \" +\n    \"magical Stevie Wonder, and the final beats from the late Charlie Watts.\",\n});\n```\n\nProviders: [Eleven Labs](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Felevenlabs), [LMNT](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Flmnt), [OpenAI](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fopenai)\n\n#### streamSpeech\n\n`generateSpeech` generates a stream of speech chunks from text or from a text stream. Depending on the model, this can be fully duplex.\n\n```ts\nimport { streamSpeech, elevenlabs } from \"modelfusion\";\n\nconst textStream: AsyncIterable\u003Cstring>;\n\nconst speechStream = await streamSpeech({\n  model: elevenlabs.SpeechGenerator({\n    model: \"eleven_turbo_v2\",\n    voice: \"pNInz6obpgDQGcFmaJgB\", \u002F\u002F Adam\n    optimizeStreamingLatency: 1,\n    voiceSettings: { stability: 1, similarityBoost: 0.35 },\n    generationConfig: {\n      chunkLengthSchedule: [50, 90, 120, 150, 200],\n    },\n  }),\n  text: textStream,\n});\n\nfor await (const part of speechStream) {\n  \u002F\u002F each part is a Uint8Array with MP3 audio data\n}\n```\n\nProviders: [Eleven Labs](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Felevenlabs)\n\n### [Generate Transcription](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ffunction\u002Fgenerate-transcription)\n\nTranscribe speech (audio) data into text. Also called speech-to-text (STT).\n\n```ts\nimport { generateTranscription, openai } from \"modelfusion\";\nimport fs from \"node:fs\";\n\nconst transcription = await generateTranscription({\n  model: openai.Transcriber({ model: \"whisper-1\" }),\n  mimeType: \"audio\u002Fmp3\",\n  audioData: await fs.promises.readFile(\"data\u002Ftest.mp3\"),\n});\n```\n\nProviders: [OpenAI (Whisper)](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fopenai), [Whisper.cpp](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fwhispercpp)\n\n### [Embed Value](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ffunction\u002Fembed)\n\nCreate embeddings for text and other values. Embeddings are vectors that represent the essence of the values in the context of the model.\n\n```ts\nimport { embed, embedMany, openai } from \"modelfusion\";\n\n\u002F\u002F embed single value:\nconst embedding = await embed({\n  model: openai.TextEmbedder({ model: \"text-embedding-ada-002\" }),\n  value: \"At first, Nox didn't know what to do with the pup.\",\n});\n\n\u002F\u002F embed many values:\nconst embeddings = await embedMany({\n  model: openai.TextEmbedder({ model: \"text-embedding-ada-002\" }),\n  values: [\n    \"At first, Nox didn't know what to do with the pup.\",\n    \"He keenly observed and absorbed everything around him, from the birds in the sky to the trees in the forest.\",\n  ],\n});\n```\n\nProviders: [OpenAI](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fopenai), [OpenAI compatible](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fopenaicompatible), [Llama.cpp](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fllamacpp), [Ollama](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Follama), [Mistral](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fmistral), [Hugging Face](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fhuggingface), [Cohere](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fcohere)\n\n### [Classify Value](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ffunction\u002Fclassify)\n\nClassifies a value into a category.\n\n```ts\nimport { classify, EmbeddingSimilarityClassifier, openai } from \"modelfusion\";\n\nconst classifier = new EmbeddingSimilarityClassifier({\n  embeddingModel: openai.TextEmbedder({ model: \"text-embedding-ada-002\" }),\n  similarityThreshold: 0.82,\n  clusters: [\n    {\n      name: \"politics\" as const,\n      values: [\n        \"they will save the country!\",\n        \u002F\u002F ...\n      ],\n    },\n    {\n      name: \"chitchat\" as const,\n      values: [\n        \"how's the weather today?\",\n        \u002F\u002F ...\n      ],\n    },\n  ],\n});\n\n\u002F\u002F strongly typed result:\nconst result = await classify({\n  model: classifier,\n  value: \"don't you love politics?\",\n});\n```\n\nClassifiers: [EmbeddingSimilarityClassifier](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ffunction\u002Fclassify#embeddingsimilarityclassifier)\n\n### [Tokenize Text](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ffunction\u002Ftokenize-text)\n\nSplit text into tokens and reconstruct the text from tokens.\n\n```ts\nconst tokenizer = openai.Tokenizer({ model: \"gpt-4\" });\n\nconst text = \"At first, Nox didn't know what to do with the pup.\";\n\nconst tokenCount = await countTokens(tokenizer, text);\n\nconst tokens = await tokenizer.tokenize(text);\nconst tokensAndTokenTexts = await tokenizer.tokenizeWithTexts(text);\nconst reconstructedText = await tokenizer.detokenize(tokens);\n```\n\nProviders: [OpenAI](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fopenai), [Llama.cpp](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fllamacpp), [Cohere](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider\u002Fcohere)\n\n### [Tools](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ftools)\n\nTools are functions (and associated metadata) that can be executed by an AI model. They are useful for building chatbots and agents.\n\nModelFusion offers several tools out-of-the-box: [Math.js](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ftools\u002Favailable-tools\u002Fmathjs), [MediaWiki Search](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ftools\u002Favailable-tools\u002Fmediawiki-search), [SerpAPI](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ftools\u002Favailable-tools\u002Fserpapi), [Google Custom Search](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ftools\u002Favailable-tools\u002Fgoogle-custom-search). You can also create [custom tools](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ftools).\n\n#### [runTool](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ftools\u002Frun-tool)\n\nWith `runTool`, you can ask a tool-compatible language model (e.g. OpenAI chat) to invoke a single tool. `runTool` first generates a tool call and then executes the tool with the arguments.\n\n```ts\nconst { tool, toolCall, args, ok, result } = await runTool({\n  model: openai.ChatTextGenerator({ model: \"gpt-3.5-turbo\" }),\n  too: calculator,\n  prompt: [openai.ChatMessage.user(\"What's fourteen times twelve?\")],\n});\n\nconsole.log(`Tool call:`, toolCall);\nconsole.log(`Tool:`, tool);\nconsole.log(`Arguments:`, args);\nconsole.log(`Ok:`, ok);\nconsole.log(`Result or Error:`, result);\n```\n\n#### [runTools](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ftools\u002Frun-tools)\n\nWith `runTools`, you can ask a language model to generate several tool calls as well as text. The model will choose which tools (if any) should be called with which arguments. Both the text and the tool calls are optional. This function executes the tools.\n\n```ts\nconst { text, toolResults } = await runTools({\n  model: openai.ChatTextGenerator({ model: \"gpt-3.5-turbo\" }),\n  tools: [calculator \u002F* ... *\u002F],\n  prompt: [openai.ChatMessage.user(\"What's fourteen times twelve?\")],\n});\n```\n\n#### [Agent Loop](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ftools\u002Fagent-loop)\n\nYou can use `runTools` to implement an agent loop that responds to user messages and executes tools. [Learn more](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ftools\u002Fagent-loop).\n\n### [Vector Indices](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Fvector-index)\n\n```ts\nconst texts = [\n  \"A rainbow is an optical phenomenon that can occur under certain meteorological conditions.\",\n  \"It is caused by refraction, internal reflection and dispersion of light in water droplets resulting in a continuous spectrum of light appearing in the sky.\",\n  \u002F\u002F ...\n];\n\nconst vectorIndex = new MemoryVectorIndex\u003Cstring>();\nconst embeddingModel = openai.TextEmbedder({\n  model: \"text-embedding-ada-002\",\n});\n\n\u002F\u002F update an index - usually done as part of an ingestion process:\nawait upsertIntoVectorIndex({\n  vectorIndex,\n  embeddingModel,\n  objects: texts,\n  getValueToEmbed: (text) => text,\n});\n\n\u002F\u002F retrieve text chunks from the vector index - usually done at query time:\nconst retrievedTexts = await retrieve(\n  new VectorIndexRetriever({\n    vectorIndex,\n    embeddingModel,\n    maxResults: 3,\n    similarityThreshold: 0.8,\n  }),\n  \"rainbow and water droplets\"\n);\n```\n\nAvailable Vector Stores: [Memory](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fvector-index\u002Fmemory), [SQLite VSS](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fvector-index\u002Fsqlite-vss), [Pinecone](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fvector-index\u002Fpinecone)\n\n### [Text Generation Prompt Styles](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ffunction\u002Fgenerate-text#prompt-styles)\n\nYou can use different prompt styles (such as text, instruction or chat prompts) with ModelFusion text generation models. These prompt styles can be accessed through the methods `.withTextPrompt()`, `.withChatPrompt()` and `.withInstructionPrompt()`:\n\n#### Text Prompt Style\n\n```ts\nconst text = await generateText({\n  model: openai\n    .ChatTextGenerator({\n      \u002F\u002F ...\n    })\n    .withTextPrompt(),\n\n  prompt: \"Write a short story about a robot learning to love\",\n});\n```\n\n#### Instruction Prompt Style\n\n```ts\nconst text = await generateText({\n  model: llamacpp\n    .CompletionTextGenerator({\n      \u002F\u002F run https:\u002F\u002Fhuggingface.co\u002FTheBloke\u002FLlama-2-7B-Chat-GGUF with llama.cpp\n      promptTemplate: llamacpp.prompt.Llama2, \u002F\u002F Set prompt template\n      contextWindowSize: 4096, \u002F\u002F Llama 2 context window size\n      maxGenerationTokens: 512,\n    })\n    .withInstructionPrompt(),\n\n  prompt: {\n    system: \"You are a story writer.\",\n    instruction: \"Write a short story about a robot learning to love.\",\n  },\n});\n```\n\n#### Chat Prompt Style\n\n```ts\nconst textStream = await streamText({\n  model: openai\n    .ChatTextGenerator({\n      model: \"gpt-3.5-turbo\",\n    })\n    .withChatPrompt(),\n\n  prompt: {\n    system: \"You are a celebrated poet.\",\n    messages: [\n      {\n        role: \"user\",\n        content: \"Suggest a name for a robot.\",\n      },\n      {\n        role: \"assistant\",\n        content: \"I suggest the name Robbie\",\n      },\n      {\n        role: \"user\",\n        content: \"Write a short story about Robbie learning to love\",\n      },\n    ],\n  },\n});\n```\n\n### [Image Generation Prompt Templates](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ffunction\u002Fgenerate-image\u002Fprompt-format)\n\nYou an use prompt templates with image models as well, e.g. to use a basic text prompt. It is available as a shorthand method:\n\n```ts\nconst image = await generateImage({\n  model: stability\n    .ImageGenerator({\n      \u002F\u002F...\n    })\n    .withTextPrompt(),\n\n  prompt:\n    \"the wicked witch of the west in the style of early 19th century painting\",\n});\n```\n\n| Prompt Template | Text Prompt |\n| --------------- | ----------- |\n| Automatic1111   | ✅          |\n| Stability       | ✅          |\n\n### Metadata and original responses\n\nModelFusion model functions return rich responses that include the raw (original) response and metadata when you set the `fullResponse` argument to `true`.\n\n```ts\n\u002F\u002F access the raw response (needs to be typed) and the metadata:\nconst { text, rawResponse, metadata } = await generateText({\n  model: openai.CompletionTextGenerator({\n    model: \"gpt-3.5-turbo-instruct\",\n    maxGenerationTokens: 1000,\n    n: 2, \u002F\u002F generate 2 completions\n  }),\n  prompt: \"Write a short story about a robot learning to love:\\n\\n\",\n  fullResponse: true,\n});\n\nconsole.log(metadata);\n\n\u002F\u002F cast to the raw response type:\nfor (const choice of (rawResponse as OpenAICompletionResponse).choices) {\n  console.log(choice.text);\n}\n```\n\n### Logging and Observability\n\nModelFusion provides an [observer framework](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Futil\u002Fobserver) and [logging support](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Futil\u002Flogging). You can easily trace runs and call hierarchies, and you can add your own observers.\n\n#### Enabling Logging on a Function Call\n\n```ts\nimport { generateText, openai } from \"modelfusion\";\n\nconst text = await generateText({\n  model: openai.CompletionTextGenerator({ model: \"gpt-3.5-turbo-instruct\" }),\n  prompt: \"Write a short story about a robot learning to love:\\n\\n\",\n  logging: \"detailed-object\",\n});\n```\n\n## Documentation\n\n### [Guide](https:\u002F\u002Fmodelfusion.dev\u002Fguide)\n\n- [Model Functions](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ffunction\u002F)\n  - [Generate text](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ffunction\u002Fgenerate-text)\n  - [Generate object](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ffunction\u002Fgenerate-object)\n  - [Generate image](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ffunction\u002Fgenerate-image)\n  - [Generate speech](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ffunction\u002Fgenerate-speech)\n  - [Generate transcription](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ffunction\u002Fgenerate-transcription)\n  - [Tokenize Text](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ffunction\u002Ftokenize-text)\n  - [Embed Value](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ffunction\u002Fembed)\n  - [Classify Value](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ffunction\u002Fclassify)\n- [Tools](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ftools)\n  - [Run Tool](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ftools\u002Frun-tool)\n  - [Run Tools](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ftools\u002Frun-tools)\n  - [Agent Loop](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ftools\u002Fagent-loop)\n  - [Available Tools](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ftools\u002Favailable-tools\u002F)\n  - [Custom Tools](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ftools\u002Fcustom-tools)\n  - [Advanced](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ftools\u002Fadvanced)\n- [Vector Indices](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Fvector-index)\n  - [Upsert](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Fvector-index\u002Fupsert)\n  - [Retrieve](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Fvector-index\u002Fretrieve)\n- [Text Chunks](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ftext-chunk\u002F)\n  - [Split Text](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ftext-chunk\u002Fsplit)\n- [Utilities](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Futil\u002F)\n  - [API Configuration](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Futil\u002Fapi-configuration)\n    - [Base URL](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Futil\u002Fapi-configuration\u002Fbase-url)\n    - [Headers](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Futil\u002Fapi-configuration\u002Fheaders)\n    - [Retry strategies](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Futil\u002Fapi-configuration\u002Fretry)\n    - [Throttling strategies](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Futil\u002Fapi-configuration\u002Fthrottle)\n  - [Logging](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Futil\u002Flogging)\n  - [Observers](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Futil\u002Fobserver)\n  - [Runs](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Futil\u002Frun)\n  - [Abort signals](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Futil\u002Fabort)\n- [Experimental](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Fexperimental\u002F)\n  - [Guards](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Fexperimental\u002Fguard)\n  - [Server](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Fexperimental\u002Fserver\u002F)\n  - [Cost calculation](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Fexperimental\u002Fcost-calculation)\n- [Troubleshooting](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ftroubleshooting)\n  - [Bundling](https:\u002F\u002Fmodelfusion.dev\u002Fguide\u002Ftroubleshooting\u002Fbundling)\n\n### [Integrations](https:\u002F\u002Fmodelfusion.dev\u002Fintegration\u002Fmodel-provider)\n\n### [Examples & Tutorials](https:\u002F\u002Fmodelfusion.dev\u002Ftutorial)\n\n### [Showcase](https:\u002F\u002Fmodelfusion.dev\u002Ftutorial\u002Fshowcase)\n\n### [API Reference](https:\u002F\u002Fmodelfusion.dev\u002Fapi\u002Fmodules)\n\n## More Examples\n\n### [Basic Examples](https:\u002F\u002Fgithub.com\u002Flgrammel\u002Fmodelfusion\u002Ftree\u002Fmain\u002Fexamples\u002Fbasic)\n\nExamples for almost all of the individual functions and objects. Highly recommended to get started.\n\n### [StoryTeller](https:\u002F\u002Fgithub.com\u002Flgrammel\u002Fstoryteller)\n\n> _multi-modal_, _object streaming_, _image generation_, _text to speech_, _speech to text_, _text generation_, _object generation_, _embeddings_\n\nStoryTeller is an exploratory web application that creates short audio stories for pre-school kids.\n\n### [Chatbot (Next.JS)](https:\u002F\u002Fgithub.com\u002Flgrammel\u002Fmodelfusion\u002Ftree\u002Fmain\u002Fexamples\u002Fchatbot-next-js)\n\n> _Next.js app_, _OpenAI GPT-3.5-turbo_, _streaming_, _abort handling_\n\nA web chat with an AI assistant, implemented as a Next.js app.\n\n### [Chat with PDF](https:\u002F\u002Fgithub.com\u002Flgrammel\u002Fmodelfusion\u002Ftree\u002Fmain\u002Fexamples\u002Fpdf-chat-terminal)\n\n> _terminal app_, _PDF parsing_, _in memory vector indices_, _retrieval augmented generation_, _hypothetical document embedding_\n\nAsk questions about a PDF document and get answers from the document.\n\n### [Next.js \u002F ModelFusion Demos](https:\u002F\u002Fgithub.com\u002Flgrammel\u002Fmodelfusion\u002Ftree\u002Fmain\u002Fexamples\u002Fnextjs)\n\n> _Next.js app_, _image generation_, _transcription_, _object streaming_, _OpenAI_, _Stability AI_, _Ollama_\n\nExamples of using ModelFusion with Next.js 14 (App Router):\n\n- image generation\n- voice recording & transcription\n- object streaming\n\n### [Duplex Speech Streaming (using Vite\u002FReact & ModelFusion Server\u002FFastify)](https:\u002F\u002Fgithub.com\u002Flgrammel\u002Fmodelfusion\u002Ftree\u002Fmain\u002Fexamples\u002Fspeech-streaming-vite-react-fastify)\n\n> _Speech Streaming_, _OpenAI_, _Elevenlabs_ _streaming_, _Vite_, _Fastify_, _ModelFusion Server_\n\nGiven a prompt, the server returns both a text and a speech stream response.\n\n### [BabyAGI Agent](https:\u002F\u002Fgithub.com\u002Flgrammel\u002Fmodelfusion\u002Ftree\u002Fmain\u002Fexamples\u002Fbabyagi-agent)\n\n> _terminal app_, _agent_, _BabyAGI_\n\nTypeScript implementation of the BabyAGI classic and BabyBeeAGI.\n\n### [Wikipedia Agent](https:\u002F\u002Fgithub.com\u002Flgrammel\u002Fmodelfusion\u002Ftree\u002Fmain\u002Fexamples\u002Fwikipedia-agent)\n\n> _terminal app_, _ReAct agent_, _GPT-4_, _OpenAI functions_, _tools_\n\nGet answers to questions from Wikipedia, e.g. \"Who was born first, Einstein or Picasso?\"\n\n### [Middle school math agent](https:\u002F\u002Fgithub.com\u002Flgrammel\u002Fmodelfusion\u002Ftree\u002Fmain\u002Fexamples\u002Fmiddle-school-math-agent)\n\n> _terminal app_, _agent_, _tools_, _GPT-4_\n\nSmall agent that solves middle school math problems. It uses a calculator tool to solve the problems.\n\n### [PDF to Tweet](https:\u002F\u002Fgithub.com\u002Flgrammel\u002Fmodelfusion\u002Ftree\u002Fmain\u002Fexamples\u002Fpdf-to-tweet)\n\n> _terminal app_, _PDF parsing_, _recursive information extraction_, _in memory vector index, \\_style example retrieval_, _OpenAI GPT-4_, _cost calculation_\n\nExtracts information about a topic from a PDF and writes a tweet in your own style about it.\n\n### [Cloudflare Workers](https:\u002F\u002Fgithub.com\u002Flgrammel\u002Fmodelfusion\u002Ftree\u002Fmain\u002Fexamples\u002Fcloudflare-workers)\n\n> _Cloudflare_, _OpenAI_\n\nGenerate text on a Cloudflare Worker using ModelFusion and OpenAI.\n\n## Contributing\n\n### [Contributing Guide](https:\u002F\u002Fgithub.com\u002Flgrammel\u002Fmodelfusion\u002Fblob\u002Fmain\u002FCONTRIBUTING.md)\n\nRead the [ModelFusion contributing guide](https:\u002F\u002Fgithub.com\u002Flgrammel\u002Fmodelfusion\u002Fblob\u002Fmain\u002FCONTRIBUTING.md) to learn about the development process, how to propose bugfixes and improvements, and how to build and test your changes.\n","ModelFusion 是一个用于构建 AI 应用的 TypeScript 库。它提供了一种抽象层，能够将多种 AI 模型集成到 JavaScript 和 TypeScript 应用中，并统一了文本流、对象生成和工具使用的 API 接口。该库支持多模态操作，涵盖文本、图像生成以及语音转换等功能，同时具备类型推断与验证、可观测性和日志记录等特性，以增强应用的健壮性和可靠性。ModelFusion 适用于需要在生产环境中快速部署AI功能的场景，如开发聊天机器人、自动化助手或是任何需要利用AI能力的应用程序。",2,"2026-06-11 03:30:08","top_topic"]