Transformers.js 文本生成实战指南:从基础生成、Token 流式输出到多轮聊天对话
【免费下载链接】skillsGive your agents the power of the Hugging Face ecosystem项目地址: https://gitcode.com/GitHub_Trending/skills7/skills
本指南以transformers-js技能(Skill)中的 TEXT_GENERATION.md 为骨架,系统讲解如何用 Transformers.js 在 JavaScript 中运行文本生成模型:包括基于pipeline的基本生成、TextStreamer流式输出(Node.js / 浏览器 / React 三种形态)、system/user/assistant 结构化聊天格式,以及temperature、top_k、top_p等生成参数的调优方法与模型选择策略。读完本文,你将能够在浏览器或 Node.js 环境中从零搭建一个可流式输出、可多轮对话、可复用与安全释放资源的文本生成应用,无需任何 Python 后端。
本文所有示例均可在当前仓库 skills/transformers-js 目录下对应文档中找到原始出处;配套的 SKILL.md 提供了 Pipeline API、模型选择、量化与设备选择等基础概念,PIPELINE_OPTIONS.md 与 CONFIGURATION.md 提供了加载选项与运行环境的完整参考。
一、环境准备:安装 Transformers.js
Transformers.js 是面向 JavaScript/TypeScript 的机器学习运行时,可在浏览器与服务端运行时(Node.js 18+、Bun、Deno)中直接运行来自 Hugging Face Hub 的预训练模型,支持 WebGPU/WASM 双后端。安装方式有两种(见 SKILL.md 的 Installation 章节):
NPM 安装(Node.js / Bundler 环境):
npm install @huggingface/transformers浏览器 CDN(无需构建工具):
<script type="module"> import { pipeline } from 'https://cdn.jsdelivr.net/npm/@huggingface/transformers@4'; </script>在浏览器中引用时建议像原文档那样锁定主版本(@4),以确保 API 行为一致。运行前提:Node.js 18+ 或兼容的 Bun/Deno 运行时、支持 ES Modules 的现代浏览器;WebGPU 加速需要运行时与硬件支持,WASM 是通用兜底后端;从 Hub 下载模型需要网络连接(可通过本地模型离线运行)。
二、基本生成:一行代码创建文本生成器
Transformers.js 的核心入口是pipeline()函数,它把分词、模型推理与后处理封装成一步调用(参见 SKILL.md 的 "Pipeline API" 一节)。文本生成任务的任务 ID 为text-generation(另见text2text-generation),完整任务 ID 列表在 SKILL.md 的 Quick Reference 中列出。
原文档 TEXT_GENERATION.md 给出的最小可运行示例如下:
import { pipeline } from '@huggingface/transformers'; const generator = await pipeline( 'text-generation', 'onnx-community/Qwen2.5-0.5B-Instruct', { dtype: 'q4' } ); const result = await generator('Once upon a time', { max_new_tokens: 100, temperature: 0.7, }); console.log(result[0].generated_text); // Clean up when done await generator.dispose();要点拆解:
pipeline('text-generation', modelId, options):第一个参数指定任务类型;第二个参数是模型标识(此处为onnx-community/Qwen2.5-0.5B-Instruct,一个 0.5B 参数的指令微调模型);第三个参数{ dtype: 'q4' }用于量化加载,将权重压缩为 4 位整数表示,显著缩小下载体积并提升 CPU/浏览器推理速度。- 生成参数:
max_new_tokens: 100限制最多新生成 100 个 token;temperature: 0.7控制采样随机性。两者都是生成阶段最常用的参数,后面「生成参数完全指南」一节会逐一展开。 - 返回结构:调用结果是一个数组(支持批处理),
result[0].generated_text包含完整的生成文本(提示词 + 新生成内容,除非配合TextStreamer流式输出时以skip_prompt: true跳过)。 - 资源释放:
await generator.dispose()是必须的收尾动作。模型会占用从数百 MB 到数 GB 不等的内存并持有 CPU/GPU 资源(SKILL.md 的 Memory Management 一节对此有专门强调),在浏览器中尤其关系到内存上限与页面稳定性,在长驻服务中关系到服务器稳定性。应至少在应用关闭、组件卸载、加载新模型或完成批量处理之后调用。
三、流式输出:逐 Token 渲染,让交互像聊天一样自然
非流式生成要等全部 token 完成才一次性返回,大模型场景下等待可达数秒甚至更久。流式输出通过TextStreamer在每个 token 生成后立即回调,让界面逐字渲染,显著改善用户体验。TextStreamer的构造与使用在三种运行环境中保持一致:skip_prompt(跳过回显提示词)、skip_special_tokens(跳过<s>、<|endoftext|>等特殊 token)与callback_function(每生成一个 token 调用一次)是三个核心选项。
Node.js:输出到标准输出
import { pipeline, TextStreamer } from '@huggingface/transformers'; const generator = await pipeline( 'text-generation', 'onnx-community/Qwen2.5-0.5B-Instruct', { dtype: 'q4' } ); const streamer = new TextStreamer(generator.tokenizer, { skip_prompt: true, skip_special_tokens: true, callback_function: (token) => { process.stdout.write(token); }, }); await generator('Tell me a story', { max_new_tokens: 200, temperature: 0.7, streamer, });这里的关键是generator.tokenizer:Pipeline 在加载模型时会一并装载对应的 tokenizer,TextStreamer需要它来完成 token 到文本的解码。将streamer作为生成参数传入后,generator()返回前,每个新 token 已经通过回调被写入了标准输出,用户能在终端实时看到文字生成过程。
浏览器:直接操作 DOM
浏览器环境下,只需把callback_function中追加 token 的目标从process.stdout换成 DOM 节点。以下 HTML 是原文档中的完整示例:
<!DOCTYPE html> <html> <body> <textarea id="prompt" placeholder="Enter prompt..."></textarea> <button onclick="generate()">Generate</button> <div id="output"></div> <script type="module"> import { pipeline, TextStreamer } from 'https://cdn.jsdelivr.net/npm/@huggingface/transformers@4'; const generator = await pipeline( 'text-generation', 'onnx-community/Qwen2.5-0.5B-Instruct', { dtype: 'q4' } ); window.generate = async function() { const prompt = document.getElementById('prompt').value; const outputDiv = document.getElementById('output'); outputDiv.textContent = ''; const streamer = new TextStreamer(generator.tokenizer, { skip_prompt: true, skip_special_tokens: true, callback_function: (token) => { outputDiv.textContent += token; }, }); await generator(prompt, { max_new_tokens: 200, temperature: 0.7, streamer, }); }; </script> </body> </html>注意两个浏览器特有细节:其一,import语句前省略了type="module"之外的其他依赖——Transformers.js 的浏览器构建会自行管理 WASM 二进制与模型下载;其二,为了获得更好的加载体验,可以为pipeline()传入progress_callback展示模型下载进度(详见 PIPELINE_OPTIONS.md 的 Progress Callback 一节,以及 EXAMPLES.md 中带进度条的浏览器完整实现)。
React:懒加载模型 + 卸载时自动清理
在 React 中,推荐用useRef缓存 Pipeline 实例(只在首次生成时加载,避免每次渲染重建模型),并在组件卸载时通过useEffect清理函数释放资源。原文档给出了可直接落地的完整组件:
import { useState, useRef, useEffect } from 'react'; import { pipeline, TextStreamer } from '@huggingface/transformers'; function StreamingGenerator() { const generatorRef = useRef(null); const [output, setOutput] = useState(''); const [loading, setLoading] = useState(false); const handleGenerate = async (prompt) => { if (!prompt) return; setLoading(true); setOutput(''); // Load model on first generate if (!generatorRef.current) { generatorRef.current = await pipeline( 'text-generation', 'onnx-community/Qwen2.5-0.5B-Instruct', { dtype: 'q4' } ); } const streamer = new TextStreamer(generatorRef.current.tokenizer, { skip_prompt: true, skip_special_tokens: true, callback_function: (token) => { setOutput((prev) => prev + token); }, }); await generatorRef.current(prompt, { max_new_tokens: 200, temperature: 0.7, streamer, }); setLoading(false); }; // Cleanup on unmount useEffect(() => { return () => { if (generatorRef.current) { generatorRef.current.dispose(); } }; }, []); return ( <div> <button onClick={() => handleGenerate('Tell me a story')} disabled={loading}> {loading ? 'Generating...' : 'Generate'} </button> <div>{output}</div> </div> ); }该模式把「模型加载」「流式回调写状态」「卸载释放」三件事分离:useRef保证模型单例复用;回调中setOutput((prev) => prev + token)利用函数式更新逐 token 累积文本;空依赖的useEffect返回清理函数,在组件卸载时执行dispose(),避免内存泄漏。与 EXAMPLES.md 中EmbeddingGenerator系列的清理模式(beforeunload事件、React 卸载清理、Express 服务 SIGTERM 优雅关闭)相互印证。
四、聊天格式:用 system / user / assistant 组织多轮对话
指令微调(Instruct)模型通常期望输入按照聊天模板组织成结构化消息,而不是一段裸文本。Transformers.js 接受符合 ChatML 习惯的消息数组,role可取system(系统指令)、user(用户输入)、assistant(模型历史回复)。聊天格式与基本生成、流式输出完全兼容——流式只需在生成参数中追加streamer。
单轮对话
import { pipeline } from '@huggingface/transformers'; const generator = await pipeline( 'text-generation', 'onnx-community/Qwen2.5-0.5B-Instruct', { dtype: 'q4' } ); const messages = [ { role: 'system', content: 'You are a helpful assistant.' }, { role: 'user', content: 'How do I create an async function?' } ]; const result = await generator(messages, { max_new_tokens: 256, temperature: 0.7, }); console.log(result[0].generated_text);多轮对话
多轮对话只需把历史消息按时间顺序完整放入数组——每轮新的用户提问都要携带之前的全部轮次,模型才能拥有上下文记忆。原文档的示例:
const conversation = [ { role: 'system', content: 'You are a helpful assistant.' }, { role: 'user', content: 'What is JavaScript?' }, { role: 'assistant', content: 'JavaScript is a programming language...' }, { role: 'user', content: 'Can you show an example?' } ]; const result = await generator(conversation, { max_new_tokens: 200, temperature: 0.7, }); // To add streaming, just pass a streamer: // streamer: new TextStreamer(generator.tokenizer, {...})实操建议:
assistant角色的历史内容必须使用模型自己生成的文本,否则容易产生错误的对话状态。- 上下文窗口:历史越长,占用的输入 token 越多。当模型输入接近上下文上限时,应考虑裁剪早期轮次或截断历史,避免生成被截断或性能下降。
- 与流式组合:
await generator(conversation, { ..., streamer })即可,聊天与流式互不排斥。
五、生成参数完全指南
生成参数在generator(prompt, params)的第二个参数中传递。原文档将常用参数按用途分为四组,下面完整保留并补充解释。
5.1 常用参数一览
await generator(prompt, { // Token limits max_new_tokens: 512, // Maximum tokens to generate min_new_tokens: 0, // Minimum tokens to generate // Sampling temperature: 0.7, // Randomness (0.0-2.0) top_k: 50, // Consider top K tokens top_p: 0.95, // Nucleus sampling do_sample: true, // Use random sampling (false = always pick most likely token) // Repetition control repetition_penalty: 1.0, // Penalty for repeating (1.0 = no penalty) no_repeat_ngram_size: 0, // Prevent repeating n-grams // Streaming streamer: streamer, // TextStreamer instance });各参数含义与影响:
| 参数 | 含义 | 取值建议 |
|---|---|---|
max_new_tokens | 最多新生成的 token 数,防止失控生成 | 按应用场景设置,如 100–512 |
min_new_tokens | 至少生成多少个 token 才允许结束 | 默认0;摘要等场景可设下限 |
temperature | 采样温度,控制随机性 | 0.0–2.0,见 5.2 |
top_k | 只在概率最高的 K 个 token 中采样 | 常见50 |
top_p | 核采样:累积概率达到 p 的最小 token 集合内采样 | 常见0.9–0.95 |
do_sample | true使用随机采样;false退化为贪心解码,每步取概率最高 token | 需要确定性输出时设false |
repetition_penalty | 对已出现 token 的惩罚系数,1.0表示无惩罚 | 抑制重复可设1.1–1.3 |
no_repeat_ngram_size | 禁止生成与历史 n-gram 重复的序列 | 0表示不限制;设3可显著减少短语级重复 |
streamer | TextStreamer实例,启用逐 token 回调 | 见第三节 |
5.2 Temperature:从确定性到创造性的滑杆
原文档给出三档经验区间:
- 低(0.1–0.5):输出更聚焦、更确定,适合事实性回答、代码生成、抽取任务;
- 中(0.6–0.9):创造性与连贯性平衡,通用对话、写作的默认区间;
- 高(1.0–2.0):更富创意也更随机,适合头脑风暴、故事创作,但可能牺牲连贯性。
// Focused output await generator(prompt, { temperature: 0.3, max_new_tokens: 100 }); // Creative output await generator(prompt, { temperature: 1.2, max_new_tokens: 100 });5.3 采样方法:贪心、Top-k 与 Top-p
三种典型解码策略及其代码形态(均摘自原文档):
// Greedy (deterministic) await generator(prompt, { do_sample: false, max_new_tokens: 100 }); // Top-k sampling await generator(prompt, { top_k: 50, temperature: 0.7, max_new_tokens: 100 }); // Top-p (nucleus) sampling await generator(prompt, { top_p: 0.95, temperature: 0.7, max_new_tokens: 100 });- 贪心(
do_sample: false):每一步固定选取概率最高的 token,输出可复现、稳定,但易陷入重复与单调; - Top-k(
top_k: 50):先截断到概率最高的 50 个候选再采样,可避免采样到极低概率的荒谬 token; - Top-p(
top_p: 0.95):动态选取累积概率达到 95% 的最小候选集,候选集大小随概率分布自适应,是当前最主流的采样方式之一。
5.4 通过config覆盖默认生成参数
除每次调用传参外,还可以在pipeline()的第三个参数中用config覆盖模型自带的默认生成配置,从而对整条 Pipeline 生效(参见 PIPELINE_OPTIONS.md 的 Custom Configuration 一节):
const pipe = await pipeline('text-generation', 'model-id', { config: { max_length: 512, temperature: 0.8, // ... other config options } });该方式适用于:覆盖模型仓库generation_config.json中的默认生成参数、针对特定任务做全局微调、以及在不动模型文件的前提下对比不同配置。
六、模型选择:为浏览器与服务器挑选合适的生成模型
文本生成模型可从 Hugging Face Hub 的模型检索页按任务与库双重过滤(pipeline_tag=text-generation与library=transformers.js,按 trending/downloads/likes/modified 排序;原文档直接给出了这一检索入口,SKILL.md 的 Finding Models 一节还提供了更多任务的过滤方式)。本文不展开外部链接,实际操作时在 Hub 搜索框组合这两个过滤条件即可。确认模型兼容性的关键是:模型仓库中存在onnx/文件夹(含 ONNX 格式权重),这是 Transformers.js 能直接运行的前提。
6.1 按参数规模与运行环境选择
原文档给出按模型规模的选型建议:
| 规模 | 特征 | 推荐 dtype |
|---|---|---|
| 小型模型(< 1B 参数) | 快速、浏览器友好 | dtype: 'q4' |
| 中型模型(1–3B 参数) | 质量与速度均衡 | dtype: 'q4'或fp16 |
| 大型模型(> 3B 参数) | 质量高、速度慢 | 最适合 Node.js,dtype: 'fp16' |
dtype是加载时指定的权重精度(详见 PIPELINE_OPTIONS.md 的 Data Type 一节与 SKILL.md 的 Quantization Options 一节),可选值包括fp32(全精度,最大最准)、fp16(半精度,体积与精度均衡)、q8(8 位量化,体积小、速度快)、q4(4 位量化,体积最小、速度最快)。其取舍关系可概括为:精度fp32 > fp16 > q8 > q4,速度与体积则相反。浏览器/边缘设备优先q4/q8,服务器端(Node.js)可用fp16换取更高生成质量;WebGPU 环境下可尝试device: 'webgpu'配合dtype: 'fp16'获取 GPU 加速(SKILL.md 的 WebGPU Usage 一节建议 GPU 不可用时回退 WASM/CPU)。
6.2 模型卡检查清单
选型时(原文档明确列出)应核对模型卡中的:
- 参数数量与模型体积:决定下载大小、内存占用与推理速度;
- 支持语言:多语言 vs 仅英文;
- 基准分数(Benchmark):作为质量横向对比的参考;
- 许可证限制:确认是否允许商用与部署场景合规。
补充一点来自 MODEL_ARCHITECTURES.md 的架构参考:文本生成相关支持包括 GPT-2、GPT-Neo、GPT-NeoX、CodeGen、CodeLlama、LLaMA、Mistral、Cohere、T5、BART、Gemma 等架构;同时支持dtype按组件分别指定(如 encoder 用fp16、decoder 用q8),详见 PIPELINE_OPTIONS.md 的 Per-Component 配置。文中示例使用的onnx-community/Qwen2.5-0.5B-Instruct是 Hub 上按library=transformers.js过滤后可直接获取的 ONNX 指令模型;SKILL.md 中另以onnx-community/gemma-3-270m-it-ONNX作为推荐示例,两者选其一即可。
6.3 版本固定与模型仓库结构
revision:生产环境建议固定模型版本(git 分支、tag 或 commit hash),例如{ revision: 'v1.0.0' },不同 revision 会独立缓存(PIPELINE_OPTIONS.md 的 Model Revision 一节)。subfolder与model_file_name:模型仓库结构非标准时,可指定subfolder: 'onnx'(默认)或自定义model_file_name(如 encoder-decoder 模型拆分的decoder_model_merged),详见同文档。
七、进阶配置:加载进度、本地模型与错误处理
7.1 展示模型下载进度
文本生成模型体积从几 MB 到数 GB 不等,且由多个文件组成。通过progress_callback可跟踪端到端与逐文件进度,推荐优先使用progress_total状态展示整体进度(PIPELINE_OPTIONS.md 的 Progress Callback 一节给出了浏览器 UI 的完整实现):
const fileProgress = {}; const pipe = await pipeline('text-generation', 'model-id', { progress_callback: (info) => { // Recommended: end-to-end loading progress if (info.status === 'progress_total') { console.log(`Total: ${info.progress.toFixed(1)}%`); return; } // Optional: per-file progress if (info.status === 'progress') { fileProgress[info.file] = info.progress; console.log(`${info.file}: ${info.progress.toFixed(1)}%`); } if (info.status === 'done') { console.log(`✓ ${info.file} complete`); } } });ProgressInfo的主要字段:status(initiate/download/progress/progress_total/done/ready)、name(模型 id 或路径)、file(正在处理的文件)、progress(0–100 百分比)、loaded/total(已下载/总字节数)。CLI 进度条、React 进度条等更多形态见 EXAMPLES.md。
7.2 离线部署与缓存策略
生产环境可以完全切断运行时下载:用env配置本地模型路径并禁用远程加载(CONFIGURATION.md 的 Production (Local Models) 模式):
import { env, pipeline } from '@huggingface/transformers'; env.allowRemoteModels = false; env.allowLocalModels = true; env.localModelPath = '/app/models/'; env.useFSCache = false; // Models already local浏览器默认useBrowserCache = true(Cache API),Node.js 默认useFSCache = true(目录默认./.cache),模型会自动缓存、重复加载免下载;自定义缓存目录、自定义env.fetch注入鉴权头等高级用法参见 CONFIGURATION.md 与 CACHE.md。注意env配置必须在加载任何模型之前完成,否则可能不生效。
7.3 错误处理
网络中断、模型不兼容等场景应显式捕获(SKILL.md 的 Error Handling 一节提供了分支处理思路):
try { const pipe = await pipeline('text-generation', 'model-id'); const result = await pipe('text to generate'); } catch (error) { if (error.message.includes('fetch')) { console.error('Model download failed. Check internet connection.'); } else if (error.message.includes('ONNX')) { console.error('Model execution failed. Check model compatibility.'); } else { console.error('Unknown error:', error); } }八、最佳实践清单
综合原文档与仓库其余参考文档(SKILL.md 的 Best Practices、Performance Tips、Memory Management 各节),文本生成应用的落地要点如下:
- 按环境选择模型精度:浏览器用量化模型(
q4),服务器用更大的模型(fp16),兼顾体积、速度与质量; - 始终启用流式输出:
TextStreamer让用户看到生成过程,交互体感更流畅; - 设置 Token 上限:通过
max_new_tokens防止失控生成与显存/内存暴涨; - 按用途调温度:创意类
0.8–1.2,事实类0.3–0.7,需要确定性输出时do_sample: false; - 及时释放内存:完成生成后调用
dispose(),React 组件在卸载时清理,服务端在 SIGTERM/SIGINT 时优雅释放; - 复用 Pipeline 实例:模型加载一次、多次推理,不要为每次请求重复创建 Pipeline(React 中用
useRef,服务端在启动时初始化,参考 EXAMPLES.md 的 Express API 示例); - 多轮对话携带历史:按 system/user/assistant 顺序维护消息数组,控制上下文长度避免超出窗口;
- 生产固定版本:用
revision固定模型版本,用local_files_only: true或env.allowRemoteModels = false避免运行时下载波动; - 展示加载进度:大模型下载用
progress_callback反馈进度,配合加载态提示; - 显式错误边界:Pipeline 创建与生成调用都包裹 try-catch,针对网络与 ONNX 兼容性给出可读提示。
九、相关文档导航
- Pipeline Options —— 配置 pipeline 加载(
progress_callback、device、dtype、revision、session_options等) - Configuration Reference ——
env全局环境配置(远程/本地模型、缓存、WASM、日志) - Code Examples —— 浏览器、Node.js、React、Express API 的完整运行示例
- Model Architectures —— 支持的全部模型架构与按任务选型建议
- Caching Reference —— 浏览器 Cache API、Node.js 文件系统缓存与自定义缓存
- Main Skill Guide —— Transformers.js 入门总览:Pipeline API、量化、设备选择、任务 ID 表
【免费下载链接】skillsGive your agents the power of the Hugging Face ecosystem项目地址: https://gitcode.com/GitHub_Trending/skills7/skills
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考