harmony 鸿蒙@ohos.app.ability.sendableContextManager (sendable上下文管理)
@ohos.app.ability.sendableContextManager (sendable上下文管理)
sendableContextManager模块提供Context与SendableContext相互转换的能力。
说明:
- 本模块首批接口从API version 12 开始支持。后续版本的新增接口,采用上角标单独标记接口的起始版本。
- 本模块接口仅可在Stage模型下使用。
使用场景
本模块主要用于ArkTS并发实例间(包括主线程、TaskPool&Worker工作线程)的数据传递。
例如,以主线程向子线程传递Sendable数据,转换过程如下: - 主线程向子线程传递Sendable数据时,需要将Context转换为SendableContext。 - 子线程使用Sendable数据时,需要将SendableContext转换为Context。
这里的Context与createModuleContext方法创建的Context不同,具体差异如下: - 与SendableContext相互转换的Context:ArkTS并发实例持有的应用侧Context是不同的实例,底层对应同一个Context对象。当一个实例中Context属性和方法被修改时,相关实例中的Context属性和方法将会同步修改。其中,Context实例中的eventHub属性比较特殊,不同实例中的eventHub是独立的对象,不支持跨ArkTS实例使用。如果需要使用EventHub跨实例传递数据,可以通过setEventHubMultithreadingEnabled启用跨线程数据传递功能。
- 通过createModuleContext创建的Context:ArkTS并发实例持有的应用侧Context是不同的实例,底层对应不同的Context对象。
约束限制
“Context转换为SendableContext”和“SendableContext转换为Context”两个环节中的Context类型必须保持一致。目前支持转换的Context包括Context、ApplicationContext、AbilityStageContext、UIAbilityContext。
导入模块
import { sendableContextManager } from '@kit.AbilityKit';
属性
系统能力:SystemCapability.Ability.AbilityRuntime.Core
原子化服务API:从API version 12开始,该接口支持在原子化服务中使用。
名称 | 类型 | 必填 | 说明 |
---|---|---|---|
SendableContext | SendableContext | 是 | SendableContext二级模块。 |
示例:
import { sendableContextManager } from '@kit.AbilityKit';
let sendableContext: sendableContextManager.SendableContext;
sendableContextManager.convertFromContext
convertFromContext(context: common.Context): SendableContext
将Context转换为SendableContext对象。
系统能力:SystemCapability.Ability.AbilityRuntime.Core
原子化服务API:从API version 12开始,该接口支持在原子化服务中使用。
参数:
参数名 | 类型 | 必填 | 说明 |
---|---|---|---|
context | common.Context | 是 | Context对象。支持Context基类,ApplicationContext、AbilityStageContext和UIAbilityContext子类。 |
返回值:
类型 | 说明 |
---|---|
SendableContext | SendableContext对象。 |
错误码:
以下错误码详细介绍请参考通用错误码。
错误码ID | 错误信息 |
---|---|
401 | If the input parameter invalid. Possible causes: 1.Incorrect parameter types; 2.Parameter verification failed. |
示例:
import { AbilityConstant, UIAbility, Want, sendableContextManager } from '@kit.AbilityKit';
import { hilog } from '@kit.PerformanceAnalysisKit';
import { worker } from '@kit.ArkTS';
@Sendable
export class SendableObject {
constructor(sendableContext: sendableContextManager.SendableContext) {
this.sendableContext = sendableContext;
}
sendableContext: sendableContextManager.SendableContext;
// other sendable object
}
export default class EntryAbility extends UIAbility {
worker: worker.ThreadWorker = new worker.ThreadWorker('entry/ets/workers/Worker.ets');
onCreate(want: Want, launchParam: AbilityConstant.LaunchParam): void {
hilog.info(0x0000, 'testTag', '%{public}s', 'Ability onCreate');
// convert and post
try {
let sendableContext: sendableContextManager.SendableContext = sendableContextManager.convertFromContext(this.context);
let object: SendableObject = new SendableObject(sendableContext);
hilog.info(0x0000, 'testTag', '%{public}s', 'Ability post message');
this.worker.postMessageWithSharedSendable(object);
} catch (error) {
hilog.error(0x0000, 'testTag', 'convertFromContext failed %{public}s', JSON.stringify(error));
}
}
}
sendableContextManager.convertToContext
convertToContext(sendableContext: SendableContext): common.Context
将SendableContext对象转换为Context。
系统能力:SystemCapability.Ability.AbilityRuntime.Core
原子化服务API:从API version 12开始,该接口支持在原子化服务中使用。
参数:
参数名 | 类型 | 必填 | 说明 |
---|---|---|---|
sendableContext | SendableContext | 是 | SendableContext对象。 |
返回值:
类型 | 说明 |
---|---|
common.Context | Context对象。 |
错误码:
以下错误码详细介绍请参考通用错误码。
错误码ID | 错误信息 |
---|---|
401 | If the input parameter invalid. Possible causes: 1.Incorrect parameter types; 2.Parameter verification failed. |
示例:
主线程传递Context:
import { AbilityConstant, UIAbility, Want, common, sendableContextManager } from '@kit.AbilityKit';
import { hilog } from '@kit.PerformanceAnalysisKit';
import { worker } from '@kit.ArkTS';
@Sendable
export class SendableObject {
constructor(sendableContext: sendableContextManager.SendableContext, contextName: string) {
this.sendableContext = sendableContext;
this.contextName = contextName;
}
sendableContext: sendableContextManager.SendableContext;
contextName: string;
}
export default class EntryAbility extends UIAbility {
worker: worker.ThreadWorker = new worker.ThreadWorker('entry/ets/workers/Worker.ets');
onCreate(want: Want, launchParam: AbilityConstant.LaunchParam): void {
hilog.info(0x0000, 'testTag', '%{public}s', 'Ability onCreate');
// convert and post
try {
let context: common.Context = this.context as common.Context;
let sendableContext: sendableContextManager.SendableContext = sendableContextManager.convertFromContext(context);
let object: SendableObject = new SendableObject(sendableContext, 'BaseContext');
hilog.info(0x0000, 'testTag', '%{public}s', 'Ability post message');
this.worker.postMessageWithSharedSendable(object);
} catch (error) {
hilog.error(0x0000, 'testTag', 'convertFromContext failed %{public}s', JSON.stringify(error));
}
}
}
Worker线程接收Context:
import { ErrorEvent, MessageEvents, ThreadWorkerGlobalScope, worker } from '@kit.ArkTS';
import { common, sendableContextManager } from '@kit.AbilityKit';
import { hilog } from '@kit.PerformanceAnalysisKit';
@Sendable
export class SendableObject {
constructor(sendableContext: sendableContextManager.SendableContext, contextName: string) {
this.sendableContext = sendableContext;
this.contextName = contextName;
}
sendableContext: sendableContextManager.SendableContext;
contextName: string;
}
const workerPort: ThreadWorkerGlobalScope = worker.workerPort;
workerPort.onmessage = (e: MessageEvents) => {
let object: SendableObject = e.data;
let sendableContext: sendableContextManager.SendableContext = object.sendableContext;
if (object.contextName == 'BaseContext') {
hilog.info(0x0000, 'testTag', '%{public}s', 'convert to context.');
try {
let context: common.Context = sendableContextManager.convertToContext(sendableContext);
// 获取context后获取沙箱路径
hilog.info(0x0000, 'testTag', 'worker context.databaseDir: %{public}s', context.databaseDir);
} catch (error) {
hilog.error(0x0000, 'testTag', 'convertToContext failed %{public}s', JSON.stringify(error));
}
}
}
workerPort.onmessageerror = (e: MessageEvents) => {
hilog.info(0x0000, 'testTag', '%{public}s', 'onmessageerror');
}
workerPort.onerror = (e: ErrorEvent) => {
hilog.info(0x0000, 'testTag', '%{public}s', 'onerror');
}
sendableContextManager.convertToApplicationContext
convertToApplicationContext(sendableContext: SendableContext): common.ApplicationContext
将SendableContext对象转换为ApplicationContext。
系统能力:SystemCapability.Ability.AbilityRuntime.Core
原子化服务API:从API version 12开始,该接口支持在原子化服务中使用。
参数:
参数名 | 类型 | 必填 | 说明 |
---|---|---|---|
sendableContext | SendableContext | 是 | SendableContext对象。 |
返回值:
类型 | 说明 |
---|---|
common.ApplicationContext | ApplicationContext对象。 |
错误码:
以下错误码详细介绍请参考通用错误码。
错误码ID | 错误信息 |
---|---|
401 | If the input parameter invalid. Possible causes: 1.Incorrect parameter types; 2.Parameter verification failed. |
示例:
主线程传递Context:
import { AbilityConstant, UIAbility, Want, common, sendableContextManager } from '@kit.AbilityKit';
import { hilog } from '@kit.PerformanceAnalysisKit';
import { worker } from '@kit.ArkTS';
@Sendable
export class SendableObject {
constructor(sendableContext: sendableContextManager.SendableContext, contextName: string) {
this.sendableContext = sendableContext;
this.contextName = contextName;
}
sendableContext: sendableContextManager.SendableContext;
contextName: string;
}
export default class EntryAbility extends UIAbility {
worker: worker.ThreadWorker = new worker.ThreadWorker('entry/ets/workers/Worker.ets');
onCreate(want: Want, launchParam: AbilityConstant.LaunchParam): void {
hilog.info(0x0000, 'testTag', '%{public}s', 'Ability onCreate');
// convert and post
try {
let context: common.Context = this.context as common.Context;
let applicationContext = context.getApplicationContext();
let sendableContext: sendableContextManager.SendableContext = sendableContextManager.convertFromContext(applicationContext);
let object: SendableObject = new SendableObject(sendableContext, 'ApplicationContext');
hilog.info(0x0000, 'testTag', '%{public}s', 'Ability post message');
this.worker.postMessageWithSharedSendable(object);
} catch (error) {
hilog.error(0x0000, 'testTag', 'convertFromContext failed %{public}s', JSON.stringify(error));
}
}
}
Worker线程接收Context:
import { ErrorEvent, MessageEvents, ThreadWorkerGlobalScope, worker } from '@kit.ArkTS';
import { common, sendableContextManager } from '@kit.AbilityKit';
import { hilog } from '@kit.PerformanceAnalysisKit';
@Sendable
export class SendableObject {
constructor(sendableContext: sendableContextManager.SendableContext, contextName: string) {
this.sendableContext = sendableContext;
this.contextName = contextName;
}
sendableContext: sendableContextManager.SendableContext;
contextName: string;
}
const workerPort: ThreadWorkerGlobalScope = worker.workerPort;
workerPort.onmessage = (e: MessageEvents) => {
let object: SendableObject = e.data;
let sendableContext: sendableContextManager.SendableContext = object.sendableContext;
if (object.contextName == 'ApplicationContext') {
hilog.info(0x0000, 'testTag', '%{public}s', 'convert to application context.');
try {
let context: common.ApplicationContext = sendableContextManager.convertToApplicationContext(sendableContext);
// 获取context后获取沙箱路径
hilog.info(0x0000, 'testTag', 'worker context.databaseDir: %{public}s', context.databaseDir);
} catch (error) {
hilog.error(0x0000, 'testTag', 'convertToApplicationContext failed %{public}s', JSON.stringify(error));
}
}
}
workerPort.onmessageerror = (e: MessageEvents) => {
hilog.info(0x0000, 'testTag', '%{public}s', 'onmessageerror');
}
workerPort.onerror = (e: ErrorEvent) => {
hilog.info(0x0000, 'testTag', '%{public}s', 'onerror');
}
sendableContextManager.convertToAbilityStageContext
convertToAbilityStageContext(sendableContext: SendableContext): common.AbilityStageContext
将SendableContext对象转换为AbilityStageContext。
系统能力:SystemCapability.Ability.AbilityRuntime.Core
原子化服务API:从API version 12开始,该接口支持在原子化服务中使用。
参数:
参数名 | 类型 | 必填 | 说明 |
---|---|---|---|
sendableContext | SendableContext | 是 | SendableContext对象。 |
返回值:
类型 | 说明 |
---|---|
common.AbilityStageContext | AbilityStageContext对象。 |
错误码:
以下错误码详细介绍请参考通用错误码。
错误码ID | 错误信息 |
---|---|
401 | If the input parameter invalid. Possible causes: 1.Incorrect parameter types; 2.Parameter verification failed. |
示例:
主线程传递Context:
import { UIAbility, sendableContextManager } from '@kit.AbilityKit';
import { hilog } from '@kit.PerformanceAnalysisKit';
import { worker } from '@kit.ArkTS';
@Sendable
export class SendableObject {
constructor(sendableContext: sendableContextManager.SendableContext, contextName: string) {
this.sendableContext = sendableContext;
this.contextName = contextName;
}
sendableContext: sendableContextManager.SendableContext;
contextName: string;
}
export default class EntryAbility extends UIAbility {
worker: worker.ThreadWorker = new worker.ThreadWorker('entry/ets/workers/Worker.ets');
onCreate(): void {
hilog.info(0x0000, 'testTag', '%{public}s', 'AbilityStage onCreate');
// convert and post
try {
let sendableContext: sendableContextManager.SendableContext = sendableContextManager.convertFromContext(this.context);
let object: SendableObject = new SendableObject(sendableContext, 'AbilityStageContext');
hilog.info(0x0000, 'testTag', '%{public}s', 'AbilityStage post message');
this.worker.postMessageWithSharedSendable(object);
} catch (error) {
hilog.error(0x0000, 'testTag', 'convertFromContext failed %{public}s', JSON.stringify(error));
}
}
}
Worker线程接收Context:
import { ErrorEvent, MessageEvents, ThreadWorkerGlobalScope, worker } from '@kit.ArkTS';
import { common, sendableContextManager } from '@kit.AbilityKit';
import { hilog } from '@kit.PerformanceAnalysisKit';
@Sendable
export class SendableObject {
constructor(sendableContext: sendableContextManager.SendableContext, contextName: string) {
this.sendableContext = sendableContext;
this.contextName = contextName;
}
sendableContext: sendableContextManager.SendableContext;
contextName: string;
}
const workerPort: ThreadWorkerGlobalScope = worker.workerPort;
workerPort.onmessage = (e: MessageEvents) => {
let object: SendableObject = e.data;
let sendableContext: sendableContextManager.SendableContext = object.sendableContext;
if (object.contextName == 'AbilityStageContext') {
hilog.info(0x0000, 'testTag', '%{public}s', 'convert to abilitystage context.');
try {
let context: common.AbilityStageContext = sendableContextManager.convertToAbilityStageContext(sendableContext);
// 获取context后获取沙箱路径
hilog.info(0x0000, 'testTag', 'worker context.databaseDir: %{public}s', context.databaseDir);
} catch (error) {
hilog.error(0x0000, 'testTag', 'convertToAbilityStageContext failed %{public}s', JSON.stringify(error));
}
}
}
workerPort.onmessageerror = (e: MessageEvents) => {
hilog.info(0x0000, 'testTag', '%{public}s', 'onmessageerror');
}
workerPort.onerror = (e: ErrorEvent) => {
hilog.info(0x0000, 'testTag', '%{public}s', 'onerror');
}
sendableContextManager.convertToUIAbilityContext
convertToUIAbilityContext(sendableContext: SendableContext): common.UIAbilityContext
将SendableContext对象转换为UIAbilityContext。
系统能力:SystemCapability.Ability.AbilityRuntime.Core
原子化服务API:从API version 12开始,该接口支持在原子化服务中使用。
参数:
参数名 | 类型 | 必填 | 说明 |
---|---|---|---|
sendableContext | SendableContext | 是 | SendableContext对象。 |
返回值:
类型 | 说明 |
---|---|
common.UIAbilityContext | UIAbilityContext对象。 |
错误码:
以下错误码详细介绍请参考通用错误码。
错误码ID | 错误信息 |
---|---|
401 | If the input parameter invalid. Possible causes: 1.Incorrect parameter types; 2.Parameter verification failed. |
示例:
主线程传递Context:
import { AbilityConstant, UIAbility, Want, common, sendableContextManager } from '@kit.AbilityKit';
import { hilog } from '@kit.PerformanceAnalysisKit';
import { worker } from '@kit.ArkTS';
@Sendable
export class SendableObject {
constructor(sendableContext: sendableContextManager.SendableContext, contextName: string) {
this.sendableContext = sendableContext;
this.contextName = contextName;
}
sendableContext: sendableContextManager.SendableContext;
contextName: string;
}
export default class EntryAbility extends UIAbility {
worker: worker.ThreadWorker = new worker.ThreadWorker('entry/ets/workers/Worker.ets');
onCreate(want: Want, launchParam: AbilityConstant.LaunchParam): void {
hilog.info(0x0000, 'testTag', '%{public}s', 'Ability onCreate');
// convert and post
try {
let sendableContext: sendableContextManager.SendableContext = sendableContextManager.convertFromContext(this.context);
let object: SendableObject = new SendableObject(sendableContext, 'EntryAbilityContext');
hilog.info(0x0000, 'testTag', '%{public}s', 'Ability post message');
this.worker.postMessageWithSharedSendable(object);
} catch (error) {
hilog.error(0x0000, 'testTag', 'convertFromContext failed %{public}s', JSON.stringify(error));
}
}
}
Worker线程接收Context:
import { ErrorEvent, MessageEvents, ThreadWorkerGlobalScope, worker } from '@kit.ArkTS';
import { common, sendableContextManager } from '@kit.AbilityKit';
import { hilog } from '@kit.PerformanceAnalysisKit';
@Sendable
export class SendableObject {
constructor(sendableContext: sendableContextManager.SendableContext, contextName: string) {
this.sendableContext = sendableContext;
this.contextName = contextName;
}
sendableContext: sendableContextManager.SendableContext;
contextName: string;
}
const workerPort: ThreadWorkerGlobalScope = worker.workerPort;
workerPort.onmessage = (e: MessageEvents) => {
let object: SendableObject = e.data;
let sendableContext: sendableContextManager.SendableContext = object.sendableContext;
if (object.contextName == 'EntryAbilityContext') {
hilog.info(0x0000, 'testTag', '%{public}s', 'convert to uiability context.');
try {
let context: common.UIAbilityContext = sendableContextManager.convertToUIAbilityContext(sendableContext);
// 获取context后获取沙箱路径
hilog.info(0x0000, 'testTag', 'worker context.databaseDir: %{public}s', context.databaseDir);
} catch (error) {
hilog.error(0x0000, 'testTag', 'convertToUIAbilityContext failed %{public}s', JSON.stringify(error));
}
}
}
workerPort.onmessageerror = (e: MessageEvents) => {
hilog.info(0x0000, 'testTag', '%{public}s', 'onmessageerror');
}
workerPort.onerror = (e: ErrorEvent) => {
hilog.info(0x0000, 'testTag', '%{public}s', 'onerror');
}
sendableContextManager.setEventHubMultithreadingEnabled20+
setEventHubMultithreadingEnabled(context: common.Context, enabled: boolean): void
如果需要使用Context中的EventHub进行跨线程通信,可以通过该接口来启用该Context的Eventhub跨线程数据传递功能。
说明:
- 当多个Context进行通信时,需要调用该接口设置每个Context都支持EventHub跨线程数据传递功能。
- 启用该接口前,数据是通过引用的方式传递的。启用该接口后,数据是通过序列化的方式传递的,即发送端线程与接收端线程的数据相互独立。
系统能力:SystemCapability.Ability.AbilityRuntime.Core
原子化服务API:从API version 20开始,该接口支持在原子化服务中使用。
参数:
参数名 | 类型 | 必填 | 说明 |
---|---|---|---|
context | common.Context | 是 | Context对象。其中,Eventhub支持传递的序列化数据类型参见序列化支持的类型,数据大小不超过16MB。 |
enabled | boolean | 是 | 表示是否启用Context的EventHub跨线程通信能力。true表示启用,false表示禁用。 |
示例:
主线程启用Context中EventHub的跨线程通信能力,并将Context转换为SenableContext后发送到Worker线程。
import { common, sendableContextManager } from '@kit.AbilityKit';
import { worker } from '@kit.ArkTS';
import { hilog } from '@kit.PerformanceAnalysisKit';
const DOMAIN = 0x0000;
@Sendable
export class SendableObject {
constructor(sendableContext: sendableContextManager.SendableContext, contextName: string) {
this.sendableContext = sendableContext;
this.contextName = contextName;
}
sendableContext: sendableContextManager.SendableContext;
contextName: string;
}
@Entry
@Component
struct Index {
@State context: common.Context|undefined = this.getUIContext().getHostContext();
worker1: worker.ThreadWorker = new worker.ThreadWorker('entry/ets/workers/Worker.ets');
aboutToAppear(): void {
let context: common.Context = this.context as common.Context;
context.eventHub.on('event1', this.eventFunc);
context.eventHub.emit('event1', 'xingming', 22);
}
eventFunc(name: string, age: number) {
hilog.info(DOMAIN, 'testTag', 'name %{public}s age %{public}d', name, age);
}
build() {
Column() {
Row() {
Button('thread 1')
.size({ width: 100, height: 100 })
.onClick(() => {
if (this.context == undefined) {
return;
}
sendableContextManager.setEventHubMultithreadingEnabled(this.context, true);
let sendableContext: sendableContextManager.SendableContext =
sendableContextManager.convertFromContext(this.context);
let object: SendableObject = new SendableObject(sendableContext, 'BaseContext');
this.worker1.postMessageWithSharedSendable(object);
})
}
}
}
}
Worker线程接收到SendableContext后,将其转换为Context。然后,在Worker线程内,启用Context中EventHub的跨线程通信能力,并通过该功能向主线程发送消息。
import { ErrorEvent, MessageEvents, ThreadWorkerGlobalScope, worker } from '@kit.ArkTS';
import { common, sendableContextManager } from '@kit.AbilityKit';
import { hilog } from '@kit.PerformanceAnalysisKit';
const DOMAIN = 0x0000;
@Sendable
export class SendableObject {
constructor(sendableContext: sendableContextManager.SendableContext, contextName: string) {
this.sendableContext = sendableContext;
this.contextName = contextName;
}
sendableContext: sendableContextManager.SendableContext;
contextName: string;
}
const workerPort: ThreadWorkerGlobalScope = worker.workerPort;
workerPort.onmessage = (e: MessageEvents) => {
let object: SendableObject = e.data;
let sendableContext: sendableContextManager.SendableContext = object.sendableContext;
if (object.contextName == 'BaseContext') {
try {
let context: common.Context = sendableContextManager.convertToContext(sendableContext);
sendableContextManager.setEventHubMultithreadingEnabled(context, true);
context.eventHub.emit('event1', 'xingming', 40);
} catch (error) {
hilog.error(DOMAIN, 'testTag', 'convertToContext failed %{public}s', JSON.stringify(error));
}
}
};
workerPort.onmessageerror = (e: MessageEvents) => {
hilog.error(DOMAIN, 'testTag', '%{public}s', 'onmessageerror');
};
workerPort.onerror = (e: ErrorEvent) => {
hilog.error(DOMAIN, 'testTag', '%{public}s', 'onerror');
};
你可能感兴趣的鸿蒙文章
harmony 鸿蒙OH_NativeBundle_ApplicationInfo
harmony 鸿蒙OH_NativeBundle_ElementName
harmony 鸿蒙ability_base_common.h
- 所属分类: 后端技术
- 本文标签:
热门推荐
-
2、 - 优质文章
-
3、 gate.io
-
8、 golang
-
9、 openharmony
-
10、 Vue中input框自动聚焦