有些工具,第一次见面就把你劝退了。
Codex 对我来说,原本就是这种工具。
它刚出来那阵子,我正用 Claude Code 用得很顺。那时候我其实对 OpenAI 这套东西还是有期待的,心想既然都出来了,总得试一试,看看它到底行不行。结果一上手,落差非常明显。不是那种“各有优劣”的明显,而是那种你前脚刚体验过一个很顺手的东西,后脚再去碰另一个,立刻就会觉得哪里都不对的明显。
我让它写文档,效果一般。让它做总结,不太抓重点。让它分析需求,常常绕来绕去。让它做 code review,也总觉得隔了一层。至于真正写代码,差距就更明显了。不能说完全不能用,但那种感觉很像你刚开完一辆底盘很稳、方向很准的车,再去开一辆看起来差不多、实际上各种细节都不听使唤的车。你不会怀疑它能不能跑。你只是会很快失去耐心。
所以后来,我基本上就不用了。
我其实早就把 Codex 判了死刑
现在回头看,我当时对 Codex 的判断其实挺绝的。
不是说“以后有机会再看看”,而是直接在心里把它归到了“试过,不行,下一位”那一类。原因也很简单:用了 Claude Code 之后,你很难再对一个更慢、更钝、而且经常给不到你想要结果的工具抱太多好感。
尤其是当你已经形成工作流以后,这种感受会更明显。你会很自然地把很多事情交给模型去做,比如写文档、整理会议纪要、归纳需求、review 代码、补实现、查问题。一个模型到底好不好,不是看它偶尔答对了什么,而是看你敢不敢把这些日常工作的“第一棒”交给它。
当时的 Codex,我不敢。
不是完全不行,是不值得。
于是它就这么被我晾在一边了。
Claude 太好用了,直到它开始不够用了
前段时间,Claude Code 做了一波优惠。美国非工作时间给双倍用量,那阵子我真是用得非常爽,几乎是敞开了跑。该丢给它的全丢给它,脑子里不会一直绷着一根弦去算“这一轮对话值不值得”“这个问题要不要省一省明天再问”。
可惜这种好日子通常都不会太久。
优惠结束以后,理论上应该只是回到原来的状态。结果它还干了一件更现实的事:为了削峰,把高峰时段每个 session 的可用量压小了。这个改动从平台角度看,我完全理解;但从用户角度看,体感就很难受了。因为你在认真做事的时候,往往不是一问一答就结束的。你会追问,会修正,会来回拉扯。现在变成几个 request 过去,session 的窗口就差不多见底了。
那种感觉很微妙,像每天拿着一张额度卡过日子。
最麻烦的还不是“量变少了”,而是你一旦用惯了顶级模型,再退回去,落差会特别明显。比如已经习惯了 Opus 4.6 这种级别的东西,你再回去用 Sonnet 或 Haiku,很多时候不是不能干活,而是你会一直感觉少了点什么。判断力、稳定性、抓重点的能力,都差着一截。
人一旦吃过好的,就很难装作普通也一样。
所以我开始认真想一件事:那要不,再回去试试 Codex?
抱着备胎心态回去试,结果有点意外
说实话,我重新打开 Codex 的时候,心态并不光彩。
不是“我看好你”,而是“先拿你顶一下”。
我原本的预期非常低。甚至可以说,我对 OpenAI 的模型一直都没有抱太大幻想。不是贬义,就是一种长期用下来形成的直觉:它们有时候很会说,但不一定真能把事做对。
结果这次试下来,我有点吃惊。
Codex 上的 GPT-5.4,真的很好用。
最直接的感受是,它很简洁。说话不拖,不绕,也不喜欢先铺一大层场面话再进入重点。很多时候你把问题丢过去,它会很快抓到事情的本质,然后沿着那个主干往下走。这个“抓本质”的能力,其实比它会不会写某一段代码更重要。因为只要主干抓对了,后面的执行就很容易变顺;主干抓错了,再勤奋都只是在错误的方向上狂奔。
这件事确实刷新了我对它的认识。
我后来慢慢发现,自己已经形成了一个很自然的用法:Claude Code 继续当主力,量用完了,或者当下不想省着花了,就切到 Codex。不是将就,不是凑合,而是真的能接得上。
这就很不一样了。
一个工具从“我不会再用了”,变成“我每天都会开着,当成 backup,而且这个 backup 很可靠”,中间其实跨过了一条很宽的线。

于是我把它接进了自己的工作流
这件事后来很自然地推动了我的另一个项目。
我之前一直在升级自己的 Web Claude Code Pilot。原先它主要还是围着 Claude 的工作流在转,虽然早就有“以后也许可以支持别家模型”的念头,但动力一直不算特别强。原因很简单,那段时间 Claude Code 正在优惠,主力用得很顺,谁都会下意识地先把眼前最好用的东西吃干榨净。
现在不一样了。
既然 Codex 这次真的让我改观了,那就没必要只把它当作浏览器里另一个单独开的标签页。我更想做的是,把它真正接进我自己的系统里,变成同一套工作流的一部分。
所以这段时间我基本上就在吭哧吭哧地干这个事。
包括怎么支持 Codex 的技能体系,怎么把它的后端接进来,应该走 SDK 还是 app-server,权限怎么转,工具调用怎么统一,消息流怎么跟前端现有的 UI 对上。这些东西单看都不算惊天动地,但凑在一起以后,工程量其实一点都不小。
不过最难的,还不是把 Codex 跑起来。
最难的是,怎么让“切换”这件事变得自然。
最难的不是切模型,是把上下文带过去
如果只是做一个模型下拉框,那根本不值一提。
真正麻烦的是,你在同一个聊天窗口里,聊到一半突然切模型,甚至不是切同一家模型,而是从 Claude 切到 Codex,再从 Codex 切回 Claude。这个时候,新的后端到底已经知道了什么,不知道什么,哪些上下文它已经吃进去了,哪些还没有,这些都不能靠猜。
我这套东西里,整段 session 数据本来就是用 SQLite 存的。所以从产品直觉上看,这件事很顺:既然所有消息都在一个地方,那切过去的时候顺手把 context 带上不就行了?
但真做起来,没有那么简单。
因为“带上 context”不是一句空话。你得处理很多细节。比如同一个后端之前已经看过哪些消息,另一个后端又停在什么位置;比如用户在一段对话中频繁来回切换,怎样避免重复灌上下文;再比如跨 provider 的时候,怎么尽量让新模型快速进入状态,而不是每次都像失忆一样从头开始。
这部分我断断续续做了挺久。
最后做出来的效果,我自己还挺满意的。现在在我的 Web App 里,Claude 和 Codex 之间的切换已经比较成型了。上下文能够接得住,聊天不会突然断片,熟练切换的时候基本上没有什么明显的卡顿感。那种体验很重要,因为一旦切换本身变成负担,你就不会真的去切;只有切换足够顺,双模型互补这件事才不是概念,而是一个真的能用的工作流。

这才是我想要的差异化
我最近越来越觉得,差异化这个词,说起来很大,真正落到产品上,往往就是一句很朴素的话:
别人做不到的那一步,你有没有把它做顺。
对我来说,我现在这个项目真正有意思的地方,不是“我也做了一个 Claude 的壳”,也不是“我给 Codex 加了个 Web UI”。这种事情本身都不够有意思。
真正有意思的是,我把两家顶级模型、两套 CLI 工作流,放进了同一个会话系统里,让它们可以互相补位。
Claude 好用的时候,就狠狠干。额度紧了,Codex 顶上。某个问题更适合哪边,就切哪边。你不需要重新开一个世界,不需要重新解释背景,不需要为了换个模型把前情提要再讲一遍。它们在同一个工作台上,各干各的强项。
我觉得这个想法本身就挺有意思。
以前文章里提到过,Claude 也在做远程控制、做自己的外延能力。但我现在这套东西,至少在我自己这条线上,已经不是“把一个 provider 搬到网页里”那么简单了。它本质上是跨 LLM provider 的。不是单点增强,是横向打通。
这件事让我挺兴奋的。
因为它不是空谈。它现在已经能跑起来了,而且跑得还不错。

写在最后
有些东西很奇怪。
你一开始对它失望过一次,就会很容易以为它以后也就那样了。Codex 对我来说,原本就是这种东西。我几乎已经把它从自己的工具箱里删掉了。
但现实有时候就是这样。不是你主动回头,而是别的工具先把你推回来。Claude Code 的额度策略一变,我重新去试,结果反倒看到了一个完全不一样的 Codex。更准确地说,我看到的是一个已经足够成熟、足够可靠,可以真正接进我日常工作流里的 GPT-5.4。
而更有意思的是,这次回头没有停在“哦,它现在不错”这个层面。
它直接推动我把自己的 Web Claude Code Pilot 往前做了一大步。原本动力没那么强的双后端、多模型、跨 provider 切换,现在一下子全都串起来了。很多之前只是“以后可以做”的想法,突然都变成了“现在就值得做”。
所以这篇文章与其说是在聊 Codex,不如说是在聊一件更实际的事:
当一个工具开始不再完全可靠的时候,你最好的选择,往往不是抱怨,而是给自己造第二条路。
现在,这条路我已经差不多铺出来了。
而且我觉得,挺好玩。