1. 从"能跑"到"跑得快":鸿蒙 AI Native 交付的真实卡点
做过鸿蒙应用交付的人大概都有类似的体感:单个页面、单个元服务跑通不难,ArkTS 的声明式 UI 写起来也顺手,可一旦项目进入多模块、多团队、多端协同的阶段,问题就集中爆发了。构建脚本散落在各个仓库、依赖版本对不齐、CI 上跑一次全量编译要等十几分钟、AI 能力接入后又要额外维护一套提示词和工具链——这些琐碎但致命的摩擦,才是拖慢规模化交付的真正原因。
高德和鸿蒙 DevEco CLI 的这次联合实践,本质上就是在回答一个问题:当 AI Native 成为研发范式,命令行工具链该怎么改造,才能让"AI 参与研发"这件事从演示 Demo 变成每天都能用的生产力。这里的关键词是DevEco CLI、AI Native、ArkTS和Agent——它们不是四个孤立的概念,而是一条链上的四个环节:CLI 提供可编排的入口,AI Native 定义研发流程的组织方式,ArkTS 是鸿蒙侧的实现语言,Agent 则是把 AI 能力落到具体任务上的执行单元。
这篇文章适合三类人看:一是正在做鸿蒙应用、被多模块构建折磨过的开发者;二是想把 AI Agent 接进现有研发流程、但不知道从哪下手的工程团队;三是单纯想搞清楚"AI Native 研发范式"到底和传统研发差在哪里的技术管理者。我会尽量把原理讲透、把步骤写细,同时把我在类似场景里踩过的坑摊开来说——毕竟文档里不会写的东西,往往才是最值钱的。
先说结论:AI Native 不是"给研发流程加个聊天框",而是把 Agent 当作一等公民嵌进构建、测试、发布、诊断的每一个环节,让 CLI 成为人和 Agent 共用的操作界面。下面我按这个思路,一层层拆开讲。
2. DevEco CLI 到底解决了什么:把鸿蒙构建从 IDE 里解放出来
2.1 为什么规模化交付必须离开 IDE
很多人对鸿蒙开发的第一印象是 DevEco Studio 那个图形界面,点一下运行按钮,应用就装到设备上了。这在单人开发、单模块项目里没问题,但规模化交付的场景完全不是这样。想象一下几十个模块、多个 HAP/HSP 包、还要同时出手机、平板、车机多个形态的产物,靠人手在 IDE 里点,既不可复现也不可审计。
DevEco CLI 的价值就在这里:它把 IDE 背后的构建、签名、打包、安装、调试能力抽成命令行接口。一旦变成命令,就意味着它可以被脚本调用、被 CI 流水线编排、被 Agent 触发。这是从"人操作工具"到"程序操作工具"的关键跃迁,也是 AI Native 能落地的前提——Agent 不会去点图形界面,它只会调命令。
我自己的经验是,凡是希望被自动化、被 AI 接管的能力,第一步都得先有稳定的 CLI 入口。没有 CLI,谈 Agent 编排就是空中楼阁。
2.2 核心命令族与它们对应的研发阶段
DevEco CLI 的命令大致可以按研发阶段归类,理解这个分类比死记命令更重要:
| 阶段 | 典型能力 | 对应命令方向 |
|---|---|---|
| 工程初始化 | 创建模板工程、生成模块骨架 | 工程创建类命令 |
| 构建编译 | ArkTS 编译、资源打包、多目标构建 | 构建类命令 |
| 签名打包 | 生成签名配置、产出 HAP/APP | 签名与打包类命令 |
| 安装调试 | 安装到设备、拉起 Ability、抓日志 | 设备与调试类命令 |
| 产物分析 | 包体积分析、依赖树查看 | 分析类命令 |
这张表的意义在于:当你设计 Agent 工作流时,可以按阶段把任务切分。比如"构建失败自动诊断"这个 Agent,它需要的能力就是构建类命令加日志抓取,不需要碰签名。职责边界清晰,Agent 才不容易失控。
提示:不同版本的 DevEco CLI 命令名和参数会有差异,实际接入前务必用
--help确认当前版本的准确签名,不要照搬网上旧版本的命令。
2.3 从 IDE 到 CLI 的迁移成本被高估了
不少人担心迁移到 CLI 会丢掉 IDE 的便利。实测下来,真正需要迁移的只是"构建和发布"这类重复性动作,日常写代码照样可以在 IDE 里进行。CLI 和 IDE 不是替代关系,而是分工:IDE 负责交互式开发,CLI 负责可编排的自动化。把这两件事分开看,迁移的心理负担会小很多。
具体操作上,我建议先在本地把一条完整链路跑通:用 CLI 完成一次干净的构建、签名、安装,确认产物和 IDE 产出的完全一致。这一步验证通过,后面接 CI 和 Agent 才有底气。
3. AI Native 研发范式的内核:Agent 不是插件,是协作者
3.1 AI Native 和"用了 AI 的工具"差在哪
这里必须先厘清一个常见误解。很多团队说自己"AI Native",其实只是装了个代码补全插件,或者接了个问答机器人。这不叫 AI Native,这叫"用了带 AI 的工具"。真正的 AI Native 研发范式,核心区别在于流程的组织方式是否以 Agent 为中心。
传统研发流程是:人接到需求 → 人拆解任务 → 人写代码 → 人测试 → 人发布。AI 只是某个环节的辅助。AI Native 流程是:人定义目标和约束 → Agent 拆解并执行 → 人审核关键节点 → Agent 继续推进。人的角色从"执行者"变成"目标定义者和质量把关者"。
这个转变对工具链的要求完全不同。传统流程里工具是给人用的,界面友好就行;AI Native 流程里工具是给 Agent 用的,接口稳定、输出结构化、错误可解析才是第一位的。DevEco CLI 之所以关键,正是因为它天然满足后者的要求。
3.2 Agent 在鸿蒙交付链路里的四种典型角色
结合鸿蒙交付的实际场景,Agent 大致可以承担四类角色,我按介入深度从浅到深排列:
- 构建诊断 Agent:监听构建命令的输出,失败时自动解析错误、定位到具体文件和行、给出修复建议。这是最容易落地、收益也最直接的一类。
- 依赖治理 Agent:扫描多模块的依赖树,发现版本冲突、冗余依赖、循环引用,并生成修复方案。鸿蒙多模块项目里这类问题特别多。
- 测试编排 Agent:根据代码变更范围,智能选择需要跑的测试用例,而不是每次全量跑。这在大型项目里能省下大量时间。
- 发布协同 Agent:串联签名、打包、产物校验、分发,把发布流程变成一条可审计的自动化链路。
这四类角色的共同点是:它们都建立在 CLI 提供的稳定命令之上,都产出结构化的结果,都能被人审核。这就是"协作者"和"插件"的区别——协作者有明确的职责边界和可验证的产出。
3.3 ArkTS 项目对 Agent 的特殊要求
鸿蒙用 ArkTS 作为主力开发语言,这对 Agent 提出了几个特殊要求。ArkTS 是 TypeScript 的强约束超集,去掉了动态特性,类型系统更严格。这意味着 Agent 在做代码生成或修改时,必须理解 ArkTS 的约束,不能生成在 TS 里合法但在 ArkTS 里报错的代码。
举个实际例子:ArkTS 不支持any和unknown的随意使用,也不支持运行时动态属性访问。如果 Agent 生成的代码里带了这些,编译直接失败。所以一个合格的鸿蒙 Agent,它的提示词和工具链里必须内置 ArkTS 的规则约束,而不是拿通用的 TS 生成逻辑硬套。
我在实践中的做法是:把 ArkTS 的常见约束整理成一份"负面清单",作为 Agent 生成代码后的自检项。这份清单不需要很长,但覆盖高频错误就够了。下面是一个简化示例:
// ArkTS 中应避免的写法(Agent 自检清单) // 1. 避免 any / unknown 的隐式使用 // 2. 避免运行时动态属性访问 obj[key] // 3. 避免结构化类型之外的鸭子类型 // 4. 对象字面量需有明确的类型标注这份清单看起来简单,但能挡掉相当一部分 Agent 生成代码的编译错误,省去大量来回返工。
4. 把 Agent 接进 DevEco CLI:一条可复现的落地路径
4.1 环境准备里最容易被忽略的三件事
在动手接 Agent 之前,有三件事如果没处理好,后面会反复出问题。
第一是命令输出的结构化。CLI 默认输出是给人看的,带颜色、带进度条、带各种装饰字符。Agent 解析这种输出很容易出错。解决办法是尽量使用 CLI 提供的机器可读输出格式(比如 JSON 输出选项),或者在 Agent 侧做一层输出清洗。我强烈建议优先找 CLI 原生的结构化输出,比事后清洗可靠得多。
第二是退出码的语义。Agent 判断一个命令成功还是失败,最可靠的方式是看退出码,而不是去匹配输出文本。要确保你的脚本和 CLI 调用都正确传递退出码,否则 Agent 会把失败当成功。
第三是幂等性。Agent 可能会重试命令,如果命令不幂等,重试就会产生副作用。构建、打包这类命令通常幂等,但安装、发布类命令要特别小心,最好加上状态检查。
注意:在把任何写操作类命令交给 Agent 自动执行之前,先在只读或沙箱环境里验证一遍。构建诊断这类只读 Agent 可以放心跑,发布类 Agent 一定要有人工确认环节。
4.2 构建诊断 Agent 的最小可用实现
构建诊断是最适合作为第一个落地的 Agent,因为它只读、风险低、收益明显。它的工作逻辑可以拆成四步:
- 调用 DevEco CLI 的构建命令,捕获标准输出和标准错误。
- 从输出中提取错误信息,定位到文件、行号、错误码。
- 把错误信息连同相关代码片段一起交给模型分析。
- 输出结构化的诊断结果:问题原因、修复建议、涉及文件。
这里的关键是第 2 步的错误提取。ArkTS 编译器的错误输出格式相对规整,通常包含文件路径、行号、列号和错误描述。用正则提取这些字段,比让模型直接读原始日志要准确得多。模型擅长的是"根据错误推断原因",不擅长"从一堆噪声里精确找字段"。
# 构建并捕获输出(示意,实际命令以当前版本为准) deveco build --project ./entry > build.log 2>&1 echo "exit code: $?"拿到日志后,先做结构化提取,再把提取结果喂给模型。这个"先解析后推理"的顺序很重要,反过来做效果会差很多。
4.3 依赖治理 Agent 的扫描逻辑
鸿蒙多模块项目的依赖问题,比单模块复杂得多。一个 HSP 包可能被多个 HAP 引用,版本不一致就会出问题。依赖治理 Agent 的核心是构建一张完整的依赖图,然后在这张图上做分析。
具体做法是:遍历每个模块的配置文件,提取依赖声明,构建模块间的引用关系。然后检查三类问题:版本冲突(同一依赖在不同模块声明了不同版本)、冗余依赖(声明了但没实际使用)、循环引用(模块 A 依赖 B,B 又依赖 A)。
循环引用在鸿蒙里是硬伤,会导致构建失败或运行时异常。Agent 发现循环引用后,应该给出拆分建议,比如把公共部分抽成独立的 HSP。这类建议模型给得通常不错,因为它本质上是图论问题,有相对标准的解法。
4.4 让 Agent 的输出可被人快速审核
Agent 再智能,最终也要人来把关。所以它的输出必须"可审核"。什么叫可审核?就是人扫一眼就能判断对不对,而不是要重新读一遍原始日志。
我的经验是,Agent 输出应该遵循固定结构:结论先行、证据在后、建议明确。比如构建诊断的输出,第一行就应该是"构建失败,原因:XXX",然后才是详细的错误定位和代码片段。这样人一眼就能抓住重点,需要深究时再往下看。
这个结构看起来是小事,但直接决定了团队愿不愿意用这个 Agent。输出乱糟糟的 Agent,哪怕分析得再准,也没人愿意看。
5. 规模化交付里那些文档不写的坑
5.1 多模块构建的缓存陷阱
鸿蒙多模块项目构建慢,很多人第一反应是加缓存。但缓存这东西,用不好比不用还糟。我遇到过最典型的问题是:缓存命中了旧产物,导致改了代码但构建结果没变,排查半天才发现是缓存没失效。
根因在于缓存的 key 设计。如果 key 只包含源文件路径而不包含内容哈希,或者依赖变更没纳入 key 计算,就会出现脏缓存。解决办法是确保缓存 key 覆盖所有影响产物的输入:源文件内容、依赖版本、构建配置、环境变量。
在 Agent 场景下这个问题更隐蔽,因为 Agent 不会像人一样"觉得不对劲"。所以缓存策略必须足够保守,宁可多构建几次,也不要出脏产物。
5.2 Agent 重试引发的副作用
Agent 的一个常见行为是失败重试。这在只读操作上没问题,但在写操作上可能出事。比如打包命令重试,如果第一次其实成功了只是返回码异常,第二次就会覆盖产物或者报文件已存在。
我的处理原则是:所有写操作命令,在 Agent 侧都要加"执行前状态检查"。比如打包前先检查目标产物是否存在,存在就先清理。这样即使重试也不会出问题。另外,重试次数要有上限,无限重试的 Agent 是灾难。
5.3 模型幻觉在代码生成里的具体表现
模型幻觉在鸿蒙开发里有个很具体的表现:它会"发明"不存在的 API。ArkTS 的 API 体系庞大,模型训练数据里可能混入了其他平台的相似 API,生成时就会张冠李戴。
防范办法有两个。一是生成后强制编译验证,编译不过的直接打回。二是给 Agent 提供一份当前项目实际可用的 API 清单,让它在这个范围内生成。第二个办法更主动,能从源头减少幻觉。
我在实践里更倾向于"生成即验证"的闭环:Agent 生成代码 → 自动编译 → 失败则把错误反馈给 Agent 重新生成。这个循环跑两三轮,大部分幻觉都能被纠正。
5.4 团队协作中的 Agent 权限边界
最后一个坑是权限。Agent 能调用的命令范围,必须有明确边界。构建诊断 Agent 不应该有发布权限,测试 Agent 不应该有改生产配置的权限。这个边界要在工具层强制,而不是靠提示词约束——提示词是可以被绕过的,工具权限不行。
具体做法是给不同角色的 Agent 配置不同的命令白名单。白名单之外的操作一律拒绝。这样即使 Agent 被误导,也造成不了实质损害。
6. 从单点 Agent 到交付流水线:编排思路
6.1 为什么单点 Agent 很快会碰到天花板
单个 Agent 能解决的问题是有限的。构建诊断 Agent 能告诉你哪里错了,但它不会自动修复;依赖治理 Agent 能发现冲突,但不会自动调整版本。当你想让流程真正自动化时,就必须把多个 Agent 编排起来。
编排的核心是定义清楚 Agent 之间的交接协议:上一个 Agent 的输出,怎么变成下一个 Agent 的输入。这个协议最好是结构化的数据格式,而不是自然语言。自然语言交接容易丢信息,结构化数据不会。
6.2 一条典型的 AI Native 交付链路
把前面讲的 Agent 串起来,一条典型的链路是这样的:
- 代码提交触发流水线。
- 依赖治理 Agent 先跑,检查依赖健康度,有问题就阻断。
- 构建 Agent 执行构建,失败则触发诊断 Agent。
- 诊断 Agent 给出修复建议,人工确认后修复。
- 构建通过后,测试编排 Agent 选择并执行相关测试。
- 测试通过,发布协同 Agent 执行签名打包。
- 产物校验通过,进入分发环节。
这条链路里,人只在关键节点介入:依赖问题确认、诊断建议审核、发布确认。其余环节自动流转。这就是 AI Native 交付的实际形态——不是无人化,而是人只做最有价值的判断。
6.3 编排层的选型考量
编排层可以用现成的 Agent 框架,也可以自己写调度逻辑。选型时我建议重点看三点:一是能不能方便地定义 Agent 之间的依赖关系;二是支不支持人工介入节点;三是执行日志是否完整可追溯。
对于鸿蒙交付这种对可追溯性要求高的场景,日志完整性比框架的"智能程度"更重要。出了问题要能查到是哪一步、哪个 Agent、哪条命令导致的,这比框架有多少花哨功能实在得多。
7. 实测下来值得记住的几条经验
7.1 先做减法,再做加法
刚开始接 Agent 时,很容易贪多,想把所有环节都自动化。实测下来,正确顺序是先做减法:把现有流程里最痛、最重复、最不需要人判断的环节挑出来,先自动化这一个。跑稳了,再扩展下一个。
我见过太多团队一上来就搞"全流程 AI 化",结果每个环节都不成熟,最后整个流水线没人敢用。单点突破、逐步扩展,才是靠谱的路径。
7.2 结构化输出是 Agent 协作的地基
前面反复提到结构化输出,这里再强调一次。Agent 之间、Agent 和人之间的所有交接,都应该尽量用结构化数据。日志、诊断结果、依赖报告,能结构化就结构化。这看起来是工程细节,但它决定了整个体系能不能规模化。
自然语言的交接在小规模时看着灵活,规模一大就变成灾难——信息丢失、歧义、无法自动校验。结构化数据虽然前期要多写点解析代码,但长期收益巨大。
7.3 人工确认节点不能省
无论 Agent 多可靠,发布、删除、覆盖这类不可逆操作,都必须保留人工确认。这不是对 Agent 不信任,而是工程上的基本审慎。不可逆操作一旦出错,代价可能是几小时的返工甚至线上事故。
我的做法是把操作分成三类:只读操作全自动,可逆写操作自动加日志,不可逆操作必须人工确认。这个分类简单,但能挡掉绝大多数严重事故。
7.4 版本对齐是长期功课
DevEco CLI、鸿蒙 SDK、ArkTS 编译器、Agent 框架,这几样东西都在快速迭代。版本不对齐,就会出现各种诡异问题。我建议在项目里维护一份"版本矩阵",明确记录每个组件的版本和兼容关系,升级时按矩阵来,不要单独升某一个。
这份矩阵不需要多复杂,一张表就够。但有了它,排查版本相关问题时能省下大量时间。
8. 关于这套实践后续还能怎么走
写到这里,核心的东西基本讲完了。最后分享一点我个人的判断:鸿蒙生态的 AI Native 交付,现在还处在"工具链打基础"的阶段。DevEco CLI 提供了稳定的命令入口,Agent 框架提供了编排能力,但两者之间的"胶水层"——也就是把 CLI 能力封装成 Agent 可调用的工具——目前还需要各团队自己搭。
这个胶水层短期内是成本,长期看是资产。谁先把这层搭稳,谁就能更快地把新出现的 AI 能力接进自己的交付链路。我的建议是,别等现成的完美方案,先用最小可用的方式把胶水层搭起来,在用的过程中迭代。工具链这东西,永远是用出来的,不是设计出来的。
另外提醒一句,鸿蒙的 API 和工具链更新很快,本文提到的命令和参数请以你当前使用的版本为准。遇到不一致的地方,优先信--help的输出,那是最权威的。