OpenHarmony Ability 机制分析
OpenHarmony Ability 机制分析
基于
/foundation/ability/源码,版本:API 9+(Stage 模型为主)
目录
1. 概述
Ability 是 OpenHarmony 应用的基本构成单元,类似 Android 的四大组件概念。OHOS 提供两套应用模型:
| 模型 | 支持版本 | 配置方式 | 核心组件 |
|---|---|---|---|
| FA(Feature Ability) | API 8 及以下 | config.json |
PageAbility/ServiceAbility/DataAbility/FormAbility |
| Stage(新一代) | API 9+ | module.json5 |
UIAbility / ExtensionAbility 系列 |
FA 模型每个 Ability 拥有独立 JS VM 实例,Stage 模型同进程共享 JS VM 实例,更支持复杂应用和分布式场景。
2. 架构分层
┌─────────────────────────────────────────────────┐
│ 应用层 (ArkTS/JS/C++) │
│ ┌──────────┐ ┌──────────────┐ ┌───────────┐ │
│ │ UIAbility│ │ Extension │ │ Context │ │
│ └────┬─────┘ └──────┬───────┘ └─────┬─────┘ │
├───────┴──────────────┴────────────────┴────────┤
│ 框架层 (frameworks/) │
│ ┌────────────────┐ ┌────────────────────────┐ │
│ │ Native C++ 框架 │ │ JS/ETS NAPI/ANI 绑定 │ │
│ │ AbilityContext │ │ context / wantAgent │ │
│ │ Lifecycle │ │ abilityManager │ │
│ └────────┬───────┘ └──────────┬─────────────┘ │
├───────────┴────────────────────┴────────────────┤
│ 系统服务层 (services/) │
│ ┌─────────────────────┐ ┌──────────────────┐ │
│ │ AbilityManagerService│ │ AppManagerService│ │
│ │ 组件调度 & 生命周期 │ │ 进程生命周期管理 │ │
│ ├─────────────────────┤ ├──────────────────┤ │
│ │ MissionListManager │ │ DataObserverMgr │ │
│ │ ConnectManager │ │ UriPermMgr │ │
│ │ PendingWantManager │ │ QuickFixMgr │ │
│ │ FreeInstallManager │ │ │ │
│ └──────────┬──────────┘ └────────┬─────────┘ │
├─────────────┴─────────────────────┴─────────────┤
│ 基础设施层 │
│ IPC/RPC │ WindowManager │ SAMGR │ Bundlemgr │
└─────────────────────────────────────────────────┘
2.1 框架层 — 应用框架实现
框架层提供 Ability 机制的运行时支持,包括基类定义、生命周期管理、多语言运行时桥接和子进程管理。
ability_runtime/frameworks/native/ ← C++ 原生框架
├── ability/ ← 核心组件:UIAbility、Extension、AbilityContext
│ └── 生命周期调度(LifecycleDeal)、AbilityRecord
├── appkit/ ← 应用级:Application、AbilityStage、TestRunner
├── child_process/ ← 子进程创建与管理
└── runtime/ ← 运行时抽象层(JS/ArkTS/CJ 三种运行时)
ability_runtime/frameworks/ ← 多语言绑定层(桥接 C++ 与脚本语言)
├── js/napi/ ← JS/TS 的 NAPI 绑定(ability、context、appManager、wantAgent)
├── ets/ ← ArkTS 的 ANI 绑定(性能优化)
└── cj/ ← CJ (C-based JSON) FFI 绑定
框架层的核心职责:
| 组件 | 职责 | 关键类 |
|---|---|---|
| Ability 基类 | 定义 UIAbility 和 Extension 的抽象接口、生命周期回调 | UIAbility、Extension、ServiceExtension |
| Context 体系 | 提供 Ability 访问系统能力的入口 | AbilityContext、ExtensionContext、ApplicationContext |
| 生命周期管理 | 状态机管理与状态转换调度 | AbilityLifecycleExecutor、LifecycleDeal、AbilityLifecycleObserver |
| AbilityStage | 应用进程入口,全局初始化 | AbilityStage、Application |
| 多语言桥接 | 将 C++ 能力暴露给 JS/ArkTS/CJ | NAPI 模块、ANI 模块、CJ FFI |
| 子进程管理 | 创建和管理子进程 | ChildProcessManager |
运行时选择机制: 框架层通过 Runtime 抽象接口屏蔽底层差异,同一个 UIAbility 基类可以跑在 JS Runtime、ArkTS Runtime 或 CJ Runtime 上,具体选择由构建时的模块类型决定。
2.2 系统服务层 — 核心系统服务
系统服务层运行在独立的系统进程(abilityms)中,负责组件的调度、生命周期管理、进程管理、权限控制等全局性工作。
两大核心服务:
┌─────────────────────────────────────────────────┐
│ AbilityManagerService (abilityms) │
│ ├── 组件启动/停止调度 │
│ ├── 生命周期管理 │
│ ├── 任务栈与多任务管理 │
│ ├── 连接管理(Extension 绑定) │
│ └── 按需安装(FreeInstall)管理 │
├─────────────────────────────────────────────────┤
│ AppManagerService (appmgr) │
│ ├── 应用进程 fork(通过 AppSpawn) │
│ ├── 进程生命周期(前后台状态) │
│ ├── 子进程管理、进程预加载 │
│ └── 应用恢复与重启 │
└─────────────────────────────────────────────────┘
辅助服务:
| 服务 | 职责 |
|---|---|
DataObserverManager |
数据观察者注册与通知分发 |
UriPermissionManager |
URI 权限的授予、撤销、持久化 |
QuickFixManager |
应用热修复(补丁包管理与运行时替换) |
AbilityManagerService 的内部架构:
AbilityManagerService (单例)
├── AbilityConnectManager ← Extension 绑定/连接管理
├── DataAbilityManager ← Data Ability 数据访问
├── MissionListManager ← 任务栈/列表管理(需 graphics 支持)
├── PendingWantManager ← 待定 Want 管理
├── FreeInstallManager ← 免安装组件支持
├── KioskManager ← Kiosk 模式强制
├── AutoStartupService ← 自动启动组件
├── AbilityInterceptorExecuter ← 拦截器链执行器
│ ├── 12 个预注册拦截器(详见第 3 章)
│ └── 支持动态注册自定义拦截器
└── UIExtensionAbilityManager ← UI 扩展组件管理
两个核心服务的协作流程:
应用请求 StartAbility(want)
│
▼
AbilityManagerService
├── 拦截器链检查(生态规则、权限、Kiosk 等)
├── 创建 AbilityRecord
├── 请求 AppManagerService 确保进程存在
│ │
│ ▼
│ AppManagerService → AppSpawn (fork 进程)
│ │
│ ▼
│ 进程启动 → 加载 Runtime → 通知 AMS"进程就绪"
│
├── 通过 IAbilityScheduler 发送生命周期指令
├── AbilityStage.onCreate() → UIAbility.OnStart()
└── 绑定窗口 → UIAbility.OnForeground()
2.3 接口层 — 核心接口定义
接口层定义了 Ability 机制运转所需的核心合约,包括 IPC 协议、生命周期回调、组件连接回调等。最重要的接口如下:
| 接口 | 类型 | 定义角色 | 关键方法 |
|---|---|---|---|
IAbilityManager |
IPC 接口 | 应用进程 ↔ AMS 系统服务 | StartAbility()、TerminateAbility()、ConnectAbility()、MoveMissionToFront() |
IAbilityConnection |
回调接口 | 应用进程(连接发起方) | onAbilityConnectDone()、onAbilityDisconnectDone() |
IAbilityScheduler |
IPC 接口 | AMS → 应用进程(生命周期调度) | ScheduleAbilityTransaction()、SendResult() |
ILifecycleObserver |
观察者接口 | 应用内监听 | OnAbilityForeground()、OnAbilityBackground()、OnAbilityStart()、OnAbilityStop() |
IAbilityContinuation |
扩展接口 | 跨设备迁移 | OnContinue()、OnRestoreData() |
IConnectionObserver |
观察者接口 | 监听连接状态 | 连接/断开通知 |
这些接口遵循 Proxy-Stub 模式,通过 IPC 实现跨进程调用:
应用进程 (Client) 系统进程 (Server)
IAbilityManagerProxy IAbilityManagerStub
│ │
├── StartAbility(want) ──→ IPC (MessageParcel) ──→ OnStartAbility()
│ │
│ ├── 权限检查、拦截器链
│ ├── 创建 AbilityRecord
│ └── ...
IAbilitySchedulerStub IAbilitySchedulerProxy
│ │
│ ←── ScheduleAbilityTransaction() ─── IPC ───┤
│ └── 应用进程执行生命周期转换
双向通信机制:
- 正向(应用→系统):通过
IAbilityManager发起组件启动、连接等请求 - 反向(系统→应用):通过
IAbilityScheduler向应用下发生命周期指令(OnStart/OnForeground/OnBackground/OnStop)
这种设计使 Ability 生命周期完全由系统服务控制,应用进程被动响应——这与 Android 的 ActivityManagerService → ApplicationThread 模式完全一致。
3. 启动拦截器链
Ability 启动过程中,AMS 通过拦截器链实现横切逻辑。这些拦截器在 StartAbility() 时按序执行:
StartAbility()
│
▼
AbilityInterceptorExecuter
├→ StartOtherAppInterceptor ← 控制启动其他应用
├→ EcologicalRuleInterceptor ← 生态规则检查
├→ KioskInterceptor ← Kiosk 模式强制
├→ ScreenUnlockInterceptor ← 锁屏状态检查
├→ ControlInterceptor ← 系统级控制
├→ DisposedRuleInterceptor ← 规则处置
├→ BlockAllAppStartInterceptor ← 紧急阻止
├→ AbilityJumpInterceptor ← 跳转拦截
├→ ExtensionControlInterceptor ← Extension 控制
└→ CrowdTestInterceptor ← 测试模式控制
4. UIAbility 组件
UIAbility 是 Stage 模型下带 UI 的组件,继承自 AbilityContext、ILifeCycle、IAbilityCallback、IAbilityContinuation。
生命周期状态
UIAbility 底层使用 AbilityLifecycleExecutor 管理状态机。该状态机定义了以下内部状态(来自 FA 模型的 LifecycleExecutor,Stage 模型复用了这套状态基建):
UNINITIALIZED
│
▼
INITIAL ──────→ STARTED_NEW
│ │
│ ▼
│ FOREGROUND_NEW
│ │
│ ▼
│ ACTIVE (运行中)
│ │
│ ▼
│ INACTIVE
│ │
│ ▼
│ BACKGROUND_NEW
│ │
│ ▼
└───────── STOPED_NEW
各状态回调:
| 回调 | 触发时机 |
|---|---|
OnStart(want, sessionInfo) |
Ability 创建时,仅调用一次 |
OnForeground() |
进入前台(可见) |
OnBackground() |
进入后台(不可见) |
OnStop() |
销毁 |
OnNewWant(want) |
已存在实例的情况下再次启动 |
Stage 模型生命周期
=== 冷启动 ===
create → OnStart(want) → OnForeground() → [可见]
→ OnBackground() → [不可见]
→ OnStop() → [销毁]
=== 热启动 ===
onNewWant(want) → OnForeground() → [可见]
→ OnBackground() → [不可见]
LaunchType(启动模式)
| 模式 | 说明 | 类比 Android |
|---|---|---|
singleton |
全局唯一实例 | singleTask |
standard |
每次启动新实例 | standard |
multiton |
同一应用内实例复用 | singleTop 变体 |
5. ExtensionAbility 组件体系
ExtensionAbility 是 Stage 模型下无 UI 或轻 UI的能力组件,功能类似 Android 的 Service/BroadcastReceiver/ContentProvider 组合。
ExtensionAbility 类型一览
| Extension 类型 | 功能 | 类比 Android |
|---|---|---|
| ServiceExtension | 后台长时间运行服务 | Service |
| UIExtensionAbility | 可嵌入其他应用的 UI 组件 | Activity + 嵌入模式 |
| EmbeddedUIExtension | 嵌入式 UI 扩展 | 无直接对应 |
| UIServiceExtension | 带 UI 的后台服务 | 无直接对应 |
| AppServiceExtension | 应用级代理服务 | 无直接对应 |
| ShareExtensionAbility | 分享扩展 | 无直接对应 |
| ActionExtensionAbility | 动作扩展 | 无直接对应 |
| PhotoEditorExtension | 图片编辑扩展 | 无直接对应 |
| AutoFillExtension | 表单自动填充 | Autofill |
| FormExtension | 桌面卡片 | AppWidget |
| DataShareExtension | 数据共享 | ContentProvider |
ServiceExtension 生命周期
ServiceExtension 支持两种启动模式:
启动并运行模式: 通过 startServiceExtensionAbility(want) 启动,适合不需要绑定回 UI 的后台任务。
onCreate() ← AbilityStage 创建后立即调用
│
▼
onStart(want) ← 收到启动请求
│
▼
[运行中] ← 后台长时间执行
│
▼
onStop() ← 系统或应用主动停止
绑定模式: 通过 connectAbility(want) 启动,适合需要与前端 UI 交互的后台服务。
发起方 ServiceExtension
│ │
├── connectAbility(want) ──→ onCreate()
│ │
│ ▼
│ onConnect(want)
│ ←── 返回 IRemoteObject ────┘
│ │
│ [通过 IRemoteObject 通信] │
│ [运行中] │
│ │
├── disconnectAbility() ──→ onDisconnect()
│ ▼
│ onStop()
关键区别:
| 维度 | 启动并运行 | 绑定模式 |
|---|---|---|
| 启动方式 | startServiceExtensionAbility() |
connectAbility() |
| 生命周期 | onCreate→onStart→[运行]→onStop | onCreate→onConnect→[绑定]→onDisconnect→onStop |
| 与调用方通信 | 无直接通信 | 通过 IRemoteObject 双向调用 |
| 停止条件 | AMS 按策略停止或调用方手动停止 | 所有绑定方断开后自动停止 |
| 典型场景 | 后台数据同步、日志上传 | 音乐播放控制、定位服务 |
UIExtensionAbility 生命周期
UIExtensionAbility 的生命周期与嵌入它的宿主应用窗口绑定:
宿主应用触发创建
│
▼
onCreate()
│ 初始化数据、绑定服务
▼
onForeground()
│ UI 嵌入宿主窗口,可见
▼
[嵌入显示]
│ 与宿主应用同生命周期
▼
onBackground()
│ 宿主应用进入后台
▼
onDestroy()
│ 宿主窗口销毁或 UIExtension 被关闭
与 ServiceExtension 的差异:
| 维度 | ServiceExtension | UIExtensionAbility |
|---|---|---|
| 是否有 UI | ❌ 无 | ✅ 有自己的 UI 页面 |
| 窗口管理 | 无窗口 | 通过 UIExtensionContext.getWindow() 获取窗口引用 |
| 宿主依赖 | 独立运行 | 必须嵌入宿主应用窗口 |
| 生命周期 | 独立管理 | 与宿主窗口绑定 |
6. Want 机制
Want 是 Ability 通信的核心载体,相当于 Android 的 Intent。定义在 ability_base/interfaces/kits/native/want/include/want.h。
结构
Want
├── element ← ElementName (bundleName + abilityName + deviceId)
├── uri ← URI 数据定位
├── action ← 动作标识
├── entities ← 类别(entities)
├── parameters ← WantParams (key-value 参数包)
├── flags ← 标志位控制
├── type ← MIME 类型
└── uriPermission ← URI 权限
Flags(部分)
| Flag | 值 | 说明 |
|---|---|---|
FLAG_AUTH_READ_URI_PERMISSION |
0x01 | URI 读授权 |
FLAG_AUTH_WRITE_URI_PERMISSION |
0x02 | URI 写授权 |
FLAG_ABILITY_FORWARD_RESULT |
0x04 | 返回结果 |
FLAG_ABILITY_CONTINUATION |
0x08 | 跨设备迁移 |
FLAG_INSTALL_ON_DEMAND |
0x0800 | 按需安装 |
FLAG_START_FOREGROUND_ABILITY |
0x0200 | 强制前台启动 |
PendingWant (待定 Want)
对应 Android PendingIntent,在 interfaces/inner_api/wantagent/ 中实现:
- PendingWant — 基础待定 Want
- LocalPendingWant — 进程内待定 Want
用于通知栏点击、定时任务等场景,授权接收方在指定时机执行 Want。
显式启动与隐式启动
| 启动方式 | 匹配依据 | 示例 |
|---|---|---|
| 显式启动 | element 指定确定的 bundleName + abilityName |
{ bundleName: "com.example.app", abilityName: "MainAbility" } |
| 隐式启动 | 通过 action + entities + type 匹配已注册的 Ability |
{ action: "ohos.want.action.dial", entities: ["entity.system.home"] } |
解析流程:
startAbility(want)
│
├── element 设置了 bundleName + abilityName?
│ ├── ✅ 显式启动 → 直接发给指定 Ability
│ └── ❌ 进入隐式匹配
│
├── queryAbilityByWant(want) ← BundleManager 查询
│ │ 匹配条件:action + entities + uri/type
│ ▼
├── 返回匹配的 AbilityInfo 列表
│ │
│ ├── 只有一个 → 直接启动
│ ├── 多个 → 弹出系统选择器(应用选择弹窗)
│ └── 无匹配 → 返回错误
│
└── 执行启动
代码示例
// 显式启动:跳转到指定应用的指定页面
let want = {
bundleName: "com.example.settings",
abilityName: "com.example.settings.MainAbility",
parameters: { page: "wifi" }
};
context.startAbility(want);
// 隐式启动:让系统选择能拨号的应用
let dialWant = {
action: "ohos.want.action.dial",
uri: "tel:10086"
};
context.startAbility(dialWant);
7. Context 体系
Context 是 Ability 访问系统能力的入口,采用类继承模式设计,不同类型提供不同范围的 API:
Context (纯虚基类) ← 最基础的接口,定义 getApplicationContext()、getResourceManager() 等
│
├── AbilityContext ← UIAbility 上下文,拥有窗口/UI 能力
│ ├── startAbility(want) ← 启动任意 Ability(隐式/显式)
│ ├── startAbilityForResult() ← 启动并获取返回结果
│ ├── connectAbility(want) ← 连接 ServiceExtension(绑定模式)
│ ├── terminateSelf() ← 终止当前 Ability
│ └── setMissionLabel() ← 设置多任务卡片标题
│
├── ExtensionContext ← 所有 Extension 的基础上下文(不含 UI 能力)
│ ├── startAbility() ← 启动 Ability
│ └── connectAbility() ← 连接 Service
│
│ ├── ServiceExtensionContext ← Service 扩展的上下文
│ │ └── startBackgroundTask() ← 注册后台长时任务
│ │
│ └── UIExtensionContext ← UI 扩展的上下文
│ └── getWindow() ← UI 扩展持有窗口引用
│
└── ApplicationContext ← 应用级上下文,生命周期贯穿整个进程
├── getProcessInfo() ← 获取当前进程信息
├── getRunningProcessInfo() ← 获取运行中进程列表
└── onConfigurationUpdated() ← 系统配置变更通知
各级 Context 的关键差异
| Context | 窗口/UI | Service 启动 | 跨进程绑定 | 典型使用场景 |
|---|---|---|---|---|
AbilityContext |
✅ 有窗口 | ✅ | ✅ | UIAbility 内 |
ExtensionContext |
❌ 无窗口 | ✅ | ✅ | Extension 内 |
ServiceExtensionContext |
❌ 无窗口 | ✅ | ✅ | 后台服务 |
UIExtensionContext |
✅ 有窗口 | ✅ | ✅ | 嵌入 UI |
ApplicationContext |
❌ 无窗口 | ✅ | ❌ | 全局数据访问 |
Context 的工作原理
Context 本身没有"权限"——它是身份令牌(token)+ 系统服务客户端(proxy)+ 进程内环境(resourceManager) 的三合一抽象。
startAbility() 的实现机制
调用链路如下:
开发者调用
context.startAbility(want)
│
▼
AbilityContext::StartAbility(want)
│ 内部持有 AbilityManagerClient 实例
▼
AbilityManagerClient::StartAbility(want)
│ 序列化 Want → MessageParcel
▼
IAbilityManagerProxy::StartAbility()
│ IPC (Binder/DBinder)
▼
AbilityManagerService::StartAbility(want)
│ 验证 callerToken(校验调用方身份)
│ 拦截器链检查
│ 创建 AbilityRecord
▼
组件启动
关键设计是 callerToken:Context 内部持有该 Ability 在 AMS 注册时分配的远程 Token(sptr<IRemoteObject>):
// AbilityContext 内部简化示意
class AbilityContext : public Context {
sptr<IRemoteObject> token_; // AMS 分配的 Ability 身份标识
std::shared_ptr<AbilityManagerClient> abilityClient_; // AMS 客户端代理
ErrCode StartAbility(const Want &want) {
// token_ 证明"我是谁",abilityClient_ 负责发送 IPC
return abilityClient_->StartAbility(want, token_);
}
};
这个 token 是 Ability 创建时由 AMS 通过 IAbilityScheduler 回调注入的:
AMS (系统进程) 应用进程
│ │
├── CreateAbilityRecord() │
├── 分配 token (IRemoteObject) │
│ │
└── ScheduleAbilityTransaction() ──→ │
(携带 want + token + sessionInfo) │
│
UIAbility::OnStart(want)
│ 保存 token 到 AbilityContext
▼
context.startAbility() 可用
所以 context.startAbility() 能工作的本质是:AMS 先信任了这个 Ability(分配了 token),Context 拿着 token 去 AMS 办事,AMS 认 token 不认人。
没有合法 token 的进程发 startAbility 会被 AMS 直接拒绝。
getResourceManager() 的实现机制
资源获取比 IPC 简单——它在进程内完成,不走 IPC:
class ApplicationContext : public Context {
std::shared_ptr<ResourceManager> resourceManager_;
std::shared_ptr<ResourceManager> GetResourceManager() {
return resourceManager_; // 直接返回已加载的实例
}
};
ResourceManager 在应用进程启动时由 AbilityStage 初始化:AppSpawn fork 进程后加载 HAP 包,解析 resources.index(二进制资源索引表),创建 ResourceManager 实例,注入到 ApplicationContext。整个过程是进程内的(no IPC),不涉及系统服务的授权——资源是 HAP 包自带的。
为什么 Context 不直接暴露系统服务 API
| 维度 | Context 代理 | 直接调用服务 |
|---|---|---|
| API 一致性 | UIAbility 和 Extension 用同一个 context.startAbility() |
各自维护一套服务引用 |
| 生命周期安全 | Context 在 Ability 销毁后自动失效(token 被释放) | 开发者容易持有已失效的 token |
| 测试性 | Mock Context 即可模拟全部系统能力 | 需 Mock 多个独立服务 |
| 封装变化 | IPC 协议升级只改 Context 内部实现 | 所有调用点都要改 |
总结
| 能力 | 实现方式 | 走 IPC? | 依赖什么 |
|---|---|---|---|
startAbility() |
Context 持有 AMS 客户端 + token | ✅ IPC | AMS 的授权(token) |
getResourceManager() |
Context 持有进程内 ResourceManager 实例 | ❌ 进程内 | HAP 包资源表 |
getApplicationContext() |
返回同一进程的 ApplicationContext 指针 | ❌ 进程内 | 进程启动时初始化 |
terminateSelf() |
通过 token 通知 AMS 销毁自己 | ✅ IPC | AMS 的授权(token) |
8. AbilityStage 与进程模型
8.1 AbilityStage
Stage 模型的应用入口,相当于 Android 的 Application 类。每个应用进程只有一个 AbilityStage 实例,在其 onCreate() 中执行全局初始化。
class AbilityStage {
onCreate() // 应用进程创建时调用(全局仅一次)
onAcceptWant(want) // 多实例场景分配实例 key(返回 string 标识唯一实例)
onConfigurationUpdated(config) // 系统配置更新(语言、主题、方向等)
}
与 Android Application 的差异
| 维度 | OHOS AbilityStage | Android Application |
|---|---|---|
| 创建时机 | 应用进程启动时 | 应用进程启动时 |
| 多实例标识 | onAcceptWant() 返回 string 标记不同实例 |
无直接对应(通过 taskId/manifest 多进程配置) |
| 初始化范围 | 进程内全局 | 进程内全局 |
| 生命周期 | onCreate 只调用一次 | onCreate 只调用一次 |
| 配置更新 | onConfigurationUpdated() 系统回调 |
onConfigurationChanged() 系统回调 |
8.2 进程架构
OHOS 采用 AppSpawn 孵化 + 沙箱隔离 的进程模型,应用进程由专门的孵化器 fork 产生,而非直接从 init 启动。
进程分类
系统中有三类进程:
| 进程类型 | 例子 | 数量 | 权限级别 |
|---|---|---|---|
| 系统进程 | abilityms、appspawn、windowmanager |
每个服务一个进程 | system_core |
| 应用进程 | 每个应用一个进程 | N(按应用数) | normal / system_basic |
| 扩展进程 | ServiceExtension 进程 | 可独立于 UI 进程运行 | 同所属应用 |
AppSpawn 孵化机制
AppSpawn (独立系统进程)
│ 预先 fork 出空闲进程池
│ 预加载通用 so 库(加速启动)
│
┌──────────┴──────────┐
▼ ▼
App Process A App Process B
(sandbox) (sandbox)
│ │
├── NWeb/NAPI libs ├── NWeb/NAPI libs
├── AbilityManager ├── AbilityManager
│ Client │ Client
├── ResourceManager ├── ResourceManager
└── Runtime (JS/ArkTS) └── Runtime (JS/ArkTS)
与传统 fork+exec 的区别:
| 机制 | OHOS AppSpawn | Linux fork+exec |
|---|---|---|
| 启动速度 | 快(预先 fork,共享库内存页 COW) | 慢(每次重新加载) |
| 共享库 | 预先 mmap 公共 so,写时复制(COW) | 每个进程独立加载 |
| 安全隔离 | 每个应用进程在独立 sandbox 中 | 取决于配置 |
| 资源复用 | 同应用多个 Ability 共享同一进程 | N/A |
进程沙箱
每个应用进程运行在独立的沙箱中:
/sandbox/<userId>/<bundleName>/
├── data/ ← 应用私有数据(其他应用不可见)
├── cache/ ← 缓存文件
├── files/ ← 用户文件
└── base/ ← HAP 解压后的资源
沙箱通过 Linux mount namespace + bind mount 实现:每个应用进程只能看到自己的目录,无法访问其他应用的数据。
进程与组件的关系
应用进程 (bundleName="com.example.app")
│
├── [主线程] AbilityStage
│ ├── UIAbility A ← 前台可见
│ └── UIAbility B ← 后台不可见
│
├── [子线程] ServiceExtension
│ └── 后台任务运行
│
└── JS/ArkTS Runtime (同进程共享 VM 实例)
关键设计:
- 同一应用的所有 UIAbility 和 ExtensionAbility 默认共享同一个进程(可配置独立进程)
- Stage 模型下同进程共享 JS VM 实例(FA 模型每个 Ability 独立 VM)
- 进程由 AMS 通过
AppManagerService管理生命周期,应用不可自建进程
进程优先级与回收
| 进程状态 | 说明 | 回收优先级 |
|---|---|---|
| 前台进程 | 当前用户交互的 Ability | 最低(最后回收) |
| 可见进程 | 有可见但非前台的 Ability | 低 |
| 服务进程 | 运行中的 ServiceExtension | 中 |
| 后台进程 | 全部不可见 | 高 |
| 空进程 | 无任何活跃组件 | 最高(最先回收) |
系统内存不足时,AMS 按此优先级从高到低逐步杀进程。KeepAlive 标记的进程可豁免回收。
8.3 启动流程详解
当系统启动一个应用时,上述架构各层按如下顺序协作:
- 用户点击图标或被其他应用请求
- AppManagerService 通知 AppSpawn fork 进程
- 进程启动 → 加载 Runtime (JS/ArkTS)
- AbilityManagerService 发起 StartAbility
- AbilityStage.onCreate() → UIAbility.OnStart(want)
- 窗口绑定 → UIAbility.OnForeground()
- 界面可见
9. 与 Android 四大组件对比
| OHOS | Android | 相似度 | 差异说明 |
|---|---|---|---|
| UIAbility | Activity | ★★★★☆ | 两者都有明确生命周期(Start/Resume/Pause/Stop vs Start/Foreground/Background/Stop),OHOS 新增 OnNewWant,Android 用 onNewIntent |
| ServiceExtension | Service | ★★★☆☆ | 都支持 bind/unbind 模式,但 OHOS ServiceExtension 只是 Extension 体系的一种,Android Service 是与 Activity 并列的独立组件 |
| DataShareExtension | ContentProvider | ★★★★☆ | 都基于 URI 提供数据共享,OHOS 更强调声明式权限管理(UriPermissionManager) |
| FormExtension | AppWidgetProvider | ★★★☆☆ | 都是桌面卡片,但 OHOS Form 通过 Extension 实现,Android 是 BroadcastReceiver 子类 |
| Want | Intent | ★★★★★ | 核心设计几乎一致:action/uri/params/flags/entities,OHOS 的 ElementName = Android 的 ComponentName |
| PendingWant | PendingIntent | ★★★★★ | 功能完全对应,使用场景一致 |
| AbilityStage | Application | ★★★★☆ | 都是应用级入口,OHOS 多了 onAcceptWant 用于多实例标识 |
| UIExtensionAbility | 无精确对应 | — | Android 不原生支持嵌入其他应用的 UI 组件,需通过 RemoteViews/LayoutInflator 模拟 |
| ShareExtension | ShareProvider | ★★☆☆☆ | 概念上类似但实现差异大 |
| ActionExtension | 无 | — | OHOS 独有模式 |
| AutoFillExtension | AutofillService | ★★★☆☆ | 目标一致但实现机制不同 |
| 无对应 | BroadcastReceiver | — | OHOS 无独立广播接收器,通过 commonEvent 系统能力 + EventManager 实现 |
| 无对应 | JobScheduler | — | OHOS 通过 WorkScheduler 系统能力替代 |
核心差异总结
| 维度 | OHOS | Android |
|---|---|---|
| 组件模型 | 两阶段:FA(旧)+ Stage(新) | 四组件统一模型(API 1+) |
| Extension 体系 | 强扩展性,8+ 预制 Extension 类型 | 仅 4 个基础组件,功能靠叠加 |
| 跨进程通信 | IPC/RPC(基于 SAMGR 框架) | Binder(核心 IPC 框架) |
| 跨设备迁移 | 原生支持 (FLAG_ABILITY_CONTINUATION) |
无原生支持(需自行实现) |
| 安全模型 | ACP(Access Control Policy) + APL | 基于签名 + 权限声明 |
| 多用户支持 | 原生 SwitchUserManager |
UserManager + 多用户 API |
| 窗口粒度 | Ability 直接绑定 Window | Activity 通过 WindowManager |
| 免安装/按需 | FreeInstallManager 原生支持 |
SplitInstallManager (Play Core) |
| 广播机制 | 无独立组件,通过 @ohos.commonEvent |
BroadcastReceiver 独立组件 |
| 前端框架 | 强绑定 ArkUI / 声明式 UI | 无绑定(XML/Compose/三方框架) |
10. 关键技术点
10.1 状态恢复
UIAbility 支持 OnSaveState 回调,在系统回收前保存状态,类比 Android 的 onSaveInstanceState。
触发时机:
- 系统内存不足,需要回收后台 Ability 时
- 应用被切换到后台一定时间后
- 设备配置变更导致重建时
工作流程:
系统决定回收 Ability
│
▼
AbilityManagerService 决定触发状态保存
│
▼
UIAbility.OnSaveState(state)
│ 开发者在此回调中向 state 写入关键数据
▼
AMS 序列化 state 到磁盘
│
▼
[进程被回收]
--- 用户重新打开 ---
AbilityManagerService 检查是否有保存的状态
│
▼
UIAbility.OnStart(want)
│ want.parameters 中包含保存的状态数据
▼
开发者从 want 参数中恢复 UI 状态
与 Android 的关键差异:
| 维度 | OHOS | Android |
|---|---|---|
| 保存回调 | OnSaveState(state) |
onSaveInstanceState(outState) |
| 恢复方式 | OnStart(want) 参数中携带 |
onCreate(savedInstanceState) 参数 |
| 序列化 | WantParams(可包含任意结构化数据) |
Bundle(key-value) |
| 触发条件 | AMS 主动触发 | ActivityManagerService 触发 |
10.2 窗口协调
UIAbility 通过 sessionInfo 与 WindowScene 交互,支持多窗口模式。
窗口绑定时机:
AbilityManagerService
│
├── StartAbility(want)
│ │
│ ▼
├── 创建 AbilityRecord
│ │
│ ▼
├── 创建 SessionInfo(多窗口会话信息)
│ │ 含:窗口模式(全屏/分屏/悬浮)
│ │ 窗口类型(主窗口/子窗口)
│ │ displayId(目标屏幕)
│ │
│ ▼
└── 调度到 UIAbility.OnStart(want, sessionInfo)
│
▼
WindowStage (由 ACE 引擎管理)
│
├── 根据 sessionInfo 创建对应类型的窗口
├── 绑定窗口到屏幕
└── UI 内容渲染
窗口模式: OHOS 支持全屏、分屏(主/副)、悬浮窗、画中画四种模式,每种模式对应不同的 WindowMode枚举值。sessionInfo 中携带的窗口模式决定了 WindowStage 创建什么类型的窗口。
多窗口协同: 分屏模式下,两个 Ability 同时可见。AMS 通过 MissionListManager 管理各窗口的任务栈关系,WindowManager 负责计算各自的窗口区域和避让区域。
10.3 应用热修复
通过 QuickFixManager + 补丁包实现运行时修复,无需重新安装应用。
工作流程:
发现线上 Bug
│
├── 生成补丁包(.hqf 格式)
│ ├── 替换的 so 库 / 字节码文件
│ └── 补丁清单(patch version、目标应用、文件名)
│
├── 推送到设备(通过应用市场)
│
├── QuickFixManager 接收补丁包
│ │
│ ├── 校验签名
│ ├── 对比 patch version
│ ├── 替换对应文件(应用进程无需重启时热替换 so)
│ └── 更新补丁清单
│
└── 应用下次启动时自动使用补丁后的代码
10.4 多用户隔离
SwitchUserManager 监听账户切换,AbilityManagerService 按用户隔离组件实例和数据。
隔离机制:
用户 A (userId=100)
├── AbilityManagerService 中 AbilityRecord 组 userId=100
├── 应用进程:com.example.app (uid=10100)
├── 沙箱目录:/sandbox/100/com.example.app/
└── 设置项:settings database 按 userId 分表
用户 B (userId=101)
├── AbilityManagerService 中 AbilityRecord 组 userId=101
├── 应用进程:com.example.app (uid=10101)
├── 沙箱目录:/sandbox/101/com.example.app/
└── 设置项:settings database 按 userId 分表
切换用户时,AMS 销毁旧用户的全部组件,拉起新用户的桌面和系统服务。每个用户的应用进程独立运行,操作系统级 uid 隔离。
10.5 后台管理
OHOS 对后台 Ability 实行严格的资源管理:
| 管理维度 | 机制 | 说明 |
|---|---|---|
| 进程优先级 | 5级优先级(前台 > 可见 > 服务 > 后台 > 空) | 低优先级进程在内存不足时优先回收 |
| KeepAlive | 系统级标记,豁免回收 | 仅系统关键服务(SystemUI、电话服务等)可使用 |
| Kiosk 模式 | 强制前台锁定 | 企业/教育设备专用,阻止切换到其他应用 |
| 后台运行时长 | 系统策略限制 | 后台 Ability 超过时限会被 AMS 暂停或回收 |
| 持久化任务 | startBackgroundTask() |
通过 ServiceExtensionContext 注册长时任务(如音乐播放、导航) |

浙公网安备 33010602011771号