Harmonyos之多目标构建产物实践
- 概述
- 基本概念
- 实现原理
- 多目标产物定制项
- 定制HAP多目标产物
- 定义产物的HAP包名
- 定义产物的deviceType
- 定义产物的资源
- 定义产物的icon、label、launchType
- 配置APP多目标构建产物
- 定义产物的APP包名和供应商名称
- 定义product的bundleType
- 定义Product的签名配置信息
- 定义product的icon和label
- 定义product中包含的target
- 构建定义的目标产物
- 参考资料
概述
多目标产物在HarmonyOS系统中的应用主要体现在软件开发与分发方面,特别是针对不同用户群体、不同业务场景的需求进行定制化开发。多目标产物为开发者提供了更加灵活和高效的开发方式,使得应用能够更好地适应市场需求和变化。
基本概念
target
:对应HAR、HSP、HAP的多目标产物。工程内的每一个模块可以定义多个target,每个Target对应一个定制的HAP、HAR包,通过配置可以实现一个模块构建出不同的HAP、HAR包。product
:对应App的多目标产物。一个HarmonyOS工程的构建产物为App包,一个工程可以定义多个product,每个product对应一个定制化应用包,通过配置可以实现一个工程构建出多个不同的应用包。
在构建过程中,鸿蒙构建系统会根据配置文件中定义的product和target信息,生成相应的构建产物。对于每个target,构建系统会生成一个对应的HAP/HSP/HAR。这个HAP/HSP/HAR包含了该target所需的所有代码和资源。对于每个product,构建系统会生成一个包含了其所有依赖的target的App包。这个App包可以用于发布和上架到应用市场。
实现原理
HarmonyOS多目标产物支持HAP(应用安装的基本单位,每个HAP都对应一个应用模块)、HAR(静态共享包)、HSP(动态共享包)以及App(由多个HAP打包一起上架的完整应用程序)包多种类型的包,以满足不同业务场景下的应用开发和定制需求。
多目标产物定制项
每一个Entry/Feature
模块均支持定制不同的target
,通过在模块中的build-profile.json5
文件中实现差异化定制,当前支持HAP包名
、设备类型(deviceType)
、源码集(source)
、资源(resource)
、buildOption配置项(如C++依赖的.so、混淆配置、abi类型、cppFlags等)
、分发规则(distributionFilter)的定制
。
定制HAP多目标产物
每一个target对应一个定制的HAP,因此,在定制HAP多目标构建产物前,应提前规划好需要定制的target名称。
示例: 我们已entry模块为示例,在entry模块的build-profile.json5
文件中配置了如下4个target:
{"apiType": "stageMode","buildOption": {},"targets": [ // 定义不同的target{"name": "default" // 默认target},{"name": "free" // 免费 target},{"name": "pay" // 付费target}]
}
按照上述target的定义,在编译构建时,会同时打包生成default、free和pay三个不同的HAP。
定义产物的HAP包名
每一个target可以指定一个产物命名
"targets": [{"name": "default","output": {"artifactName": "customizedTargetOutputName-default-1.0.0"}},{"name": "free","output": {"artifactName": "customizedTargetOutputName-free-1.0.0"}},{"name": "pay","output": {"artifactName": "customizedTargetOutputName-pay-1.0.0"}}]
如果已配置签名,target产物对应的HAP包名为开发者定制的名称;如果未配置签名,target产物对应的HAP包名为开发者定制的名称+unsigned。
定义产物的deviceType
每一个target
均可以指定支持的设备类型deviceType
,也可以不定义。如果不定义,则该target
默认支持config.json
或module.json5
中定义的设备类型。
同时,在定义每个target的deviceType时,支持的设备类型必须在config.json或module.json5中已经定义。例如,在上述定义的3个target中,分别定义default默认支持所有设备类型,free和pay版本只支持phone设备。
定义产物的资源
每个target使用的资源文件可能存在差异,在开发过程中,开发者可以将每个target所使用的资源存放在不同的资源目录下。**其中,ArkTS工程支持对main目录下的资源文件目录(resource)进行定制;JS工程支持对main目录下的资源文件目录(resource)及 Ability下的资源文件目录(res)进行定制。**如下为ArkTS工程的资源文件目录定制示例:
"targets": [{"name": "default","output": {"artifactName": "customizedTargetOutputName-default-1.0.0"},// 不指定设备类型 , 默认支持config,json或者module.json5配置文件中指定的类型"source": { // 指定default模块的源码集"pages": ["pages/Index"]},"resource": {"directories": ["./src/main/resources"]}},{"name": "free","output": {"artifactName": "customizedTargetOutputName-free-1.0.0"},"config": { // 配置free模块 支持设备类型为phone"deviceType": ["phone"]},"source": { // 指定free 的源码集"pages": ["pages/Index","pages/FreePage"]},"resource": { // 定义free版的资源目录"directories": ["./src/main/resources","./src/main/free/resources"]}},{"name": "pay","output": {"artifactName": "customizedTargetOutputName-pay-1.0.0"},"config": { // 配置pay模块 支持设备类型为phone"deviceType": ["phone"]},"source": { // 指定pay源码集"pages": ["pages/Index","pages/PayPage"]},"resource": { // 定义pay版的资源目录"directories": ["./src/main/resources","./src/main/pay/resources"]}}]
**注意:**如果target引用的多个资源文件目录下,存在同名的资源,则在构建打包过程中,将按照配置的资源文件目录顺序进行选择。例如,上述pay的target引用的资源中,resource_default和resource_pay中存在同名的资源文件,则resource_default中的资源会被打包到HAP中。
定义产物的icon、label、launchType
针对每一个的target的ability,均可以定制不同的icon、label和launchType。如果不定义,则该target采用module.json5中module.abilities配置的icon、label,launchType默认为"singleton"。示例如下所示:
"targets": [{"name": "free","output": {"artifactName": "customizedTargetOutputName-free-1.0.0"},"config": {// 配置free模块 支持设备类型为phone"deviceType": ["phone"]},"source": {// 配至target的 icon、名称"abilities": [{"name": "EntryAbility","icon": "$media:app_icon","label": "$string:EntryAbility_label"}]},{"name": "pay","output": {"artifactName": "customizedTargetOutputName-pay-1.0.0"},"config": {// 配置pay模块 支持设备类型为phone"deviceType": ["phone"]},"source": {// 配至target的 icon、名称"abilities": [{"name": "EntryAbility","icon": "$media:app_icon","label": "$string:EntryAbility_label"}]}]
注意: HAR包中的target配置和HAP包中的配置类似, 可以直接参考HAP包中的target配置
配置APP多目标构建产物
APP用于应用/元服务上架发布,针对不同的应用场景,可以定制不同的product,每个product中支持对bundleName、bundleType、签名信息、icon和label以及包含的target进行定制。
首先我们需要定义目标产物的product:
每一个product对应一个定制的APP包,因此,在定制APP多目标构建产物前,应提前规划好需要定制的product名称。例如,定义productA和productB。工程级build-profile.json5文件示例如下:
**注意: 在定制product时,必须存在"default"的product,否则编译时会出现错误。 **
"products": [{"name": "default","signingConfig": "default","compatibleSdkVersion": "5.0.0(12)","runtimeOS": "HarmonyOS","buildOption": {"strictMode": {"caseSensitiveCheck": true,"useNormalizedOHMUrl": true}}},{"name": "free","arkTSVersion": "1.0","compatibleSdkVersion": "5.0.0(12)","runtimeOS": "HarmonyOS"},{"name": "pay","arkTSVersion": "1.0","compatibleSdkVersion": "5.0.0(12)","runtimeOS": "HarmonyOS"}],
定义产物的APP包名和供应商名称
每一个product均可以指定产物命名和供应商名称。
"products": [{"name": "default","signingConfig": "default","compatibleSdkVersion": "5.0.0(12)","runtimeOS": "HarmonyOS","output": {"artifactName": "customizedProductOutputName-default-1.0.0"},"vendor": "customizedProductVendorNameDefault","buildOption": {"strictMode": {"caseSensitiveCheck": true,"useNormalizedOHMUrl": true}}},{"name": "free","arkTSVersion": "1.0","compatibleSdkVersion": "5.0.0(12)","runtimeOS": "HarmonyOS","output": {"artifactName": "customizedProductOutputName-free-1.0.0"},"vendor": "customizedProductVendorNameFree"},{"name": "pay","arkTSVersion": "1.0","compatibleSdkVersion": "5.0.0(12)","runtimeOS": "HarmonyOS",// 产物名称"output": {"artifactName": "customizedProductOutputName-pay-1.0.0"},// 厂商名称"vendor": "customizedProductVendorNamePay"}],
如果已配置签名,product产物对应的APP包名为开发者定制的名称;如果未配置签名,product产物对应的APP包名为开发者定制的名称+unsigned。
"products": [{"name": "default","bundleName": 'com.example00.com' // 定义bundleName},{"name": "free","bundleName": 'com.example01.com' // 定义bundleName},{"name": "pay","bundleName": 'com.example02.com' // 定义bundleName}],
定义product的bundleType
针对每个定义的product,均可以定制不同的bundleType。开发者可以通过定义每个product的bundleType,分别定义产物类型:
bundleType
值为app
,表示产物为应用;bundleType
值为atomicService
,表示产物为元服务。
如果product未定义bundleType
,则采用工程的bundleType(即创建工程时选择的Application/Atomic Service)。示例如下所示:
"bundleType": "app" //定义default的bundleType信息 或者
"bundleType": "atomicService" //定义free的bundleType信息
定义Product的签名配置信息
针对每个定义的product,均可以定制不同的signingConfig签名文件,如果product未定义signingConfig,则构建生成未签名的APP包。
"signingConfigs": [{"name": "default","type": "HarmonyOS","material": {"certpath": "C:\\Users\\issuse\\.ohos\\config\\default_Ohos_mul_target_product_demo_eVRTvrSbxrlOl4o4IImUYNHhIuAnbI_qnI0PSjX-AFg=.cer","storePassword": "0000001BB81859FEC4357F35F89B9A23A36703FB89251062664DE4DF08394C29C889DA2E9ACB83AA7C95F7","keyAlias": "debugKey","keyPassword": "0000001B4EFFA6E841485EFCE68965018214B13B65ECAFF6FBC2C0BA4C77BAC468C7073A95DBC467D01A5C","profile": "C:\\Users\\issuse\\.ohos\\config\\default_Ohos_mul_target_product_demo_eVRTvrSbxrlOl4o4IImUYNHhIuAnbI_qnI0PSjX-AFg=.p7b","signAlg": "SHA256withECDSA","storeFile": "C:\\Users\\issuse\\.ohos\\config\\default_Ohos_mul_target_product_demo_eVRTvrSbxrlOl4o4IImUYNHhIuAnbI_qnI0PSjX-AFg=.p12"}},{"name": "free","type": 'HarmonyOS',"material": {"certpath": "C:\\Users\\issuse\\.ohos\\config\\default_Ohos_mul_target_product_demo_eVRTvrSbxrlOl4o4IImUYNHhIuAnbI_qnI0PSjX-AFg=.cer","storePassword": "0000001BB81859FEC4357F35F89B9A23A36703FB89251062664DE4DF08394C29C889DA2E9ACB83AA7C95F7","keyAlias": "debugKey","keyPassword": "0000001B4EFFA6E841485EFCE68965018214B13B65ECAFF6FBC2C0BA4C77BAC468C7073A95DBC467D01A5C","profile": "C:\\Users\\issuse\\.ohos\\config\\default_Ohos_mul_target_product_demo_eVRTvrSbxrlOl4o4IImUYNHhIuAnbI_qnI0PSjX-AFg=.p7b","signAlg": "SHA256withECDSA","storeFile": "C:\\Users\\issuse\\.ohos\\config\\default_Ohos_mul_target_product_demo_eVRTvrSbxrlOl4o4IImUYNHhIuAnbI_qnI0PSjX-AFg=.p12"}},{"name": "pay","type": 'HarmonyOS',"material": {"certpath": "C:\\Users\\issuse\\.ohos\\config\\default_Ohos_mul_target_product_demo_eVRTvrSbxrlOl4o4IImUYNHhIuAnbI_qnI0PSjX-AFg=.cer","storePassword": "0000001BB81859FEC4357F35F89B9A23A36703FB89251062664DE4DF08394C29C889DA2E9ACB83AA7C95F7","keyAlias": "debugKey","keyPassword": "0000001B4EFFA6E841485EFCE68965018214B13B65ECAFF6FBC2C0BA4C77BAC468C7073A95DBC467D01A5C","profile": "C:\\Users\\issuse\\.ohos\\config\\default_Ohos_mul_target_product_demo_eVRTvrSbxrlOl4o4IImUYNHhIuAnbI_qnI0PSjX-AFg=.p7b","signAlg": "SHA256withECDSA","storeFile": "C:\\Users\\issuse\\.ohos\\config\\default_Ohos_mul_target_product_demo_eVRTvrSbxrlOl4o4IImUYNHhIuAnbI_qnI0PSjX-AFg=.p12"}}]
定义product的icon和label
针对每个定义的product,均可以定制不同的icon和label,如果product未定义icon和label,则采用工程默认的icon和label。示例如下所示:
products中的icon和label字段在编译时会替换app.json5中对应的字段,app.json5和module.json5均可以配置这两个字段,如果都配置,优先级顺序请参考应用/组件级配置。
"product": [{"icon":"$media:default_icon", //定义default的icon"label":"$string:default_name", //定义default的label},{"icon":"$media:productA_icon", //定义productA的icon"label":"$string:productA_name", //定义productA的label},{"icon":"$media:productB_icon", //定义productB的icon"label":"$string:productB_name", //定义productB的label}
]
定义product中包含的target
开发者可以选择需要将定义的target分别打包到哪一个product中,每个product可以指定一个或多个target。
同时每个target也可以打包到不同的product中,但是同一个module的不同target不能打包到同一个product中(除非该module的不同target配置了不同的deviceType或distributionFilter/distroFilter)。
"modules": [{"name": "entry","srcPath": "./entry","targets": [{"name": "default", // 将default target打包到default App中"applyToProducts": ["default"]},{"name": 'free', // 将free target打包到free APP中"applyToProducts": [// target关联的模块"free"]},{"name": "pay", // //将pay target打包到pay APP中"applyToProducts": ["pay"]}]}]
构建定义的目标产物
每个target对应一个HAP,每个product对应一个APP包,在编译构建时,如果存在多product或多target时,您可以指定编译具体的包。
- Product:选择需要构建的 APP 包。
- Build Mode:选择编译模式。
- Product Info:该APP包的BundleName和SigningConfig信息。
- Target Select:选择各个模块的Target,该Target需要包含在定义的Product中才能选择,如果未包含则显示"No Target to apply"
运行结果:
参考资料
HarmonyOS多环境+多渠道+自定义路径输出+自定义名称一键打app和hap包
官方文档(更多,更详细的配置参考官方文档):
多目标产物开发实践
配置多目标产物