自主性就是你需要的一切——米歇尔·卡塔斯塔,Replit




内容概要

在本场演讲中,Replit 的 AI 副总裁 Michele Catasta 探讨了自主性 (Autonomy) 在为非技术用户构建 AI 智能体 (Agent) 中的关键作用。他认为,真正的自主性需要超越简单的“人在回路 (Human-in-the-loop)”模式,转向一种类似“Waymo”的体验,即用户可以将技术决策完全委托给 AI。Catasta 概述了实现这一目标的三个基础支柱:前沿模型 (Frontier Models) 的先进能力、防止出现“画出来的门 (Painted Doors)”的严格自主验证,以及使用子智能体编排进行高效的上下文管理。最后,他讨论了并行化 (Parallelization) 的未来,提议将编排者从用户转变为核心智能体循环,以最大化效率和用户体验。

目录

  • 引言:自主性这一北极星

  • 智能体自主性的格局

  • 两种自主性:特斯拉 (Tesla) 与 Waymo 的对比

  • Replit Agent 的演变

  • 重新定义自主性与控制权

  • 最大化不可缩减的运行时间

  • 自主性的三大支柱

  • 支柱 2:验证与自主测试

  • 代码验证的各个层级

  • 技术深究:Playwright 与浏览器操作

  • 支柱 3:上下文管理与子智能体

  • 并行化的作用

  • 核心循环作为编排者

引言:自主性这一北极星

在 Replit,我们正在为非技术用户构建一个编码智能体 (Coding Agent)。与在座许多人相比,这是一个非常独特的挑战。今天我要讲的是,为什么“自主性”已经成为我们在去年九月推出第一个版本的 Replit Agent 后,一直在这个领域追逐的“北极星”。

智能体自主性的格局

让我们从这张非常有趣的图表开始。我想你们都见过了,这是 a16z 几周前发布的开创性价值图表,它在某种程度上为我们所有智能体构建者理清了当前的格局。

一方面,我们有低延迟的交互,这确实允许你保持在回路中,这样你可以进行深度工作并专注于手头的编码任务。但这要求你是专家。你需要确切地知道要向模型询问什么,并且你需要能迅速判断是否接受这些更改。

然后在几个月的时间里,包括 Replit 在内的许多公司,我们都处在一个我称之为“低谷”的阶段:智能体的自主性不足以让你真正委托一项任务并在回来时看到它已完成;但与此同时,它的运行时间又太长,导致你无法保持专注,无法留在回路中。

幸运的是,随着时间的推移,我们设法一路向右移动,现在我们拥有的智能体可以连续运行几个小时。我今天要提出的观点——希望大会方不会因此停止邀请我——是这张图表还需要增加一个维度,也就是第三个维度,即:我们如何为非技术用户构建自主智能体?

两种自主性:特斯拉 (Tesla) 与 Waymo 的对比

今天要论证的是,存在两种类型的自主性。一种是更加偏向监督式的。想想特斯拉 FSD (全自动驾驶) 的例子。当你坐在特斯拉里时,你仍然被期望拥有驾照。你会坐在方向盘前。也许 99% 的时间你不会用到它,但你在那里是为了处理长尾事件。

同样,我们今天拥有的许多编码智能体都要求你在技术上很精通,才能正确使用它们。而在 Replit,以及现在的其他一些公司,我们正专注于一种类似 Waymo 的自动编码智能体体验。也就是说,你被期望坐在后座,你甚至无法接触方向盘,而且我期望你基本上不需要任何驾照。

为什么这很重要?因为我们想要赋能每一位知识工作者去创造软件。我不能指望知识工作者知道智能体应该做出什么样的技术决策。我们应该完全替他们卸下这层复杂的负担。

Replit Agent 的演变

当然,到达这一步花了一些时间。这里展示的内容大家应该都很熟悉。我们要花数年时间,才能从不到一分钟的反馈循环、持续监督、代码补全 (Completions) 和助手 (Assistants) 模式中走出来。这些是 AI 力量所在的领域,并且真正开创了这种类型的用户交互。

然后我们慢慢攀升至更高层次的自主性。我们有了第一版基于 ReAct 的智能体。我们在大语言模型 (LLM) 之上用一种非常简单的范式构建了自主性。幸运的是,AI 提供商意识到工具调用 (Tool Calling) 极其重要,并为此投入了大量精力。因此,我们构建了具有原生工具调用功能的下一版智能体。

接着是第三代智能体,我称之为自主智能体 (Autonomous Agents)。这时我们开始打破“一小时自主性”的障碍。基本上,智能体能够执行长跨度任务 (Long-horizon tasks) 并保持连贯性。

这也恰好是我们去年发布的 Replit Agent 版本的发展历程。V3 版本是我们几个月前推出的,它恰好展示了这些特性。所以今天的问题是:我们真的能构建完全自主的智能体吗?我们要如何到达那里?

重新定义自主性与控制权

今天我想尝试重新定义“自主性”。我认为我们要么经常把自主性与长时间运行混为一谈,通常作为用户,你会因此失去控制权。

实际上,我想赋予智能体的自主性是可以被明确限定范围的。我的意思是,特别是在 Replit Agent V3 中,我们要确保我们的智能体全权做出技术决策。当然,如果智能体再次运行几个小时,这可能会导致不同用户交互之间存在很长的时间间隔。

但这只有在你给智能体设定的任务范围非常广泛时才会发生。事实证明,实际上你可以拥有一个既真正自主又快速的智能体,只要你给它一个非常窄的任务范围。

通过这种方式,我们可以实现的是:用户仍然保持对他们关心的方面的控制权。用户关心的是他们正在构建什么——尤其是我们的用户,即知识工作者。他们不关心某样东西是“如何”被构建出来的;他们只想看到目标达成。因此,自主性不应该与长运行时间混为一谈。

最大化不可缩减的运行时间

同样,这也不应该成为一个虚荣指标。我们很多人把它当作某种荣誉勋章。在过去的几个月里,看到我们许多人打破了连续运行数小时的障碍确实令人兴奋。但我认为,为了构建未来更强大、更稳健的智能体,我们在某种程度上必须改变一下目标,即我们要关注的指标。

试着这样思考:任务具有自然层级的复杂性。基本上,我们关心的是它们所表现出的最小不可缩减的工作量 (Irreducible amount of work)。智能体所做的是不断经历规划、实施和测试的循环。当然,为了让这个过程发生并正确运作,你希望这项工作是在一个长期的、连贯的轨迹上进行的。

所以我们的目标是最大化智能体的“不可缩减运行时间”。所谓不可缩减,是指在这段时间内,用户不需要做出任何技术决策,智能体可以完全自主地完成任务。

这对我们来说尤其重要,因为我不能信任我们的用户去做技术决策。所以他们需要在身边有一个合适的技术协作者。我想从软件创造过程中尽可能多地抽象出复杂性。最后但同样重要的是,我希望用户感觉能够掌控他们正在创造的东西,而不会因为还要思考智能体正在做的技术决策而扼杀他们的创造力。

自主性的三大支柱

那么,自主性的支柱是什么?我们是如何实现这一点的?我认为有三个支柱是非常重要的。

第一个当然是前沿模型的能力——就像我们在主智能体循环中注入的基准智商。这一点我留给读者和在座的其他同行去探索。我很高兴大家正在构建令人惊叹的模型,我们在 Replit 一直在使用这些模型。这是第一支柱。

第二个支柱是验证 (Verification)。在我们采取的每一步中测试智能体的局部正确性是非常重要的。原因很直观:如果你在非常不稳固的基础上构建,最终城堡会倒塌。所以我们将验证引入循环中,以确保某种程度上的“几个九”的可靠性,防止如果你不加控制,智能体无疑会产生的复合误差。

最后但同样重要的一点——你们刚才在台上听到过,我也确信在整个会议期间你们会听到——是上下文管理 (Context Management) 的重要性。一方面,你希望拥有一个能够保持全局连贯性的智能体,使其与用户的意图和期望保持一致。但同时,它也必须能够管理高层目标和智能体正在处理的单个任务。

我认为我们在过去几个月里在上下文管理方面取得了惊人的进步,我也很兴奋看到作为一个领域我们将走向何方。

支柱 2:验证与自主测试

让我们从 Replit 积极投入的第一个支柱开始,即验证。我们为什么关注这个?在过去的一年里,我们意识到了一些我想你们每个人都经历过的事情:如果没有测试,智能体会构建出许多“画出来的门 (Painted Doors)”。

在我们的案例中,这些“画出来的门”非常明显,因为我们创建了许多 Web 应用程序。结果是你试图点击一个按钮,但处理程序并没有被查找,或者显示的某些数据实际上是模拟数据,并非来自数据库。但在一般情况下,这种现象跨越了你构建的每种类型的组件,无论是前端还是后端。许多组件实际上并没有被智能体完全实现。

我们在内部进行了一些评估。我们发现超过 30% 的独立功能在智能体第一次构建时是损坏的。这也意味着几乎每个应用程序都至少有一个损坏的功能或“画出来的门”。

这些问题很难发现。原因是用户不会花时间测试每一个按钮、每一个字段。这可能也是我们许多用户,尤其是非技术用户,仍然不太信任编码智能体的原因之一。当他们发现那里有一个“画出来的门”时,他们会感到震惊。

那么我们如何解决这个问题?从根本上说,智能体必须从其环境中收集所有需要的反馈。对吧?但这说起来容易做起来难。再次强调,非技术用户不仅无法做出技术决策,而且他们也无法提供智能体取得进展所需的技术反馈。

他们能做的主要是基本的质量保证测试 (QA)。他们可以真的在 UI 上到处点击,与应用程序交互。我相信你们在生活中也试过;这极其乏味,并且会导致非常糟糕的用户体验。即使我们在去年首次发布智能体时依赖这种方式,我们很快就明白用户不想花时间做测试。

所以我们要找到一个完全正交的解决方案,那就是自主测试。它解决了几个不同的问题。

首先,它打破了反馈瓶颈。即使我们向用户寻求反馈,我们也得不到足够的反馈。现在我们不再需要等待人类反馈;我们有办法自主地从应用程序中获取尽可能多的信息。

我们还要防止小错误的累积——就像我之前说的,我们不希望在智能体构建时出现复合误差。最后但同样重要的是,我们要克服前沿模型的懒惰。我们需要验证每当模型告诉我们任务已完成时,这实际上是事实,结果不是幻觉。

代码验证的各个层级

代码验证有一个很宽的范围。我想我们都是从最左边开始的。也就是使用语言服务器协议 (LSP) 进行基本的静态代码分析。自从我们有了能够调试的大语言模型后,我们就一直在执行代码。

然后我们慢慢开始向右移动。比如生成单元测试并运行它们。这有局限性:它仅限于功能正确性。根据定义,单元测试在进行适当的集成测试方面并不是很强大。

我们现在也开始做 API 测试,但这仅限于 API 代码。你可以测试应用程序的端点;你无法真正测试 Web 应用程序的功能和外观。

出于这个原因,在过去的几个月里,Replit 和其他公司投入了大量精力,真正创建基于浏览器的自主测试(如果我们构建的是 Web 应用程序的话)。

这里主要有两类。一类是“计算机使用 (Computer Use)”。这是与用户界面的对一映射。模型直接与应用程序交互。这需要截图。它往往相当昂贵且相当慢——我相信你自己也测试过。

中间的一个好方法是“浏览器使用 (Browser Use)”,我们模拟用户界面。然后你可以与浏览器和 Web 应用程序交互,它依赖于通过抽象访问 DOM。

技术深究:Playwright 与浏览器操作

那么我们如何让它工作呢?我们的做法是生成易于测试的应用程序,并将前面幻灯片中展示的所有内容融合在一起。

我们允许测试智能体与应用程序交互并在没有任何效果时收集截图——所以我们有“计算机使用”作为后备方案。但在绝大多数情况下,我们所做的是与应用程序进行程序化交互。我们会与数据库交互,读取日志,进行 API 调用,实际上点击应用程序并获取我们需要的所有信息。通过将所有这些放在一起,我们收集了足够的反馈,不仅允许智能体取得进展,还可以修复它遇到的所有“画出来的门”。

这里做一个简短的技术深究,看看我们在 Replit 是如何实现这一点的。我相信你们见过很多基于工具的浏览器操作。外面有很棒的库;我脑海中第一个浮现的是 Selenium。其理念是你有一个智能体,它暴露了一些非常通用的工具。比如,智能体可以创建一个新标签页、点击、填写表单等等。

其局限性在于很难枚举你可能与浏览器进行的所有不同类型的交互。测试问题与我之前做的特斯拉类比非常相似。也许这种可用工具的基数足以覆盖 99% 的交互类型,但总是存在长尾的特殊交互,用户会对 Web 应用程序进行这些操作,而这些操作很难映射到这些不同的工具调用中。

所以在我们的案例中,我们直接编写 Playwright 代码。首先,Playwright 代码对于大语言模型来说非常易于管理。模型在编写 Playwright 方面表现惊人。这是我们开始在这个项目上工作以来的经验。它也非常强大且具有表现力。所以在某种意义上,它是相比于左侧工具测试所能表达内容的超集。

最后但同样重要的是,创建 Playwright 代码有一种美感,因为你可以重用这些测试。一旦你编写了一个测试脚本,你就可以根据需要多次重新运行它。所以在某种意义上,当你创建一个测试时,你也正在创建一个回归测试套件,可以在未来持续运行。我刚才向你们解释的所有这些技巧,帮助我们创建了一种比“计算机使用”便宜且快大约一个数量级的东西。我们稍后会回头讨论延迟的重要性。

支柱 3:上下文管理与子智能体

我想今天谈论的第二件事——也就是第二个支柱,当然是上下文管理。我会讲得很快,因为我想你们今天会听到很多关于这方面的演讲。这里的高层信息是:并不一定需要长上下文模型才能在连贯和长轨迹上工作。

根据经验,我们发现大多数任务,即使是更有野心的任务,也可以在 200,000 个 Token 内完成。所以我们还没有处在一个必须使用 1000 万或 1 亿上下文窗口的模型来运行自主智能体的世界。我们通过学习如何正确进行上下文管理来实现这一点。

首先,有几种不同的方法来维护状态,这并不意味着要把所有状态都塞进你的上下文窗口。例如,你可以利用代码库本身来维护状态。你可以在智能体创建新代码时编写文档。你还可以包含计划描述和智能体正在处理的所有不同任务列表;你可以将它们持久化在文件系统中。所以即使在这里,也有很多方法可以卸载你的记忆。

最后但同样重要的是——这也是我认为 Anthropic 一直在宣传的——你甚至可以直接将记忆转储到文件系统中,然后确保你的智能体决定何时在它们变得与工作相关时将它们写回来。

正因为如此,我们在过去几个月里看到了很多公告。比如 Anthropic 的 Claude Sonnet 3.5(他在演讲中口误为 4.7),他们已经能够连续运行专注任务超过 30 小时。我们在 OpenAI 的数学问题上也看到了类似的结果。所以我认为我们已经打破了长时间运行并能够执行连贯任务的障碍。

我要说实现这一点的关键要素是模型和我们智能体构建者在进行“子智能体编排 (Sub-agent orchestration)”方面变得多么出色。子智能体基本上是通过......它们在核心循环中被调用。所以它是完全......从一张白纸开始,从一个全新的上下文开始。

作为智能体构建者,你决定当子智能体启动时注入什么样的上下文子集。这是一个与过去几十年编写软件的人都非常相似的概念,即关注点分离 (Separation of concerns)。你决定你的子智能体将要处理什么,你给它尽可能少的上下文,你允许它运行直到完成,你只获取输出结果,将它们注回主循环,然后以这种方式继续运行。

当然,这显著提高了每次压缩的记忆数量。这张图直接来自 Replit Agent 的生产环境。当我们启动新的子智能体编排器的那一刻,在 Y 轴上你可以看到每次压缩的记忆数量。我们从大约 35 增加到了 45,最近达到了 50。这是一个巨大的进步,仅仅因为我们可以通过使用子智能体卸载大量的上下文污染。

我要举一个例子,说明这对我们产生的差异。我刚才展示的更多是某种成本优化——比如你压缩得更少了。你还有关注点分离,这无疑会让你的智能体更聪明一些。

在测试的案例中,使用子智能体对我们来说几乎是强制性的。基本上,我们在子智能体编排非常先进之前就开始从事自动化测试工作。我们发现,当然,正如我之前所说,它让事情变得更容易,成本更好,污染更少。

但是,当你允许主循环不仅创建代码,还执行浏览器操作——并将浏览器操作的观察结果放回主循环时,你往往会让智能体循环非常困惑,因为此时主循环看到的动作中有太多的“它”指代不清。

所以为了让它工作,我们不仅要构建我之前展示的所有 Playwright 框架,而且我们还必须将整个架构移入子智能体。所以在这一点上,你可以非常清楚地看到这里的关注点分离。我们有运行的主智能体循环。我们在某一点决定是时候验证智能体的输出是否正确了。我们在一个子智能体内完成这一切。然后我们清除该子智能体的上下文窗口,只将最后的观察结果返回给智能体循环,然后我们继续以这种方式运行。

所以如果你今天在让子智能体正确工作方面遇到问题,这是你想查看的原因之一。

并行化的作用

我认为我们要讨论的最后一个要素是并行化 (Parallelism)。我认为我们已经涵盖了关于如何随着时间的推移创建越来越强大的自主智能体的高层内容,而且我只看到我们在接下来的几个月里作为一个领域会变得更加精通。但还有一个额外的要素将会带来不同,那就是并行化。

我会认为并行化之所以重要,并不是因为它本身会让智能体更强大,而是因为它会让用户体验更令人兴奋。当然,拥有一个能够长时间自主运行的智能体是很棒的,但同时也付出了让用户体验变得不那么刺激的代价。

你不再处于那种专注状态了。你所做的是写一个很长的提示词,它被翻译成任务列表,然后你去和同事吃午饭,回来时希望智能体已经完成了。这不是大多数富有成效的人生活中想要的那种体验。你想在最短的时间内看到尽可能多的工作被完成。

所以我们在该领域目前所做的是创建并行智能体。这是一个非常常见的权衡,顺便说一句,这不仅适用于智能体;它适用于一般的计算。对于并行智能体,你所做的是基本上用额外的计算资源来换取时间。

为什么会有这种权衡?首先,当你并行运行智能体时,你在多个上下文窗口中收集相同的上下文。所以你运行的每一个并行智能体可能在各个方面共享大约 80% 的上下文。所以当然你只是投入了更多的计算工作,因为你在并行运行这些智能体。

还有一个成本,对于在座的许多人来说是有形的,因为我相信你们都是专家级软件开发人员:但在最后你如何处理多个并行智能体的输出?通常你需要解决合并冲突 (Merge conflicts)。提醒一下,我的用户甚至不知道合并冲突的概念是什么。这是我必须自己弄清楚的事情。所以我们在该领域目前思考并行智能体的方式并不真正适用于 Replit。

与此同时,我仍然非常想实现这一点。并行化可以启用许多有趣的功能。除了你可以完成更多工作这一事实外,有时你希望测试与创建代码的智能体并行运行。测试,无论我们如何优化它,仍然非常慢。如果一个智能体只花时间在测试上,用户就不会再与你的应用程序互动了。

与此同时,在你的智能体运行时有一个异步进程运行也是很棒的,因为你可以将有用的信息注回主核心循环。最后但同样重要的是,这是一个我们知道可以提升性能的非常常见的技术:如果你有足够的预算,你应该同时采样多个轨迹。

所以并行智能体带来了很多好处,但我们今天实现它们的方式——我基本上称之为“用户作为编排者”——是你想运行的并行任务是由你,即用户决定的。并且每个任务都在自己的线程中分发。

所以这有点手动过程。甚至任务分解在某种意义上也是发生在你脑海中的,当你思考你想运行哪些智能体时,然后当你拿回所有结果的那一刻,你需要经历合并冲突的问题。通常这根本不简单,无论外面有多少惊人的工具。

核心循环作为编排者

所以我们今天为下一版智能体所做的工作是让核心循环作为编排者。这里的关键区别在于,我们将要处理的子任务不是由用户决定的,而是由核心循环决定的。并行化基本上是即时决定的;智能体代表用户进行任务分解。

这带来了几个优势。首先,再次强调,用户没有认知负担去理解他们应该如何分解任务。同时,也有办法创建某些任务来某种程度上缓解合并冲突的问题。

我不是在声称我们将能够 100% 缓解它。有太多的边缘情况会导致合并冲突仍然是一个问题,但在软件工程中有许多已知的不同技术可以确保你可以尝试让多个子智能体互不干扰。

所以“核心循环作为编排者”将是我们未来几个月的主要赌注。如果你对这些话题充满热情,我在 Replit 一直在招聘。谢谢。


AI 前线

用子模优化做文本选择、段落重排和上下文工程

2025-12-23 22:48:25

AI 前线

DeepSeek-V3.1 版本更新

2025-12-23 22:48:33

0 条回复 A文章作者 M管理员
    暂无讨论,说说你的看法吧
个人中心
购物车
优惠劵
今日签到
有新私信 私信列表
搜索