Harmony os——ExtensionAbility 组件笔记:把「特定场景能力」拆出去做

54 阅读7分钟

Harmony os——ExtensionAbility 组件笔记:把「特定场景能力」拆出去做

这一篇是我给 ExtensionAbility 组件 写的学习笔记,定位: 弄清楚它是什么、能干什么、什么时候该用它。 适合发博客当一篇「概念 + 结构化理解」的总结。


一、ExtensionAbility 是什么?

在 Stage 模型里,UIAbility 是“带界面的主角”,ExtensionAbility 更像“专门做某件事的能力插件”

  • 不负责完整 App 的 UI 流程,而是针对某个场景提供扩展能力;

  • 每一种场景会有一种对应的 ExtensionAbility 类型,例如:

    • FormExtensionAbility:给服务卡片用的;
    • InputMethodExtensionAbility:输入法;
    • WorkSchedulerExtensionAbility:延时任务;
    • ……

几个关键点:

  1. 类型是系统定义好的

    • 开发者不能直接继承 ExtensionAbility 基类;
    • 只能继承它的具体子类,比如 FormExtensionAbilityInputMethodExtensionAbility 等。
  2. 通常由系统服务统一管理

    • 比如:

      • 输入法相关能力由「输入法管理服务」管理;
      • 卡片相关能力由「卡片管理服务 FormManagerService」管理。
  3. 用途:丰富应用功能 + 加强和系统/其它应用交互

    • 想对外暴露「数据共享、打印、分享、推送、备份、嵌入式 UI」这种能力时,就会考虑对应的 ExtensionAbility 类型。

二、已经定义好的 ExtensionAbility 类型一览

官方是用表格列出来的,我整理成便于自己快速扫一眼的版本👇

ExtensionAbility 类型功能描述三方应用能否实现是否有独立 Extension 沙箱典型场景
FormExtensionAbility卡片扩展能力✅ 可以❌ 否桌面服务卡片
WorkSchedulerExtensionAbility延时任务能力✅ 可以❌ 否定时/延迟后台任务
InputMethodExtensionAbility输入法扩展能力✅ 可以✅ 是第三方输入法
ServiceExtensionAbility后台服务扩展能力,提供后台能力并可连接通信❌ 不允许三方实现❌ 否系统后台服务
AccessibilityExtensionAbility无障碍服务扩展能力,访问/操作前台界面✅ 可以❌ 否屏幕朗读、辅助功能
DataShareExtensionAbility数据共享扩展,提供数据读写服务,可被三方连接使用❌ 不允许三方实现❌ 否系统级数据共享
BackupExtensionAbility数据备份/恢复能力✅ 可以❌ 否备份应用数据
EnterpriseAdminExtensionAbility企业设备管理(安装应用、密码错误次数过多等事件)✅ 可以❌ 否企业设备管控
PrintExtensionAbility文件打印能力(照片/文档打印)✅ 可以❌ 否打印服务
ShareExtensionAbility分享扩展能力,提供分享模板服务✅ 可以❌ 否自定义分享面板
DriverExtensionAbility驱动扩展能力✅ 可以❌ 否驱动相关扩展
ActionExtensionAbility自定义服务扩展,基于 UIExtension 的自定义操作模板✅ 可以❌ 否自定义处理动作
AdsServiceExtensionAbility广告服务扩展✅ 可以❌ 否广告业务
EmbeddedUIExtensionAbility嵌入式 UI 扩展,提供跨进程界面嵌入能力✅ 可以❌ 否在别的进程中嵌入你的 UI
FenceExtensionAbility地理围栏扩展能力✅ 可以❌ 否基于地理围栏的业务
DistributedExtensionAbility分布式扩展能力,提供分布式创建/销毁/连接回调✅ 可以❌ 否分布式业务扩展
AppServiceExtensionAbility应用后台服务扩展,提供创建/销毁/连接/断开回调✅ 可以❌ 否应用自有后台服务
FaultLogExtensionAbility提供故障延迟通知能力✅ 可以❌ 否异常监控
WebNativeMessagingExtensionAbilityWeb 插件对接到 native 应用✅ 可以❌ 否Web 与原生通信
PushExtensionAbility推送扩展能力,获取场景化消息数据等✅ 可以❌ 否消息推送场景
InsightIntentUIExtensionAbility被小艺意图调用,以窗口形态呈现内容✅ 可以❌ 否与小艺意图联动的 UI 窗口
AssetAccelerationExtensionAbility资源预下载扩展,设备空闲时后台预下载资源✅ 可以❌ 否资源预下载、加速体验

两个小点可以记一下:

  • “是否允许三方应用实现”:关系到你能不能自己写这个类型;
  • “是否有独立 Extension 沙箱”:关系到和主应用数据是否隔离。

三、ExtensionAbility 的进程模型补充

一般情况:

  • 同一个应用(同一个 BundleName)内,
  • 同一种类型的 ExtensionAbility,
  • 通常会运行在同一个独立进程中

也有例外(官方特别说明的):

  1. ServiceExtensionAbility(仅系统应用)
  2. DataShareExtensionAbility(仅系统应用)

这俩 和所有 UIAbility 一起跑在主进程

另外:

  • UIExtensionAbility 以及继承它的 Extension 类型 可以在 module.json5 里通过 extensionProcessMode 字段配置具体的进程运行模式。

四、ExtensionAbility 是怎么被调用的?

一个很重要的点:

所有 ExtensionAbility 组件都不能被应用直接 startAbility 拉起来。

它们的生命周期统一由对应的系统服务管理,调用模式大致是:

  1. 调用方应用 → 发起某种能力请求(比如:选输入法、请求分享、添加卡片等);

  2. 系统对应的管理服务(比如输入法管理服务、卡片管理服务等):

    • 收到请求;
    • 内部「拉起对应类型的 ExtensionAbility」;
    • 管控它的创建、销毁、连接、断开等生命周期;
  3. 调用方只和管理服务交互,不需要直接关心 ExtensionAbility 本身是怎么创建 / 退出的。

以 InputMethodExtensionAbility 为例

  • 调用方:某个普通应用的输入框;

  • 管理服务:输入法管理服务;

  • 执行流程类似于:

    1. 应用触发输入需求(焦点点到输入框);
    2. 输入法管理服务选择当前默认输入法(一个 InputMethodExtensionAbility 实现);
    3. 管理服务拉起对应的 ExtensionAbility;
    4. 输入法 Extension 的生命周期、连接、断开都由系统服务接管;
    5. 调用方只管拿「输入结果」。

五、实现指定类型的 ExtensionAbility:以卡片为例

这里用 FormExtensionAbility(服务卡片)来理解「作为实现方」我们要做什么。

1. 系统提供基类

系统先提供一个基类:

 // 伪代码:真实签名以官方文档为准
 export abstract class FormExtensionAbility extends ExtensionAbility {
   // 生命周期 & 卡片相关回调
   abstract onCreate(...args): void;
   abstract onUpdateForm(...args): void;
   abstract onDeleteForm(...args): void;
   // ...
 }

. 我们继承这个基类实现自己的逻辑

比如:

 export default class MyFormExtensionAbility extends FormExtensionAbility {
   onCreate(formId: number, params: Record<string, Object>) {
     // 创建卡片时的初始化逻辑
   }
 ​
   onUpdateForm(formId: number, params: Record<string, Object>) {
     // 定时刷新 / 主动拉起时的更新逻辑
   }
 ​
   // ... 其他需要实现的回调
 }

本质上就是:在“卡片场景”中,ExtensionAbility 承担了卡片背后那部分逻辑与数据管理。

3. 生命周期完全由卡片系统服务管理

  • 管理者:FormManagerService(卡片管理系统服务)

  • 它负责:

    • 什么时候创建 MyFormExtensionAbility 实例;
    • 什么时候调用 onCreate() / onUpdateForm() / onDeleteForm()
    • Extension 所在进程什么时候启动、什么时候销毁;
  • 卡片实现方(我们)不用关心调用方是谁,也不用自己控制生命周期。

所以这类 Extension 的使用方式,可以概括为:

“我只管实现回调 & 业务逻辑,何时被调用、何时销毁交给系统服务。”


六、EmbeddedUIExtensionAbility 简单理解一下

文档最后特别提到 EmbeddedUIExtensionAbility,我也单独拉出来记一下:

  • 类型:嵌入式 UI 扩展能力;

  • 能力:提供跨进程界面嵌入

  • 典型场景:

    • 比如一个主应用,想把另一个应用的某个 UI 片段「嵌」进来显示,从架构上就会用到这种能力。

可以简单理解成:

UIExtension + 跨进程嵌入 = EmbeddedUIExtensionAbility 适合做「组件级 UI 能力输出」的那种业务。


七、我的小总结

如果用一句话来区分:

  • UIAbility:一个完整的「前台 UI 能力 + 生命周期」,对应一个任务(Task);
  • ExtensionAbility:为了某个特定功能输出的「专业插件」,由系统服务统一调度。

记 ExtensionAbility 的时候,我会这样归类记忆:

  1. 按场景记

    • 卡片 → FormExtensionAbility
    • 延时任务 → WorkSchedulerExtensionAbility
    • 输入法 → InputMethodExtensionAbility
    • 分享 → ShareExtensionAbility
    • 打印 → PrintExtensionAbility
    • 数据备份 → BackupExtensionAbility
    • 嵌入式 UI → EmbeddedUIExtensionAbility
    • 分布式 → DistributedExtensionAbility
    • 小艺意图 UI → InsightIntentUIExtensionAbility
    • ……
  2. 按开发者角度记

    • 有的类型三方可以实现(适合我们玩);
    • 有的只给系统用(看得懂就行)。
  3. 按生命周期归属记

    • UIAbility → 由应用框架调度;
    • ExtensionAbility → 由对应系统管理服务调度;
    • 调用方只管发起调用,不亲自管理生命周期。