HarmonyOS编译构建工具: Havigor(上)

Havigor 是鸿蒙平台一款使用 TypeScript 实现的构建任务编排工具,类似于 Android 平台的 Gradle。它主要提供任务管理机制,包括任务注册编排、工程模型管理、配置管理等关键能力。针对 HarmonyOS 应用提供了一系列编译构建任务,支持将 HarmonyOS 应用编译构建出对应的产物包。

作为一款 HarmonyOS 应用编译构建任务流工具,DevEco Hvigor 具备诸多提升构建效率的特性,比如并行编译、增量编译等等;支持多产物差异化构建。也支持HarmonyOS应用可分可合等特性。

文件结构介绍

当我们在 DevEco 中新建一个 Harmony OS 应用的项目后,可以在项目目录中看到如下关于 hvigor 的文件:

├─entry   // entry 模块,对于后续新增的 module 同样会有一个 hvigotfile.ts 文件
│  ├─src   
│  └─hvigorfile.ts    // 模块级编译构建脚本
├─hvigor  // hvigor 插件信息
│  ├─hvigor-config.json5   // hvigor 插件配置文件
│  └─hvigor-wrapper.js    // hvigor 插件具体业务逻辑实现的 js 代码,执行此代码以执行 hvigor 相关操作
├─build-profile.json5   // 工程级配置文件,声明工程对应的构建参数
├─hvigorfile.ts   // 工程级编译构建脚本
├─hvigorw   // 非 Windows 系统下的执行脚本
└─hvigorw.bat   // Windows 系统下的执行脚本

Hvigor-config.json5 文件主要用来配置 hvigor 和 hvigor-ohos-plugin 的版本,同时也支持一些编译过程中的配置,比如是够启用守护进程编译、是否启用增量编译、是否启用并行编译、是否启用类型检、定义日志级别、是否警用堆栈跟踪编译等等。

{
  "hvigorVersion": "4.0.4",
  "dependencies": {
    "@ohos/hvigor-ohos-plugin": "4.0.4"
  },
  "execution": {
    "daemon": true,                          /* 启用守护进程编译。默认值:true */
    "incremental": true,                     /* 启用增量编译。默认值:true */
    "parallel": true,                        /* 启用并行编译。默认值:true */
    "typeCheck": false                       /* 启用类型检查。默认值:false */
  },
  "logging": {
    "level": "info"                          /* 定义日志级别。取值:[ "debug" | "info" | "warn" | "error" ]。默认值:"info" */
  },
  "debugging": {
    "stacktrace": false                      /* 禁用堆栈跟踪编译。默认值:false */
  }
  "nodeOptions": {
    "maxOldSpaceSize": 4096                  /* 启用守护进程编译时,守护进程内存大小,单位为MB。默认值:4096 */
  }
}

增量构建

增量构建是 hvigor 执行任务的一种优化,如果在两次执行任务过程中,执行任务的输入和输出没有更改,hvigor 会复用上次构建产物,从而跳过该任务的执行节省构建时间。如果需要使用增量编译特性,我们需要在 DevEco 中(Setting->Build,Execution,Deployment->Build Tools->Hvigor)勾选 「Re-execute the task in incremental mode」。

HarmonyOS编译构建工具: Havigor(上)

除了前面我们说的,可以在 hvigor-config.json5 中 execution.incremental 字段来控制是否启用增量构建。我们还可以通过如下命令选择是否开启增量构建(hvigor 默认开启增量构建)。

# 启用增量构建
./hvigorw <task> --incremental
# 关闭增量构建
./hvigorw <task> --no-incremental

开启增量构建后,我们会在增量执行场景下看到显著的性能改进。

并行构建

大部分工程都包含了多个子工程,其中一些子工程是相互独立的,也就是说,它们之间没有状态共享。在大多数情况下,通过并行构建可以有效地减少多个子工程的整体构建时间。对于 C++ 编译、ArkTS 任务等耗时且没有依赖关系的任务,DevEco Hvigor 可以使用不同的工作线程并行执行,提高编译构建的效率。熟悉 Android Gradle 的同学应该知道,这种特性在多模块的中大型项目中,会带来非常可观的耗时节省。然而,在特定的情况下,如子工程之间存在大量的依赖关系,可能无法显著缩短构建时间。节省的具体时间取决于我们的工程结构和子工程之间的依赖关系

如果需要使用并行编译特性,我们需要在 DevEco 中开启支持(Setting->Build,Execution,Deployment->Build Tools->Hvigor)

HarmonyOS编译构建工具: Havigor(上)

除了前面我们说的,可以在 hvigor-config.json5 中 execution.parallel 字段来控制是否启用并行构建。我们还可以通过如下命令选择是否开启并行构建(hvigor 默认开启并行构建)。

# 启用并行执行
./hvigorw <task> --parallel
# 关闭并行执行
./hvigorw <task> --no-parallel

守护进程

hvigor 守护进程是一个持续存在的后台进程,可以减少运行构建所需的时间。当我们重复构建同一项目时,守护进程可以将构建时间缩短。多次构建时,守护进程只会将 hvigor一次性加载到内存中,而不是每一次构建。使用守护行程编译,我们需要在DevEco 中(Setting->Build,Execution,Deployment->Build Tools->Hvigor)勾选 「Enable the Daemon for tasks」。

HarmonyOS编译构建工具: Havigor(上)

除了前面我们说的,可以在 hvigor-config.json5 中 execution.daemon 字段来控制是否启用守护进程。我们还可以通过如下命令选择是否开启守护进程(hvigor 默认开启守护进程)。

# 启用守护进程
./hvigorw <task> --daemon
# 关闭守护进程
./hvigorw <task> --no-daemon

默认情况下,hvigor 为我们的项目构建保留了4096 MB的内存空间,这对于大多数项目来说已经足够了,但是如果我们的项目非常庞大,项目的构建可能需要更多的内存来保存 hvigor 的模型和缓存。遇到这种情况,我们可以设置 hvigor-config.json5 文件中的nodeOptions.maxOldSpaceSize 字段来调整为更大的内存。

更多的设置选项可以参考hvigor-config.json5字段说明

HarmonyOS编译构建工具: Havigor(上)

查看 hvigor 可用任务

任务是一个基本的工作单元,是hvigor构建的一部分。在工程目录下,输入以下命令可以列出项目中所有可用的任务:

./hvigorw tasks

Tasks 命令会列出当前项目中工程和模块中的所有可用的任务:

> hvigor hvigor client: The argument passed to Node.js or hvigor version have changed and a new daemon will be created to replace the existing daemon. Reason:{isHvigorVersionChanged: false, isNodeEnvChanged: true}
> hvigor hvigor client: Starting hvigor daemon.
> hvigor Hvigor Daemon started in 258 ms
--------------------------------------------------------------------------
All tasks from hvigor node 'entry'
--------------------------------------------------------------------------
Help tasks
-------------
tasks - Displays the tasks of the HvigorCoreNode.
taskTree - Displays the task dag tree of the HvigorCoreNode.
​
Sync tasks
-------------
init
​
> hvigor Finished :entry:tasks... after 1 ms 
--------------------------------------------------------------------------
All tasks from hvigor node 'router_library'
--------------------------------------------------------------------------
Help tasks
-------------
tasks - Displays the tasks of the HvigorCoreNode.
taskTree - Displays the task dag tree of the HvigorCoreNode.
​
Sync tasks
-------------
init
​
> hvigor Finished :router_library:tasks... after 1 ms 
--------------------------------------------------------------------------
All tasks from hvigor node 'WBRouter'
--------------------------------------------------------------------------
Help tasks
-------------
tasks - Displays the tasks of the HvigorCoreNode.
taskTree - Displays the task dag tree of the HvigorCoreNode.
​
Other tasks
-------------
prune - Clean up old hvigor cache files and remove unreferenced packages from store.
clean - Clear the cache information.
collectCoverage - Generate coverage statistics reports based on instrumentation dotting data.
​
Hook tasks
-------------
assembleApp - Assemble the task for the packaged app.
​
Sync tasks
-------------
init
​
Sign tasks
-------------
SignApp - Sign the app package.
​
Package tasks
-------------
PackageApp - Build the app package in the stage model.
​
Generate tasks
-------------
GeneratePackRes - Build the pack.res file in the stage model.
MakeProjectPackInfo - Generate project pack.info in the stage model.
​
Verification tasks
-------------
PreBuildApp - Prepare before building the app.
​
> hvigor Finished ::tasks... after 1 ms 
> hvigor BUILD SUCCESSFUL in 834 ms 

根据输出结果可以看到,当前的 hvigor 任务有:

模块级的任务(entry 和 router_library两个module)

  • Help tasks (tasks、taskTree)
  • Sync tasks(init)

工程级的任务 (WBRouter)

  • Help tasks(tasks、taskTree)
  • Other tasks (prune、clean、collectCoverage)
  • Hook tasks (assembleApp)
  • Sync tasks (init)
  • Sign tasks (SignApp)
  • Package tasks (PackageApp)
  • Generate tasks (GeneratePackRes、MakeProjectPackInfo)
  • Verification tasks (PreBuildApp)

自定义你的任务

在hvigorfile.ts文件中只需定义一个pluginId(任务Id)和name(任务名称),并实现其中的run方法,即可创建一个任务。例如,我们创建一个打印”Hello HarmonyOS”任务:

function helloHarmonyOS() {
  return {
    pluginId: 'HelloHarmonyOS',
    apply(pluginContext) {
      pluginContext.registerTask({
        // 编写自定义任务
        name: 'HelloHarmonyOS',
        run: (taskContext) => {
          console.log('Hello HarmonyOS!');
        }
      })
    }
  }
}
​
export default {
  system: [],
  plugins: [ helloHarmonyOS() ]
}

运行任务:

./hvigorw HelloHarmonyOS

HarmonyOS编译构建工具: Havigor(上)

关于 DevEco Hvigor 本篇我们就先介绍到这,下一篇我们将继续介绍 hvigor 的编译过程,以及如何开发 hvigor 任务插件。

原文链接:https://juejin.cn/post/7350320544527450151 作者:BaronTalk

(0)
上一篇 2024年3月27日 下午5:09
下一篇 2024年3月27日 下午5:20

相关推荐

发表评论

登录后才能评论