1. 项目概述与核心价值如果你和我一样长期在Node.js生态里折腾AI应用那你肯定对Vercel AI SDK不陌生。它确实是个好东西把调用各种大模型的复杂逻辑封装得明明白白。但最近OpenAI放了个大招推出了Codex CLI——一个能让你在终端里直接调用GPT-5.1/5.2系列模型并且具备文件读写、代码执行等“动手能力”的命令行工具。这玩意儿潜力巨大但问题来了AI SDK原生并不支持这个新玩家。难道我们要为了用Codex CLI放弃AI SDK那套优雅的generateText、streamTextAPI回头去自己拼凑子进程调用和JSON-RPC解析吗这就是ai-sdk-provider-codex-cli这个社区项目诞生的原因。它精准地填补了这块空白作为一个AI SDK v6的Provider提供者让你能像调用OpenAI API或Anthropic Claude一样无缝地在你的Node.js应用里集成Codex CLI的能力。简单来说它把Codex CLI这个“终端猛兽”驯化成了AI SDK生态里一个温顺且强大的成员。这个Provider最核心的价值在于统一与简化。它提供了两种集成模式一种是每次调用都启停一个Codex进程的codexExec模式适合简单、独立的任务另一种是维护一个持久化JSON-RPC连接的codexAppServer模式支持真正的流式输出和可保持状态的会话线程适合构建复杂的交互式AI助手。无论哪种模式你都能继续享受AI SDK带来的类型安全、统一的错误处理和丰富的工具函数如Zod对象生成而无需关心底层是codex exec还是codex app-server命令的细节。2. 架构设计与模式选型这个Provider的设计非常务实直接对应了Codex CLI的两种主要使用方式。理解这两种模式的本质区别是做出正确技术选型的关键。2.1 执行器模式codexExeccodexExec模式或者说通过createCodexExec工厂函数创建的模型其工作方式非常直接每次调用AI SDK的生成函数如generateText时它都会在背后启动一个新的codex exec子进程。任务完成后这个进程立即退出。它的工作原理是这样的你调用generateText({ model, prompt })。Provider将你的请求包括消息、工具调用等转换为Codex CLI能理解的参数和标准输入。它使用Node.js的child_process.spawn启动一个codex exec --experimental-json ...进程。Provider监听这个进程的stdout解析其输出的实验性JSON事件流。当捕获到最终的item.completed事件包含完整的助手回复或工具执行结果后Provider整理数据返回给AI SDK。子进程退出临时文件被清理。这种模式的优势在于简单纯粹没有长期运行的进程没有连接状态管理每个请求都是独立的。这在无服务器Serverless环境或简单的脚本中非常友好因为不存在跨请求的资源泄漏问题。强隔离性每个请求都在全新的进程中执行配置如工作目录、环境变量完全独立相互之间绝无干扰。启动快速对于冷启动场景它和直接运行codex命令的开销几乎一致。但代价也很明显无流式输出由于codex exec --experimental-json目前截至我撰写时只会在生成完全结束后输出item.completed事件因此streamText()函数虽然能用但你收到的是整个回复作为一个“大块”而不是逐词蹦出的体验。这对于需要实时反馈的对话应用来说是个硬伤。性能开销频繁的进程创建和销毁尤其是模型加载会带来额外的延迟和资源消耗。不适合高并发或高频调用的场景。无状态会话每次调用都是全新的开始无法维持一个连贯的、带有历史消息的对话线程。实操心得我通常把codexExec模式用在CI/CD流水线中的自动化任务、一次性数据处理脚本或者简单的CLI工具里。比如一个在代码提交前自动运行codex检查代码规范的钩子脚本用这种模式就非常合适——任务明确执行完即退出。2.2 应用服务器模式codexAppServercodexAppServer模式则采用了完全不同的思路。它通过createCodexAppServer创建一个Provider实例这个实例在内部会启动并维护一个持久的codex app-server后台进程。这个进程以JSON-RPC服务器的方式运行你的所有请求都通过WebSocket或HTTP连接到这个服务器进行。它的工作流程是你调用createCodexAppServer()Provider在后台启动codex app-server进程并等待其就绪。该进程持续监听等待连接。当你通过provider(gpt-5.3-codex)获取模型并调用AI SDK函数时Provider会通过JSON-RPC客户端向这个持久化进程发送请求。codex app-server处理请求并可以通过item/agentMessage/delta等事件实时流式返回生成的文本。Provider将这些事件转换为AI SDK的流式部件text-delta实现真正的逐词输出。请求结束后连接可复用服务器进程继续运行以处理下一个请求。这种模式的核心优势真正的流式输出这是选择此模式最强烈的理由。你能看到模型一个字一个字地生成内容极大地提升了交互应用的体验。高性能与低延迟避免了每次请求的进程启动和模型加载开销。一旦服务器启动后续请求的响应速度非常快特别适合聊天机器人等交互式应用。有状态线程你可以获取并传递threadId让多个请求在同一个对话上下文中进行实现连贯的多轮对话。这是构建复杂助手的基础。远程图像支持在此模式下你可以直接使用HTTP/HTTPS图片URL作为多模态输入而codexExec模式只支持本地图片数据。当然它也更复杂生命周期管理你需要显式地调用provider.close()来关闭服务器进程否则它可能会一直运行。必须妥善处理应用退出时的资源清理。状态管理虽然提供了有状态线程的能力但你也需要自己管理这些threadId的存储和传递。单点问题这个持久化进程如果意外崩溃会影响所有后续请求。Provider内部有重连机制但仍需考虑健壮性。避坑指南在开发codexAppServer应用时一定要用try...catch...finally块或在进程退出信号监听器中确保调用close()。我曾因为忘记关闭在开发时跑了一堆僵尸codex进程把机器内存都吃满了。另外对于生产环境考虑将createCodexAppServer实例封装成一个单例或通过依赖注入管理避免重复创建。2.3 如何选择提供一个简单的决策矩阵特性/需求codexExec(执行器模式)codexAppServer(应用服务器模式)使用场景脚本、自动化任务、CLI工具、Serverless函数交互式应用、聊天机器人、长期运行的服务流式输出不支持单次返回支持真正逐词流性能每次调用有启动开销首次启动后延迟低状态管理无状态支持有状态线程(threadId)资源管理简单自动清理需手动管理进程生命周期图像输入仅本地文件/Buffer支持本地和远程URL复杂度低中高我的经验法则如果你的应用需要与用户实时交互或者需要多次在同一个上下文里对话毫不犹豫选codexAppServer。如果只是跑个一次性任务codexExec更轻量省心。3. 从零开始的完整配置与实操理论讲完了我们动手搭一个。假设我们要构建一个内部用的代码审查助手它需要流式响应和上下文记忆所以我们选择codexAppServer模式。3.1 环境准备与安装首先确保你的环境符合要求Node.js: 版本 18。建议用LTS版本我用的是20.x。Codex CLI: 需要 0.105.0。这是支持app-server所有特性的关键版本。# 1. 全局安装或更新Codex CLI npm install -g openai/codexlatest # 检查版本 codex --version # 2. 登录认证。这会在 ~/.codex/auth.json 存储OAuth令牌。 # 如果你更喜欢用API Key可以跳过这步后面设置环境变量。 codex login # 按照提示在浏览器中完成OAuth授权。 # 3. 在你的项目目录中初始化并安装AI SDK v6和本Provider。 # 假设你已有package.json如果没有先运行 npm init -y npm install ai ai-sdk-provider-codex-cli注意事项codex login是首选认证方式因为它关联的是你的ChatGPT Plus/Pro订阅通常有更高的配额和权限。如果你在CI/CD等无头环境运行则需要通过环境变量OPENAI_API_KEY提供标准的OpenAI API Key。Provider的env配置项可以帮你把变量传递给子进程。3.2 基础应用搭建我们来创建一个最简单的、支持流式输出的聊天循环。// file: simple-chat.mjs import { streamText } from ai; import { createCodexAppServer } from ai-sdk-provider-codex-cli; import readline from readline/promises; // 1. 创建App Server Provider实例 const provider createCodexAppServer({ defaultSettings: { // 设置自动审批策略为“失败时询问”沙箱模式为“仅工作区可写”平衡安全与自动化 autoApprove: false, // 设置为 true 则完全自动批准慎用 personality: pragmatic, // 模型人格设为“务实” }, }); // 2. 创建模型实例指定使用 gpt-5.3-codex 模型 const model provider(gpt-5.3-codex); // 3. 创建交互式命令行接口 const rl readline.createInterface({ input: process.stdin, output: process.stdout, }); console.log(代码审查助手已启动 (输入 exit 退出)); let currentThreadId null; // 用于保存对话线程ID async function chatLoop() { while (true) { const userInput await rl.question(\n你: ); if (userInput.toLowerCase() exit) { break; } console.log(\n助手: ); try { const result await streamText({ model, prompt: userInput, // 如果存在之前的threadId则传入以继续对话 providerOptions: currentThreadId ? { codex-app-server: { threadId: currentThreadId } } : undefined, }); let fullResponse ; for await (const chunk of result.textStream) { process.stdout.write(chunk); // 流式输出到控制台 fullResponse chunk; } console.log(); // 换行 // 关键步骤从返回的元数据中提取本次对话的threadId供下次使用 if (result.providerMetadata?.[codex-app-server]?.threadId) { currentThreadId result.providerMetadata[codex-app-server].threadId; // console.log([调试] 线程ID已更新: ${currentThreadId}); // 调试时可打开 } } catch (error) { console.error(\n请求出错:, error.message); // 某些错误可能导致线程无效这里简单重置 currentThreadId null; } } } // 启动聊天循环并在退出时清理资源 chatLoop() .catch(console.error) .finally(async () { rl.close(); await provider.close(); // 非常重要关闭后台Codex进程。 console.log(助手已退出。); });运行这个脚本node simple-chat.mjs。你会看到模型一个字一个字地生成回复并且你后续的提问会基于之前的对话历史因为threadId被传递了。这就是codexAppServer模式的核心魅力。3.3 高级配置详解上面的例子用了默认配置。但在实际项目中尤其是生产环境你需要更精细的控制。Provider提供了丰富的配置项主要分为两大类通用设置和App Server专属设置。3.3.1 通用设置CodexCliSettings这些设置对codexExec和codexAppServer都有效通常在创建模型或Provider时传入。import { codexExec, createCodexAppServer } from ai-sdk-provider-codex-cli; // 示例一个配置较全的 codexExec 模型 const robustExecModel codexExec(gpt-5.2-codex, { // 基础路径与回退 cwd: process.cwd(), // Codex进程的工作目录 allowNpx: true, // 如果系统PATH里找不到codex自动尝试用 npx -y openai/codex codexPath: /usr/local/bin/codex, // 显式指定codex二进制路径优先级最高 // 安全与权限控制自动化场景的关键 skipGitRepoCheck: true, // 忽略“是否在Git仓库中”的检查适用于CI或非Git项目 approvalMode: on-failure, // 审批策略always(总是问), on-failure(失败时问), never(从不问危险!) sandboxMode: workspace-write, // 沙箱模式none(无限制), workspace-write(仅工作区可写), read-only(只读) // 警告以下选项会完全绕过审批和沙箱仅在你完全信任上下文时使用 // dangerouslyBypassApprovalsAndSandbox: true, // 文件系统访问 addDirs: [/tmp/shared-data, ../config], // 允许Codex访问这些额外目录 // 输出控制 color: auto, // 输出颜色always, never, auto outputLastMessageFile: /tmp/codex_last_msg.txt, // 自定义最后消息输出文件路径默认用临时文件 // 日志记录 (v0.5.0) verbose: false, // 设为true会打印大量debug/info日志用于排错 // logger: false, // 完全禁用所有日志 // 或传入自定义日志器集成Winston/Pino等 logger: { debug: (msg) console.debug([DEBUG] ${msg}), info: (msg) console.info([INFO] ${msg}), warn: (msg) console.warn([WARN] ${msg}), error: (msg) console.error([ERROR] ${msg}), }, // 环境变量传递 env: { ...process.env, MY_CUSTOM_VAR: value, // OPENAI_API_KEY: sk-..., // 可以在这里覆盖API Key }, }); // 对于 createCodexAppServer通用设置放在 defaultSettings 里 const appServerProvider createCodexAppServer({ defaultSettings: { // 上述所有通用设置同样适用 allowNpx: true, skipGitRepoCheck: true, approvalMode: on-failure, sandboxMode: workspace-write, verbose: process.env.NODE_ENV development, }, });3.3.2 App Server 专属设置这些是createCodexAppServer独有的配置用于控制持久化服务器的行为。const appServerProvider createCodexAppServer({ defaultSettings: { // 连接与超时 connectionTimeoutMs: 30000, // 初始化连接超时毫秒 requestTimeoutMs: 120000, // 单个JSON-RPC请求超时 idleTimeoutMs: 600000, // 服务器闲置10分钟后自动关闭 // 版本与兼容性 minCodexVersion: 0.105.0, // 要求的最低Codex CLI版本 // 线程与状态管理 threadMode: stateless, // stateless(默认新线程) 或 persistent(自动复用线程) persistExtendedHistory: true, // 请求服务器持久化扩展历史如果支持 // 高级调试 includeRawChunks: false, // 设为true会在流中包含原始的JSON-RPC事件用于深度调试 // 服务器端请求处理器 serverRequests: { // 当Codex请求用户批准时如 approval_policyon-request这个函数会被调用 approval_request: async ({ request, session }) { console.log([审批请求] 动作: ${request.params.action}); // 这里可以实现自定义审批逻辑例如弹出UI或查询数据库 // 返回 approved, rejected, 或 pending等待后续决定 return approved; // 示例自动批准 }, // 可以处理其他类型的服务器请求... }, // 会话创建回调 onSessionCreated: (session) { // session对象可用于后续向该线程注入消息或中断生成 // 例如mySessions.set(session.threadId, session); }, }, });3.4 工具流式调用与监控Codex CLI的强大之处在于它能自主调用工具执行命令、读写文件、搜索网络等。从v0.3.0开始Provider提供了全面的工具流式支持让你能实时监控这些操作。import { streamText } from ai; import { codexExec } from ai-sdk-provider-codex-cli; const model codexExec(gpt-5.3-codex, { allowNpx: true, skipGitRepoCheck: true, }); const result await streamText({ model, prompt: 请检查当前目录下package.json的内容并列出其依赖项。, }); console.log(开始执行监听工具调用...\n); for await (const part of result.fullStream) { switch (part.type) { case text-delta: // 文本流在app-server模式下是逐词的exec模式下是整个文本 process.stdout.write(part.textDelta); break; case tool-call: // 工具被调用Codex开始执行一个动作。 console.log(\n[工具调用] 名称: ${part.toolName}); console.log( 参数: ${JSON.stringify(part.args, null, 2)}); // 注意providerExecuted 为 true表示由Codex自主执行我们无需处理。 break; case tool-result: // 工具执行完成返回结果。 console.log(\n[工具结果] 工具: ${part.toolName}); console.log( 结果类型: ${part.result.type}); if (part.result.type output) { console.log( 输出: ${part.result.output.substring(0, 200)}...); // 截断长输出 } else if (part.result.type output-delta) { // 在app-server模式下可能会收到输出流 console.log( 输出增量: ${part.result.delta}); } break; case finish: console.log(\n\n[完成] 原因: ${part.finishReason}); console.log( 使用情况: ${JSON.stringify(part.usage)}); break; } }运行这段代码你会清晰地看到Codex如何一步步解析你的指令调用fs.readFile或类似工具读取package.json再调用某个分析工具列出依赖。这种透明度对于调试复杂的自动化工作流至关重要。实操心得在开发涉及文件操作的AI助手时务必开启工具流监控。我曾经遇到过Codex误删临时文件的情况通过实时日志很快定位到了问题所在并在approvalMode中设置了更严格的策略如on-failure避免了生产事故。4. 图像输入、对象生成与高级特性4.1 多模态图像输入Codex CLI支持视觉模型。Provider允许你以多种格式提供图像。import { generateText } from ai; import { codexExec } from ai-sdk-provider-codex-cli; import { readFileSync } from fs; import { fileURLToPath } from url; const model codexExec(gpt-5.3-codex, { allowNpx: true }); // 方式1直接读取文件为Buffer最常用 const imageBuffer readFileSync(./screenshot.png); const result1 await generateText({ model, messages: [{ role: user, content: [ { type: text, text: 描述这张图片中的主要内容。 }, { type: image, image: imageBuffer, mimeType: image/png }, ] }], }); // 方式2使用Base64字符串 const base64String imageBuffer.toString(base64); const result2 await generateText({ model, messages: [{ role: user, content: [ { type: text, text: 这张图是什么风格 }, // 可以带 data URL 前缀 { type: image, image: data:image/png;base64,${base64String} }, // 也可以不带 // { type: image, image: base64String }, ] }], }); console.log(result1.text); console.log(result2.text);重要区别codexExec模式只支持本地图像数据Buffer/Base64。Provider会将其写入临时文件并通过--image参数传递给CLI。codexAppServer模式除了支持本地数据还支持直接传递HTTP/HTTPS图片URL。Provider会将URL直接转发给app-server效率更高。// 仅在 codexAppServer 模式下有效 const result3 await generateText({ model: appServerModel, messages: [{ role: user, content: [ { type: text, text: 分析这张网络图片。 }, { type: image, image: https://example.com/chart.png }, ] }], });4.2 使用Zod生成结构化对象这是AI SDK的一大亮点Provider完美支持。它能将模型的输出自动匹配并验证为你定义的Zod模式比在提示词里描述JSON格式更可靠、更省Token。import { generateObject } from ai; import { z } from zod; import { createCodexAppServer } from ai-sdk-provider-codex-cli; const provider createCodexAppServer(); const model provider(gpt-5.3-codex); // 1. 定义你的数据结构模式 const IssueSchema z.object({ title: z.string().describe(问题的简短标题), description: z.string().describe(问题的详细描述), severity: z.enum([low, medium, high, critical]).describe(严重等级), category: z.enum([bug, feature, documentation, performance]).describe(问题类别), // 注意OpenAI严格模式不支持 .optional()所有字段必须是 required relatedFiles: z.array(z.string()).describe(相关的代码文件路径列表), }); const codeSnippet function calculateTotal(items) { let total 0; for (let i 0; i items.length; i) { // 潜在错误 导致越界 total items[i].price; } return total; } ; try { const { object, usage } await generateObject({ model, schema: IssueSchema, prompt: 分析以下代码片段识别其中的问题并按照定义的结构输出。代码\n${codeSnippet}, // providerOptions: { ... } // 可以在这里覆盖线程ID等设置 }); console.log(生成的结构化问题报告:); console.log(JSON.stringify(object, null, 2)); console.log(\nToken使用情况: ${JSON.stringify(usage)}); } catch (error) { if (error instanceof z.ZodError) { console.error(生成的对象不符合模式:, error.errors); } else { console.error(请求失败:, error); } } finally { await provider.close(); }关于Zod模式的限制重要 OpenAI的严格模式strict: true对JSON Schema有约束。Provider在转换Zod模式时会自动处理但你需要知道所有字段必须是必填的不能使用.optional()。如果字段可能不存在考虑用空数组[]、空字符串或使用联合类型。某些校验器会被移除如.email()、.url()、.uuid()、.regex()。这些格式校验不会传递给模型。你应该在describe()中说明格式要求并在收到数据后自己再做验证。使用describe()为每个字段添加清晰的描述这能极大提高模型输出的准确性。4.3 模型参数与高级选项v0.4.0Provider允许你精细控制Codex CLI的底层参数。import { codexExec } from ai-sdk-provider-codex-cli; const advancedModel codexExec(gpt-5.3-codex, { allowNpx: true, // 推理与输出控制 reasoningEffort: high, // 控制模型思考深度none, minimal, low, medium, high, xhigh reasoningSummary: auto, // 推理摘要auto, detailed modelVerbosity: medium, // 模型输出详细程度low, medium, high // 功能开关 webSearch: true, // 启用网络搜索功能如果模型支持 profile: production, // 使用特定的Codex配置集 // 集成MCP (Model Context Protocol) 服务器 mcpServers: { // 一个通过stdio通信的本地MCP工具服务器 my-local-tools: { transport: stdio, command: node, args: [./my-mcp-server.js], env: { SECRET_KEY: process.env.TOOLS_SECRET }, }, // 一个远程HTTP MCP服务器 company-docs: { transport: http, url: https://mcp.internal.company.com, bearerTokenEnvVar: MCP_BEARER_TOKEN, // 从该环境变量读取token }, }, // 直接覆盖Codex CLI的 -c 配置参数 configOverrides: { experimental_resume: /tmp/debug_session.jsonl, sandbox_workspace_write.network_access: true, // 允许工作区沙箱内的网络访问 }, });更灵活的是“按调用覆盖”你可以在每次调用AI SDK函数时通过providerOptions临时改变某些设置而无需创建新模型。import { generateText } from ai; const baseModel codexExec(gpt-5.3-codex, { reasoningEffort: medium }); // 这次调用需要更深入的思考 const deepAnalysis await generateText({ model: baseModel, prompt: 分析这份复杂架构图的潜在瓶颈。, providerOptions: { codex-cli: { reasoningEffort: xhigh, // 临时提升推理强度 modelVerbosity: high, // 临时要求更详细输出 }, }, }); // 下次调用恢复构造模型时的默认设置medium const simpleTask await generateText({ model: baseModel, prompt: 打个招呼。, // 不提供 providerOptions使用默认的 medium });这种设计非常优雅允许你在共享基础配置的同时针对特定任务进行微调。5. 故障排查与最佳实践即使配置得当在实际集成中也可能遇到问题。以下是我在实践中总结的常见陷阱和解决方法。5.1 常见问题速查表问题现象可能原因解决方案Error: spawn codex ENOENT1. Codex CLI未安装。2. 未在PATH中且未设置allowNpx: true。1. 运行npm i -g openai/codex。2. 设置allowNpx: true或指定codexPath。Error: Authentication failed1. 未登录且未设置OPENAI_API_KEY。2. Token过期。1. 运行codex login或设置env: { OPENAI_API_KEY: sk-... }。2. 重新运行codex login。流式输出不“流”(Exec模式)codex exec --experimental-json目前只输出最终结果。这是当前限制。如需真流式必须使用codexAppServer模式。工具调用被挂起approvalMode设置为always或on-failure且未处理审批请求。1. 在codexAppServer的serverRequests中实现approval_request处理器。2. 或根据场景将approvalMode设为never慎用。3. 使用autoApprove: true(App Server)。skipGitRepoCheck相关错误在非Git目录中运行且未启用此选项。设置skipGitRepoCheck: true。Zod对象生成失败1. 模式中包含可选字段或特定校验器。2. 模型未按模式生成。1. 确保所有字段required移除email(),url(),regex()。2. 用describe()加强字段描述捕获ZodError做降级处理。App Server 进程不退出未调用provider.close()。确保在应用退出前调用await provider.close()。使用finally块。内存使用过高1. 长时间运行线程历史积累。2. 未清理的App Server实例。1. 定期重启Provider或监控内存。2. 确保实现正确的关闭逻辑。5.2 调试与日志当问题复杂时启用详细日志是首选。const model codexExec(gpt-5.3-codex, { allowNpx: true, verbose: true, // 开启详细日志 logger: { // 你也可以集成到现有日志系统 debug: (msg) myLogger.debug({ source: codex-provider }, msg), info: (msg) myLogger.info({ source: codex-provider }, msg), warn: (msg) myLogger.warn({ source: codex-provider }, msg), error: (msg) myLogger.error({ source: codex-provider }, msg), }, });开启verbose: true后你会在控制台看到进程启动命令、发送的JSON-RPC请求、接收的原始事件等对排查通信问题极有帮助。5.3 安全最佳实践最小权限原则永远从最严格的沙箱开始sandboxMode: read-only或workspace-write。仅在明确需要时添加addDirs或放宽沙箱。谨慎使用自动审批approvalMode: never和dangerouslyBypassApprovalsAndSandbox: true非常危险。在自动化流水线中可考虑结合on-failure和自定义的approval_request处理器实现基于规则的白名单自动批准。隔离工作目录为不同的任务设置不同的cwd防止任务间相互干扰。管理敏感信息不要将API密钥等硬编码在配置中。使用环境变量并通过Provider的env配置有选择地传递。监控工具调用务必监听tool-call和tool-result事件记录所有由AI执行的操作以便审计和复盘。5.4 性能优化建议复用Provider实例对于codexAppServer确保在应用生命周期内复用同一个Provider实例避免重复启动进程的开销。合理设置超时根据任务复杂度调整requestTimeoutMs。对于长文档分析或复杂推理可以设置得长一些如5-10分钟。管理线程生命周期对于codexAppServer无状态的threadMode: stateless默认更轻量。只有需要真正持久化对话时才使用persistent模式或手动管理threadId。长时间不用的线程应主动清理。图片处理如果使用大量本地图片注意临时文件的I/O开销。在codexAppServer模式下优先使用远程URL以减少本地读写。这个Provider将强大的Codex CLI能力无缝桥接到了成熟的AI SDK生态中。两种模式覆盖了从简单脚本到复杂交互应用的全场景丰富的配置和实时工具流监控赋予了开发者极大的控制力。