Kea2

文档

中文文档

Kea2 教程

  1. 微信 上应用 Kea2 功能 2 和 3 的小教程。

Kea2 脚本

Kea2 使用 Unittest 来管理脚本。所有 Kea2 脚本都可以在 unittest 规则中找到(即测试方法应以 test_ 开头,测试类应继承自 unittest.TestCase)。

Kea2 使用 Uiautomator2 操控 Android 设备。详情请参考 Uiautomator2 文档

一般地,你可以通过以下两步编写 Kea2 脚本:

  1. 创建继承 unittest.TestCase 的测试类。
import unittest

class MyFirstTest(unittest.TestCase):
    ...
  1. 通过定义测试方法编写脚本

默认情况下,只有以 test_ 开头的测试方法会被 unittest 识别。你可以用 @precondition 装饰函数。装饰器 @precondition 接收一个返回布尔值的函数作为参数。当函数返回 True 时,前置条件满足,脚本将被激活,接下来Kea2 会根据装饰器 @prob 定义的概率运行脚本。

注意,如果测试方法未被 @precondition 装饰,该测试方法在自动化 UI 测试中永远不会被激活,而是被当作普通的 unittest 测试方法处理。因此,当测试方法应始终执行时,需要显式指定 @precondition(lambda self: True)。如果未装饰 @prob,默认概率为 1(即前置条件满足时始终执行)。

import unittest
from kea2 import precondition

class MyFirstTest(unittest.TestCase):

    @prob(0.7)
    @precondition(lambda self: ...)
    def test_func1(self):
        ...

更多细节请阅读 Kea - Write your first property

装饰器

@precondition

@precondition(lambda self: ...)
def test_func1(self):
    ...

@precondition 是一个装饰器,接受一个返回布尔值的函数作为参数。当该函数返回 True 时,前置条件满足,函数 test_func1 会被激活,并且 Kea2 会基于 @prob 装饰器定义的概率值执行 test_func1。 如果未指定 @prob,默认概率值为 1,此时当前置条件满足时,test_func1 会始终执行。

@prob

@prob(0.7)
@precondition(lambda self: ...)
def test_func1(self):
    ...

@prob 装饰器接受一个浮点数参数,该数字表示当前置条件满足时执行函数 test_func1 的概率。概率值应介于 0 到 1 之间。 如果未指定 @prob,默认概率值为 1,即当前置条件满足时函数总是执行。

当多个函数的前置条件都满足时,Kea2 会根据它们的概率值随机选择其中一个函数执行。 具体地,Kea2 会生成一个 0 到 1 之间的随机值 p,并用 p 和这些函数的概率值共同决定哪个函数被选中。

例如,若三个函数 test_func1test_func2test_func3 的前置条件满足,它们的概率值分别为 0.20.40.6

@max_tries

@max_tries(1)
@precondition(lambda self: ...)
def test_func1(self):
    ...

@max_tries 装饰器接受一个整数参数,表示当前置条件满足时函数 test_func1 最多执行的次数。默认值为 inf(无限次)。

启动 Kea2

我们提供两种方式启动 Kea2。

1. 通过 shell 命令启动

Kea2 兼容 unittest 框架,可以用 unittest 风格管理测试用例。你可以使用 kea run 加上驱动参数和子命令 unittest(用以传递 unittest 选项)启动 Kea2。

shell 命令示例:

kea2 run <Kea2 cmds> unittest <unittest cmds> 

示例 shell 命令:

# 启动 Kea2 并加载单个脚本 quicktest.py
kea2 run -s "emulator-5554" -p it.feio.android.omninotes.alpha --agent u2 --running-minutes 10 --throttle 200 --driver-name d unittest discover -p quicktest.py

# 启动 Kea2 并从目录 mytests/omni_notes 加载多个脚本
kea2 run -s "emulator-5554" -p it.feio.android.omninotes.alpha --agent u2 --running-minutes 10 --throttle 200 --driver-name d unittest discover -s mytests/omni_notes -p test*.py

如果需要向底层 Fastbot 传递额外参数,可以在常规参数后添加 --,然后列出额外参数。例如,设置触摸事件比例为 30%:

kea2 run -s "emulator-5554" -p it.feio.android.omninotes.alpha --agent u2 --running-minutes 10 --throttle 200 --driver-name d -- --pct-touch 30 unittest discover -p quicktest.py

kea2 run 参数说明

参数 意义 默认值
-s 设备序列号,可通过 adb devices 查看  
-t 设备传输 ID,可通过 adb devices -l 查看  
-p 指定被测试应用的包名(例如 com.example.app)。支持多个包:-p pkg1 pkg2 pkg3  
-o 日志和结果输出目录 output
–agent {native, u2}。默认使用 u2,支持 Kea2 三个重要功能。如果想运行原生 Fastbot,请使用 native u2
–running-minutes 运行 Kea2 的时间(分钟) 10
–max-step 发送的最大随机事件数(仅在 --agent u2 有效) inf(无限)
–throttle 两次随机事件之间的延迟时间(毫秒) 200
–driver-name Kea2 脚本中使用的驱动名称。如果指定 --driver-name d,则需用 d 操作设备,例如 self.d(..).click()  
–log-stamp 日志文件和结果文件的标识(例如指定 --log-stamp 123,日志文件命名为 fastbot_123.log,结果文件命名为 result_123.json 当前时间戳
–profile-period 覆盖率分析和截图采集周期(单位为随机事件数)。截图保存在设备 SD 卡,根据设备存储调整此值。 25
–take-screenshots 在每个随机事件执行时截图,截图会被周期性地自动从设备拉取到主机(周期由 --profile-period 指定)。  
–device-output-root 设备输出目录根路径,Kea2 将暂存截图和结果日志到 "<device-output-root>/output_*********/"。确保该目录可访问。 /sdcard
unittest 指定加载的脚本。该子命令 unittest 完全兼容 unittest。更多选项请参阅 python3 -m unittest -h。此选项仅在 --agent u2 下有效。  

kea2 report 参数说明

kea2 report 命令根据已有测试结果生成 HTML 测试报告。该命令分析测试数据,创建包含测试执行统计、覆盖率信息、性质违规和崩溃详情的综合可视化报告。

参数 意义 是否必需 默认值
-p, –path 测试结果目录路径(res_* 目录)  

使用示例:

# 从测试结果目录生成报告
kea2 report -p res_20240101_120000

# 启用调试模式生成报告
kea2 -d report -p res_20240101_120000

# 使用相对路径生成报告
kea2 report -p ./output/res_20240101_120000

报告内容包括:

输出内容: 报告命令生成:

输入目录结构示例:

res_<timestamp>/
├── result_<timestamp>.json          # 性质测试结果
├── output_<timestamp>/
│   ├── steps.log                    # 测试执行步骤
│   ├── coverage.log                 # 覆盖率数据
│   ├── crash-dump.log               # 崩溃和 ANR 事件
│   └── screenshots/                 # UI 截图(如启用)
└── property_exec_info_<timestamp>.json  # 性质执行详情

kea2 merge 参数说明

kea2 merge 命令允许合并多个测试报告目录,生成合并后的综合报告。适用于多次测试会话结果的汇总。

参数 意义 是否必需 默认值
-p, –paths 需要合并的测试报告目录路径(res_* 目录),至少两个路径  
-o, –output 合并报告的输出目录 merged_report_<timestamp>

使用示例:

# 合并两个测试报告目录
kea2 merge -p res_20240101_120000 res_20240102_130000

# 合并多个测试报告目录并指定输出目录
kea2 merge -p res_20240101_120000 res_20240102_130000 res_20240103_140000 -o my_merged_report

# 启用调试模式合并
kea2 -d merge -p res_20240101_120000 res_20240102_130000

合并内容包括:

输出内容: 合并命令生成:

kea 参数

参数 意义 默认值
-d 启用调试模式  
# 加上 -d 启用调试模式
kea2 -d run -s "emulator-5554" -p it.feio.android.omninotes.alpha --agent u2 --running-minutes 10 --throttle 200 --driver-name d unittest discover -p quicktest.py

2. 通过 unittest.main 启动

像 unittest 一样,可以通过 unittest.main 方法启动 Kea2。

示例(保存为 mytest.py),你可以看到选项直接定义在脚本中。

import unittest

from kea2 import KeaTestRunner, Options
from kea2.u2Driver import U2Driver

class MyTest(unittest.TestCase):
    ...
    # <你的测试方法>

if __name__ == "__main__":
    KeaTestRunner.setOptions(
        Options(
            driverName="d",
            Driver=U2Driver,
            packageNames=[PACKAGE_NAME],
            # serial="emulator-5554",   # 指定设备序列号
            maxStep=100,
            # running_mins=10,  # 指定最大运行时间(分钟),默认10分钟
            # throttle=200,   # 指定延迟时间(毫秒),默认200毫秒
            # agent='native'  # 'native' 运行原生 Fastbot
        )
    )
    # 声明 KeaTestRunner
    unittest.main(testRunner=KeaTestRunner)

运行该脚本启动 Kea2,如:

python3 mytest.py

以下是 Options 中的所有可用选项。

# 脚本中的驱动名称(如 self.d,则为 d)
driverName: str
# 驱动(当前只有 U2Driver)
Driver: U2Driver
# 包名列表,指定被测试的应用
packageNames: List[str]
# 目标设备序列号
serial: str = None
# 测试代理,默认 "u2"
agent: "u2" | "native" = "u2"
# 探索时最大步数(阶段 2~3 可用)
maxStep: int # 默认 "inf"
# 探索时长(分钟)
running_mins: int = 10
# 探索时等待时间(毫秒)
throttle: int = 200
# 日志和结果保存目录
output_dir: str = "output"
# 日志文件和结果文件的时间戳标识,默认当前时间戳
log_stamp: str = None
# 覆盖率采样周期
profile_period: int = 25
# 是否每步截图
take_screenshots: bool = False
# 设备上的输出目录根路径
device_output_root: str = "/sdcard"
# 是否启用调试模式
debug: bool = False

查看脚本运行统计

如果想查看你的脚本是否被执行及执行次数,测试结束后打开 result.json 文件。

示例:

{
    "test_goToPrivacy": {
        "precond_satisfied": 8,
        "executed": 2,
        "fail": 0,
        "error": 1
    },
    ...
}

如何解读 result.json

字段 说明 含义
precond_satisfied 在探索过程中,测试方法的前置条件满足次数 是否到达了该状态
executed UI 测试过程中,测试方法被执行的次数 该测试方法是否执行过
fail UI 测试中,测试方法断言失败次数 失败时,测试方法发现了可能的功能缺陷
error UI 测试中,测试方法因发生意外错误(如找不到某些 UI 组件)中断的次数 出现错误时,意味着脚本需要更新或修复,因为脚本导致了意外错误

配置文件

执行 Kea2 init 后,会在 configs 目录生成一些配置文件。 这些配置文件属于 Fastbot,具体介绍请参见 配置文件介绍

更新用户配置文件

在更新 Kea2 时,用户的本地配置有时需要更新。(最新的 kea2 版本可能与旧的配置文件不兼容。)

当检测到运行时错误时,Kea2 会检查本地配置文件是否与当前 Kea2 版本兼容。如果不兼容,控制台会打印警告信息。请按照以下说明更新本地配置文件。

  1. 备份你的本地配置文件(以防在更新过程中出现意外问题)。
  2. 删除项目根目录中 “/configs” 下的所有配置文件。
  3. 运行 kea2 init 以生成最新的配置文件。
  4. 根据你的需要,将旧配置合并到新的配置文件中。

应用崩溃缺陷

Kea2 会将触发的崩溃缺陷转储在由 -o 指定输出目录中的 fastbot_*.log 文件内。你可以在 fastbot_*.log 中搜索关键词 FATAL EXCEPTION 来获取崩溃缺陷的具体信息。

这些崩溃缺陷也会记录在你的设备上。详情请参考 Fastbot 手册