Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
OpenHarmony
Docs
提交
417ae4c3
D
Docs
项目概览
OpenHarmony
/
Docs
1 年多 前同步成功
通知
159
Star
292
Fork
28
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
D
Docs
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
提交
Issue看板
提交
417ae4c3
编写于
12月 02, 2022
作者:
H
HuangXW
浏览文件
操作
浏览文件
下载
电子邮件补丁
差异文件
FA_ServiceAbility文档优化
Signed-off-by:
N
HuangXW
<
huangxinwei4@huawei.com
>
上级
3a1e4d85
变更
2
显示空白变更内容
内联
并排
Showing
2 changed file
with
199 addition
and
265 deletion
+199
-265
zh-cn/application-dev/ability/fa-serviceability.md
zh-cn/application-dev/ability/fa-serviceability.md
+198
-264
zh-cn/application-dev/reference/apis/js-apis-extension-context.md
...plication-dev/reference/apis/js-apis-extension-context.md
+1
-1
未找到文件。
zh-cn/application-dev/ability/fa-serviceability.md
浏览文件 @
417ae4c3
...
...
@@ -3,17 +3,21 @@
## 场景介绍
基于Service模板的Ability(以下简称“Service”)主要用于后台运行任务(如执行音乐播放、文件下载等),但不提供用户交互界面。Service可由其他应用或Ability启动。即使用户切换到其他应用,Service仍将在后台继续运行。
##
接口说明
##
生命周期
**表1**
Service中相关生命周期API功能介绍
|接口名|描述|
|:------|:------|
|onStart?(): void|该方法在创建Service的时候调用,用于Service的初始化
。在Service的整个生命周期只会调用一次,调用时传入的Want应为空
。|
|onStart?(): void|该方法在创建Service的时候调用,用于Service的初始化
,在Service的整个生命周期只会调用一次
。|
|onCommand?(want: Want, startId: number): void|在Service创建完成之后调用,该方法在客户端每次启动该Service时都会调用,开发者可以在该方法中做一些调用统计、初始化类的操作。|
|onConnect?(want: Want): rpc.RemoteObject|在Ability和Service连接时调用。|
|onDisconnect?(want: Want): void|在Ability与绑定的Service断开连接时调用。|
|onStop?(): void|在Service销毁时调用。开发者应通过实现此方法来清理资源,如关闭线程、注册的侦听器等。|
onCommand()与onConnect()的区别在于:
-
onCommand()只能被startAbility或startAbilityForResult触发,客户端每次启动Service均会触发该回调
-
onConnect()只能被connectAbility触发,客户端每次与Servcie建立新的连接时会触发该回调
## 开发步骤
### 创建注册Service
...
...
@@ -22,7 +26,7 @@
创建Service的代码示例如下:
```
javascript
```
ts
export
default
{
onStart
()
{
console
.
log
(
'
ServiceAbility onStart
'
);
...
...
@@ -32,14 +36,15 @@
},
onConnect
(
want
)
{
console
.
log
(
'
ServiceAbility OnConnect
'
);
return
new
FirstServiceAbilityStub
(
'
test
'
);
// ServiceAbilityStub的实现在下文给出
return
new
ServiceAbilityStub
(
'
test
'
);
},
onDisconnect
(
want
)
{
console
.
log
(
'
ServiceAbility OnDisConnect
'
);
},
onStop
()
{
console
.
log
(
'
ServiceAbility onStop
'
);
},
}
}
```
...
...
@@ -47,7 +52,7 @@
Service需要在应用配置文件config.json中进行注册,注册类型type需要设置为service。
```
j
avascript
```
j
son
{
"module"
:
{
"abilities"
:
[
...
...
@@ -72,50 +77,61 @@ Ability为开发者提供了startAbility()方法来启动另外一个Ability。
开发者可以通过构造包含bundleName与abilityName的Want对象来设置目标Service信息。参数的含义如下:
-
bundleName:表示包名称。
-
bundleName:表示
对端应用的
包名称。
-
abilityName:表示待启动的Ability名称。
启动本地设备Service的代码示例如下:
```
javascript
import
featureAbility
from
'
@ohos.ability.featureAbility
'
;
let
promise
=
featureAbility
.
startAbility
(
```
ts
import
featureAbility
from
'
@ohos.ability.featureAbility
'
featureAbility
.
startAbility
(
{
want
:
{
bundleName
:
"
com.jstest.service
"
,
abilityName
:
"
com.jstest.service.ServiceAbility
"
,
}
,
abilityName
:
"
com.jstest.service.ServiceAbility
"
}
}
);
).
then
((
err
)
=>
{
console
.
log
(
"
startService success
"
);
}).
catch
(
err
=>
{
console
.
log
(
"
startService FAILED
"
);
});
```
执行上述代码后,Ability将通过startAbility() 方法来启动Service。
-
如果Service尚未运行,则系统会先
调用onStart()来初始化Service,再回调Service的onCommand()方法来启动Service
。
-
如果Service正在运行,则系统会直接回调Service的onCommand()方法
来启动Service
。
-
如果Service尚未运行,则系统会先
初始化Service,然后回调onStart()来启动Service,再回调onCommand()方法
。
-
如果Service正在运行,则系统会直接回调Service的onCommand()方法。
启动远端设备Service的代码示例如下,
getRemoteDeviceId()方法详见
[
连接远程Service
](
#连接远程service当前仅对系统应用开放
)
:
启动远端设备Service的代码示例如下,
详见
[
连接远程Service
](
fa-serviceability.md
#连接远程service当前仅对系统应用开放
)
:
```
javascript
import
featureAbility
from
'
@ohos.ability.featureAbility
'
;
let
promise
=
featureAbility
.
startAbility
(
```
ts
import
featureAbility
from
'
@ohos.ability.featureAbility
'
featureAbility
.
startAbility
(
{
want
:
{
deviceId
:
getRemoteDeviceId
(),
//
远端设备Id
deviceId
:
remoteDeviceId
,
//
远端设备Id
bundleName
:
"
com.jstest.service
"
,
abilityName
:
"
com.jstest.service.ServiceAbility
"
,
}
,
abilityName
:
"
com.jstest.service.ServiceAbility
"
}
}
);
).
then
((
err
)
=>
{
console
.
log
(
"
startService success
"
);
}).
catch
(
err
=>
{
console
.
log
(
"
startService FAILED
"
);
});
```
### 停止Service
Service一旦创建就会一直保持在后台运行,除非必须回收内存资源,否则系统不会停止或销毁Service。
常规情况下,Service可以将自己停止,或者被系统停止,具体场景如下:
-
Service调用particleAbility.terminateSelf()方法将自己停止。
-
Service所在的应用进程退出,Service将随着进程被回收。
-
若Service仅仅是通过connectAbility()方法被访问的(从未执行过onCommand()回调),那么当最后一个连接被断开后,系统会将Service停止。
### 连接本地Service
...
...
@@ -128,189 +144,151 @@ let promise = featureAbility.startAbility(
使用OpenHarmony IDL(OpenHarmony Interface Definition Language)来自动生成对应客户端服务端及IRemoteObject代码,具体示例代码和说明请参考:
-
[
`OpenHarmony IDL`:TS开发步骤
](
https://gitee.com/openharmony/docs/blob/master/zh-cn/application-dev/IDL/idl-guidelines.md#ts%E5%BC%80%E5%8F%91%E6%AD%A5%E9%AA%A4
)
-
[
`OpenHarmony IDL`:TS开发步骤
](
../IDL/idl-guidelines.md#ts
)
2.
在对应文件编写代码
在使用connectAbility()处理回调时,需要传入目标Service的Want与IAbilityConnection的实例。IAbilityConnection提供了以下方法供开发者实现:onConnect()是用来处理连接Service成功的回调,onDisconnect()是用来处理Service异常死亡的回调,onFailed()是用来处理连接Service失败的回调。
在使用connectAbility()时,需要传入目标Service的Want与ConnectOptions的实例,其中ConnectOptions封装了三个回调,分别对应不同情况,开发者需自行实现:
- onConnect():用来处理连接Service成功的回调。
- onDisconnect():用来处理Service断连或异常死亡的回调。
- onFailed():用来处理连接Service失败的回调。
创建连接本地Service回调实例的代码示例如下:
```
javascript
```
ts
import prompt from '@system.prompt'
var option = {
onConnect: function onConnectCallback(element, proxy) {
console.log(`onConnectLocalService onConnectDone`)
console.log(`onConnectLocalService onConnectDone`)
;
if (proxy === null) {
prompt.showToast({
message: "Connect service failed"
})
return
})
;
return
;
}
let data = rpc.MessageParcel.create()
let reply = rpc.MessageParcel.create()
let option = new rpc.MessageOption()
data.writeInterfaceToken("connect.test.token")
proxy.sendRequest(0, data, reply, option)
// 得到Service的proxy对象后便可以与其进行通信
let data = rpc.MessageParcel.create();
let reply = rpc.MessageParcel.create();
let option = new rpc.MessageOption();
data.writeString("InuptString");
proxy.sendRequest(0, data, reply, option);
prompt.showToast({
message: "Connect service success"
})
})
;
},
onDisconnect: function onDisconnectCallback(element) {
console.log(`onConnectLocalService onDisconnectDone element:${element}`)
console.log(`onConnectLocalService onDisconnectDone element:${element}`)
;
prompt.showToast({
message: "Disconnect service success"
})
})
;
},
onFailed: function onFailedCallback(code) {
console.log(`onConnectLocalService onFailed errCode:${code}`)
console.log(`onConnectLocalService onFailed errCode:${code}`)
;
prompt.showToast({
message: "Connect local service onFailed"
})
}
});
}
};
```
连接本地Service的代码示例如下:
```
javascript
import featureAbility from '@ohos.ability.featureAbility'
;
let connectId = featureAbility.connectAbility(
{
```
ts
import featureAbility from '@ohos.ability.featureAbility'
let want =
{
bundleName: "com.jstest.service",
abilityName: "com.jstest.service.ServiceAbility",
},
{
onConnect: onConnectCallback,
onDisconnect: onDisconnectCallback,
onFailed: onFailedCallback,
},
);
abilityName: "com.jstest.service.ServiceAbility"
};
let connectId = featureAbility.connectAbility(want, option);
```
同时,Service侧也需要在onConnect()时返回IRemoteObject,从而定义与Service进行通信的接口。onConnect()需要返回一个IRemoteObject对象。OpenHarmony提供了IRemoteObject的默认实现,开发者可以通过继承rpc.RemoteObject来创建自定义的实现类。
同时,Service侧也需要在onConnect()时返回IRemoteObject,从而定义与Service进行通信的接口。onConnect()需要返回一个IRemoteObject对象。OpenHarmony提供了IRemoteObject的默认实现,开发者可以通过继承rpc.RemoteObject来创建自定义的实现类
,从而实现与Service的通信。具体使用方法可参考[ohos.rpc API文档](..\reference\apis\js-apis-rpc.md)
。
Service侧把自身的实例返回给调用侧的代码示例如下:
```
javascript
import rpc from "@ohos.rpc"
;
```
ts
import rpc from "@ohos.rpc"
class
First
ServiceAbilityStub extends rpc.RemoteObject {
class ServiceAbilityStub extends rpc.RemoteObject {
constructor(des: any) {
if (typeof des === 'string') {
super(des)
super(des);
} else {
return
console.log("Error, the input param is not string");
return;
}
}
onRemoteRequest(code: number, data: any, reply: any, option: any) {
console.log(printLog + ` onRemoteRequest called`)
console.log("onRemoteRequest called");
// 可根据code执行不同的业务逻辑
if (code === 1) {
let string = data.readString()
console.log(printLog + ` string=${string}`)
let result = Array.from(string).sort().join('')
console.log(printLog + ` result=${result}`)
reply.writeString(result)
// 将传入的字符串进行排序
let string = data.readString();
console.log(`Input string = ${string}`);
let result = Array.from(string).sort().join('');
console.log(`Output result = ${result}`);
reply.writeString(result);
} else {
console.log(printLog + ` unknown request code`)
console.log(`Unknown request code`);
}
return true;
}
```
### 连接远程Service(当前仅对系统应用开放)
>说明:由于DeviceManager的getTrustedDeviceListSync接口仅对系统应用开放,当前连接远程Service仅支持系统应用。
如果Service需要与Page Ability或其他应用的Service Ability进行跨设备交互,则须创建用于连接的Connection。Service支持其他Ability通过connectAbility()方法与其进行跨设备连接。
在使用connectAbility()处理回调时,需要传入目标Service的Want与IAbilityConnection的实例。IAbilityConnection提供了以下方法供开发者实现:onConnect()是用来处理连接Service成功的回调,onDisconnect()是用来处理Service异常死亡的回调,onFailed()是用来处理连接Service失败的回调。
创建连接远程Service回调实例的代码示例如下:
```
ts
import
prompt
from
'
@system.prompt
'
var
option
=
{
onConnect
:
function
onConnectCallback
(
element
,
proxy
)
{
console
.
log
(
`onConnectRemoteService onConnectDone`
)
if
(
proxy
===
null
)
{
prompt
.
showToast
({
message
:
"
Connect service failed
"
})
return
}
let
data
=
rpc
.
MessageParcel
.
create
()
let
reply
=
rpc
.
MessageParcel
.
create
()
let
option
=
new
rpc
.
MessageOption
()
data
.
writeInterfaceToken
(
"
connect.test.token
"
)
proxy
.
sendRequest
(
0
,
data
,
reply
,
option
)
prompt
.
showToast
({
message
:
"
Connect service success
"
})
export default {
onStart() {
console.log('ServiceAbility onStart');
},
onDisconnect
:
function
onDisconnectCallback
(
element
)
{
console
.
log
(
`onConnectRemoteService onDisconnectDone element:
${
element
}
`
)
prompt
.
showToast
({
message
:
"
Disconnect service success
"
})
onCommand(want, startId) {
console.log('ServiceAbility onCommand');
},
onFailed
:
function
onFailedCallback
(
code
)
{
console
.
log
(
`onConnectRemoteService onFailed errCode:
${
code
}
`
)
prompt
.
showToast
({
message
:
"
Connect local service onFailed
"
})
onConnect(want) {
console.log('ServiceAbility OnConnect');
return new ServiceAbilityStub('ServiceAbilityRemoteObject');
},
onDisconnect(want) {
console.log('ServiceAbility OnDisConnect');
},
onStop() {
console.log('ServiceAbility onStop');
}
}
```
}
```
目标Service的Want需要包含远程deviceId,该远程deviceId可通过deviceManager获取,具体示例代码如下:
### 连接远程Service(当前仅对系统应用开放)
```
ts
import
deviceManager
from
'
@ohos.distributedHardware.deviceManager
'
;
连接远程Service,构造ConnectOptions的方法与连接本地Serivce相同,区别在于:
-
应用需要向用户申请数据同步权限
-
目标Service的Want需要包含对端设备的deviceId
//dmClass具体实现请参考:相关实例 分布式Demo 章节中的实现
let
dmClass
;
> 说明:
> (1) 由于DeviceManager的getTrustedDeviceList等接口仅对系统应用开放,当前仅系统应用支持连接远程Service。
> (2) API定义可见:[deviceManager模块](..\reference\apis\js-apis-device-manager.md)
> (3) 参考Demo可见:[分布式Demo](https://gitee.com/openharmony/applications_app_samples/tree/master/ability/DMS)
function
getRemoteDeviceId
()
{
if
(
typeof
dmClass
===
'
object
'
&&
dmClass
!=
null
)
{
let
list
=
dmClass
.
getTrustedDeviceListSync
();
if
(
typeof
(
list
)
==
'
undefined
'
||
typeof
(
list
.
length
)
==
'
undefined
'
)
{
console
.
log
(
"
MainAbility onButtonClick getRemoteDeviceId err: list is null
"
);
return
;
}
console
.
log
(
"
MainAbility onButtonClick getRemoteDeviceId success:
"
+
list
[
0
].
deviceId
);
return
list
[
0
].
deviceId
;
}
else
{
console
.
log
(
"
MainAbility onButtonClick getRemoteDeviceId err: dmClass is null
"
);
在跨设备场景下,需要向用户申请数据同步的权限,首先在config.json里配置权限:
```
json
{
...
"module"
:
{
...
"reqPermissions"
:
[{
"name"
:
"ohos.permission.DISTRIBUTED_DATASYNC"
}]
}
}
```
连接远程Service的代码示例
如下:
DISTRIBUTED_DATASYNC权限需要用户授予,在应用启动时需要向用户弹框请求授予权限,示例代码
如下:
```
ts
import
featureAbility
from
'
@ohos.ability.featureAbility
'
;
let
connectId
=
featureAbility
.
connectAbility
(
{
deviceId
:
getRemoteDeviceId
(),
bundleName
:
"
ohos.samples.etsDemo
"
,
abilityName
:
"
ohos.samples.etsDemo.ServiceAbility
"
,
},
{
onConnect
:
onConnectCallback
,
onDisconnect
:
onDisconnectCallback
,
onFailed
:
onFailedCallback
,
},
);
```
在跨设备场景下,需要向用户申请数据同步的权限。具体示例代码如下:
import
abilityAccessCtrl
from
"
@ohos.abilityAccessCtrl
"
import
bundle
from
'
@ohos.bundle
'
```
ts
import
abilityAccessCtrl
from
"
@ohos.abilityAccessCtrl
"
;
import
bundle
from
'
@ohos.bundle
'
;
async
function
RequestPermission
()
{
console
.
info
(
'
RequestPermission begin
'
);
let
array
:
Array
<
string
>
=
[
"
ohos.permission.DISTRIBUTED_DATASYNC
"
];
...
...
@@ -324,8 +302,7 @@ async function RequestPermission() {
for
(
let
i
=
0
;
i
<
array
.
length
;
i
++
)
{
let
result
=
await
atManager
.
verifyAccessToken
(
tokenID
,
array
[
i
]);
console
.
info
(
"
verifyAccessToken result:
"
+
JSON
.
stringify
(
result
));
if
(
result
==
abilityAccessCtrl
.
GrantStatus
.
PERMISSION_GRANTED
)
{
}
else
{
if
(
result
!=
abilityAccessCtrl
.
GrantStatus
.
PERMISSION_GRANTED
)
{
requestPermissions
.
push
(
array
[
i
]);
}
}
...
...
@@ -341,68 +318,25 @@ async function RequestPermission() {
}
```
同时,Service侧也需要在onConnect()时返回IRemoteObject,从而定义与Service进行通信的接口。onConnect()需要返回一个IRemoteObject对象。OpenHarmony提供了IRemoteObject的默认实现,开发者可以通过继承rpc.RemoteObject来创建自定义的实现类。
获取deviceId需要导入
`@ohos.distributedHardware.deviceManager`
模块,其中提供了getTrustedDeviceList等接口用于获取远端设备的deviceId。
-
接口使用可参考
[
deviceManager模块
](
..\reference\apis\js-apis-device-manager.md
)
-
具体实现可参考
[
分布式Demo
](
https://gitee.com/openharmony/applications_app_samples/tree/master/ability/DMS
)
Service侧把自身的实例返回给调用侧的代码示例
如下:
连接远程Service,只需要在want内定义deviceId即可,示例代码
如下:
```
ts
import
rpc
from
"
@ohos.rpc
"
;
import
featureAbility
from
'
@ohos.ability.featureAbility
'
class
FirstServiceAbilityStub
extends
rpc
.
RemoteObject
{
constructor
(
des
:
any
)
{
if
(
typeof
des
===
'
string
'
)
{
super
(
des
)
}
else
{
return
}
}
onRemoteRequest
(
code
:
number
,
data
:
any
,
reply
:
any
,
option
:
any
)
{
console
.
log
(
printLog
+
` onRemoteRequest called`
)
if
(
code
===
1
)
{
let
string
=
data
.
readString
()
console
.
log
(
printLog
+
` string=
${
string
}
`
)
let
result
=
Array
.
from
(
string
).
sort
().
join
(
''
)
console
.
log
(
printLog
+
` result=
${
result
}
`
)
reply
.
writeString
(
result
)
}
else
{
console
.
log
(
printLog
+
` unknown request code`
)
}
return
true
;
}
}
export
default
{
onStart
()
{
console
.
info
(
'
ServiceAbility onStart
'
);
},
onStop
()
{
console
.
info
(
'
ServiceAbility onStop
'
);
},
onConnect
(
want
)
{
console
.
log
(
"
ServiceAbility onConnect
"
);
try
{
let
value
=
JSON
.
stringify
(
want
);
console
.
log
(
"
ServiceAbility want:
"
+
value
);
}
catch
(
error
)
{
console
.
log
(
"
ServiceAbility error:
"
+
error
);
}
return
new
FirstServiceAbilityStub
(
"
first ts service stub
"
);
},
onDisconnect
(
want
)
{
console
.
log
(
"
ServiceAbility onDisconnect
"
);
let
value
=
JSON
.
stringify
(
want
);
console
.
log
(
"
ServiceAbility want:
"
+
value
);
},
onCommand
(
want
,
startId
)
{
console
.
info
(
'
ServiceAbility onCommand
'
);
let
value
=
JSON
.
stringify
(
want
);
console
.
log
(
"
ServiceAbility want:
"
+
value
);
console
.
log
(
"
ServiceAbility startId:
"
+
startId
);
}
let
want
=
{
deviceId
:
remoteDeviceId
,
bundleName
:
"
com.jstest.service
"
,
abilityName
:
"
com.jstest.service.ServiceAbility
"
};
let
connectId
=
featureAbility
.
connectAbility
(
want
,
option
);
```
其余实现均与本地连接Service相同,参考
[
连接本地Service
](
fa-serviceability.md#连接本地service
)
的示例代码即可。
## 相关实例
针对ServiceAbility开发,有以下相关实例可供参考:
...
...
zh-cn/application-dev/reference/apis/js-apis-extension-context.md
浏览文件 @
417ae4c3
...
...
@@ -17,7 +17,7 @@ ExtensionContext模块提供访问特定Extension的资源的能力,对于拓
| -------- | -------- | -------- | -------- | -------- |
| currentHapModuleInfo | HapModuleInfo | 是 | 否 | 所属Hap包的信息。
<br>
(详见SDK目录下的
`api\bundle\hapModuleInfo.d.ts`
) |
| config | Configuration | 是 | 否 | 所属Module的配置信息。
<br>
(详见SDK目录下的
`api\@ohos.application.Configuration.d.ts`
) |
| extensionAbilityInfo |
[
ExtensionAbilityInfo
](
js-apis-bundle
-E
xtensionAbilityInfo.md
)
| 是 | 否 | 所属Extension的信息。
<br>
(详见SDK目录下的
`api\bundle\extensionAbilityInfo.d.ts`
) |
| extensionAbilityInfo |
[
ExtensionAbilityInfo
](
js-apis-bundle
Manager-e
xtensionAbilityInfo.md
)
| 是 | 否 | 所属Extension的信息。
<br>
(详见SDK目录下的
`api\bundle\extensionAbilityInfo.d.ts`
) |
## 使用场景
ExtensionContext主要用于查询所属Extension的信息、Module的配置信息以及Hap包的信息,开发者可根据自身业务需求使用对应的信息。此处以ServiceExtension为例,展示ExtensionContext的一种使用场景。
...
...
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录