(无需 Root) 基于 Android Monkey 二次开发,实现高速点击的 Android Monkey 自动化工具 fastmonkey – 代号 Maxim

random
random
random
订阅者
10318
文章
0
粉丝
测试交流200542字数 1266阅读4分13秒阅读模式

打造一款快速高效且高度可复用的 android 自动化测试工具

主页入口 请点我https://github.com/zhangzhao4444/Maxim

(无需 Root) 基于 Android Monkey 二次开发,实现高速点击的 Android Monkey 自动化工具 fastmonkey – 代号 Maxim-图片1

优势

  1. 高速点击,每秒 10-15 action!
  2. 多平台兼容! 同时兼容 Android 5-9
  3. 轻量极简!

如何使用

  1. adb push framework.jar monkey.jar 文件到 /sdcard
  2. 执行
    adbshell CLASSPATH=/sdcard/monkey.jar:/sdcard/framework.jar exec app_process /system/bin tv.panda.test.monkey.Monkey-p com.panda.videoliveplatform --uiautomatormix --running-minutes 60

    脱机运行(#53 楼)

参数说明

  1. tv.panda.test.monkey.Monkey 主调入口 无需修改
  2. -p com.panda.videoliveplatform 待测 appid
  3. 策略模式

    --uiautomatormix 混合模式(70% 控件解析随机点击,其余 30% 按原 Monkey 事件概率分布)
    --pct-uiautomatormix n 可自定义混合模式中控件解析事件概率
    --uiautomatordfs DFS 深度遍历算法(优化版)(注 Android5 不支持 dfs)
    --uiautomatortroy Troy 模式 见(#74 楼)
    非以上两种为原始 Monkey 策略

  4. 执行时长
    --running-minutes 60 执行 60 分钟 monkey

  5. 场景细粒度控制
    --act-whitelist-file/sdcard/awl.strings 自定义 Activity 白名单
    例:

    com.panda.videoliveplatform.activity.WelcomeActivity
    com.panda.videoliveplatform.activity.SplashWakeActivity
    com.panda.videoliveplatform.activity.MainFragmentActivity
    com.panda.videoliveplatform.activity.LiveRoomActivity
    

    锁定跳转只可进入其中的某个 Activity
    --act-blacklist-file 同上

  6. 其他参数及用法同原始 Monkey

特性简介

a. 速度快 每秒 10-15 个 Action 事件
界面控件解析算法通过改造底层 framework,直接使用 AccessibilityNodeInfo 并优化减化其调度流程,解析速度控制在 50ms 内,可对界面变化做快速反应。

{
val clickable = ArrayList<AccessibilityNodeInfo>()
collectClickable(clickable, root)   //递归算法生成node树结构
......
val node = clickable[random.nextInt(count)]
val nodeRect = Rect()
node.getBoundsInScreen(nodeRect)  //选取其中某个node的 rect ,随机点击其中某point
generateClickEventAt(nodeRect, 0L)
}

b. Android 全平台兼容
兼容 Android5,6,7,8,p 各系列。通过反射原理动态解析各平台 Api 差异,使用一套逻辑兼容全系列。

{
Class<?> clazz = mAm.getClass();
String name = "setActivityController";    //存在差异的api
Method method = findMethod(clazz, name, android.app.IActivityController.class);     //反射动态search api
if (method != null) {
......
}
method = findMethod(clazz, name, android.app.IActivityController.class, boolean.class);
if (method != null) {
......
}

c. 防跳出
控件解析时获取进程推栈 Top Activity,按非白即黑立即执行切回。各事件执行时按特有逻辑屏蔽掉状态栏,防止误操作。

{
......
cn = this.mDevice.mAm.getTasks(1, 0).get(0).topActivity    //取top activity
if (cn != null) currentPackage = cn.getPackageName()
if (!MonkeyUtils.packageFilter.isPackageValid(currentPackage!!)) {    //判断非白即黑
this.mQ.clear()
this.generateActivity()
......
}

d. 防休眠
休眠时自动检测并唤醒屏幕。

{
......
if (!this.mPM!!.isInteractive) {      //判断处于休眠中
......
val i = Runtime.getRuntime().exec(arrayOf("input", "keyevent", "26")).waitFor()    //唤醒设备
......
}

e. 熔断机制
当事件按某个特有模式固定执行一段时间时则自动触发熔断开始自拉活,防止假死。如重复点击同一位置 n 秒。

private fun isBlocked(): Boolean{
val jam = true
......
val last = actionsHistory.last()
for (i in 2..30){    //重复点击n次 触发熔断
if (mVerbose > 1) Logger.log("last action is ${actionsHistory.size-1} code = $last, action${actionsHistory.size-i} code = ${actionsHistory[actionsHistory.size-i]}")
if (last != actionsHistory[actionsHistory.size-i]){
return false
}
}
//其他熔断
.....
}

f. 场景细粒度
引入 Activity 黑白名单,可控制限定在某些场景内。如只测试某几个相关页面。

private inner class ActivityController : IActivityController.Stub() {
override fun activityStarting(intent: Intent, pkg: String): Boolean {
var allowActivity = true
if (MonkeyUtils.activityFilter.hasValidActivitys()){
val currentActivity: String? = try {intent.component.className} catch (e:Exception){null}
if (currentActivity != null){
allowActivity = MonkeyUtils.activityFilter.checkEnteringActivity(currentActivity)     //通过filter的才允许跳转
}
Logger.log("// Activity : ${currentActivity} in Intent")
}
......
}
......
}

g. 随机自动输入
检测当遇到可输入模式时,按设定(ape.string)或随机输入键盘事件。如输入 666 或 2333 弹幕
随机输入 需要提前安装 adbkeyboard
https://github.com/senzhk/ADBKeyBoard

{
......
val inputMethodVisbleHight = this.mDevice.mIMM!!.getInputMethodWindowVisibleHeight()    //存在键盘输入栏
if (inputMethodVisbleHight <= 0) return
//注入键盘事件
try { generateRandomKeyEvents() }catch (e : Exception){ }
......
}

h. 崩溃堆栈自动保存
当崩溃(crash、oom)发生时自动抓取,并存于/sdcard/crash-dump.log

{
override fun appCrashed(processName: String, pid: Int, shortMsg: String, longMsg: String, timeMillis: Long, stackTrace: String): Boolean {
......
writeDumpLog("// CRASH: $processName (pid $pid) (dump time: $dateStr)")
writeDumpLog("// Build Time: ${Build.TIME}")
writeDumpLog("// ${stackTrace.replace("n", "n// ")}")
....
}

todo

  1. 特殊事件序列 - 已完成
  2. 引入 GT 性能测试
  3. 控件黑名单 - 已完成
  4. xposed 模式 --见 xmonkey
  5. Ai 算法 模式

** 其他 **

扫盲贴: https://testerhome.com/topics/11884

常见问题排查

  1. 小米手机未开启 “开发者选项” -> "USB 调试(安全设置)允许通过 usb 调试修改权限或模拟点击"。
    开启后 ok 。报错 log 如下图

    (无需 Root) 基于 Android Monkey 二次开发,实现高速点击的 Android Monkey 自动化工具 fastmonkey – 代号 Maxim-图片2

  2. accessibilityservice 被其他驱动占用 agent 未注销。如使用过 atx 未执行 unregister。
    执行 unregister 后 OK。报错 log 如下图,或无 log

    (无需 Root) 基于 Android Monkey 二次开发,实现高速点击的 Android Monkey 自动化工具 fastmonkey – 代号 Maxim-图片3



  3. 厂商修改造成 dex 无法 load ,maxim 启动后就退出。实际什么都未执行。无 log 输出。 logcat 如下图。此问题暂时待查

    (无需 Root) 基于 Android Monkey 二次开发,实现高速点击的 Android Monkey 自动化工具 fastmonkey – 代号 Maxim-图片4

4.运行 maxim 无任何 log,启动后就退出。需检查/sdcard/是否存在 monkey.jar ,framework.jar。部分机型发现 adb push 过去 monkey.jar 自动被更名成 monkey. 导致无法运行。

(无需 Root) 基于 Android Monkey 二次开发,实现高速点击的 Android Monkey 自动化工具 fastmonkey – 代号 Maxim-图片5

5.vivo7.1 运行 maxim 报错,需要关闭锁屏和开启 usb 模拟点击 ,然后就可以跑 monkey 了。报错如下:

(无需 Root) 基于 Android Monkey 二次开发,实现高速点击的 Android Monkey 自动化工具 fastmonkey – 代号 Maxim-图片6

update

#40 楼
支持特殊事件序列 max.xpath.actions
如何查看特殊事件 log #79 楼

#44 楼 #52 楼
支持屏蔽黑控件或黑区域 max.widget.black

#57 楼
支持截图,dump xml
崩溃回溯式截图 #92 楼

#74 楼
Troy 模式

#169 楼
Monkeyapi

 
评论  200  访客  200
    • isally
      isally 9

      我跟你遇到相同的问题,也是配置了 max.widget.black 不生效,但是配在 max.xpath.selector 的 blackList 里面是有效的,你后来有研究过怎么让 max.widget.black 生效吗?

      • 对酒当歌
        对酒当歌 9

        你这个问题找到原因了没,老哥

        • zhangzhao_lenovo
          zhangzhao_lenovo 9

          Throttle: 2000 增加这个延迟时间试试。 要么是这个设备性能太差了

          • zhangzhao_lenovo
            zhangzhao_lenovo 9

            找到原因了 resourceId 这个地方要用 resource-id,但是发现了一个新问题,输入框输入不全就执行了下一个步骤了。比如账号,我想输入 13188880000,但是实际执行时,只输入了 13,就不输入了,不知道这是什么原因
            日志
            [Maxim] // Special Event:
            [Maxim] // Event1:
            [Maxim] // Prob: 1.0
            [Maxim] // Actvity: com.pingan.anydoor.rymlogin.ui.login.LoginActivity
            [Maxim] // Step0:
            [Maxim] // XPath: //*[@resource-id=’com.pingan.anne.rym:id/comm_input_txt’]
            [Maxim] // XPathExpression: org.apache.xpath.jaxp.XPathExpressionImpl@dec9966
            [Maxim] // Action: INPUTTEXT
            [Maxim] // Text: 13188880000
            [Maxim] // Throttle: 2000
            [Maxim] // Step1:
            [Maxim] // XPath: //*[@resource-id=’com.pingan.anne.rym:id/comm_input_txt’]
            [Maxim] // XPathExpression: org.apache.xpath.jaxp.XPathExpressionImpl@f5e94a7
            [Maxim] // Action: INPUTTEXT
            [Maxim] // Text: qweqwe123
            [Maxim] // Throttle: 1000
            [Maxim] // Step2:
            [Maxim] // XPath: //*[@resource-id=’com.pingan.anne.rym:id/yzt_sdk_login_login_btn’]
            [Maxim] // XPathExpression: org.apache.xpath.jaxp.XPathExpressionImpl@cba5d54
            [Maxim] // Action: CLICK
            [Maxim] // Text:
            [Maxim] // Throttle: 1000

            ——- 下面接一段—–
            [Maxim] // Activity : com.pingan.anydoor.rymlogin.ui.login.LoginActivity in Intent
            [Maxim] // Allowing start of Intent { cmp=com.pingan.anne.rym/com.pingan.anydoor.rymlogin.ui.login.LoginActivity } in package com.pingan.anne.rym
            [Maxim] // Activity : com.pingan.anydoor.rymlogin.ui.login.LoginActivity in Intent
            [Maxim] // Allowing start of Intent { cmp=com.pingan.anne.rym/com.pingan.anydoor.rymlogin.ui.login.LoginActivity } in package com.pingan.anne.rym
            [Maxim] // : debug, currentActivity is com.pingan.anydoor.rymlogin.ui.login.LoginActivity
            [Maxim] // Special Event : XPath = //*[@resource-id=’com.pingan.anne.rym:id/comm_input_txt’], Index = 0, Action = INPUTTEXT, Text = 13188880000
            [Maxim] // Find it : 1|1|4|0|1, android.widget.EditText, null, 13188880000, null, true, Rect(174, 554 – 914, 678)
            [Maxim] // Special Event : XPath = //*[@resource-id=’com.pingan.anne.rym:id/comm_input_txt’], Index = 1, Action = INPUTTEXT, Text = qweqwe123
            [Maxim] // Find it : 3|1|4|0|1, android.widget.EditText, null, 登录密码, null, true, Rect(174, 716 – 997, 840)
            [Maxim] // Special Event : XPath = //*[@resource-id=’com.pingan.anne.rym:id/yzt_sdk_login_login_btn’], Index = 0, Action = CLICK, Text =
            [Maxim] // Find it : 4|1|4|0|1, android.widget.TextView, null, 登录, null, true, Rect(83, 946 – 997, 1056)
            [Maxim] // Click: com.pingan.anne.rym:id/rym_login_sdk_back_img, android.widget.ImageView, Rect(0, 110 – 110, 239), 8fc0405b6d8b908be727aa0e73466490
            [Maxim] // event3, 2019-04-15 15:07:35.892
            [Maxim] :Sending Touch (ACTION_DOWN): 0:(544.0,616.0)
            [Maxim] // event4, 2019-04-15 15:07:35.894
            [Maxim] :Sending Touch (ACTION_UP): 0:(544.0,616.0)
            [Maxim] // event5, 2019-04-15 15:07:35.895
            [Maxim] // Sleeping for 800 milliseconds
            [Maxim] // event5, 2019-04-15 15:07:36.698
            [Maxim] // debug, send text =13188880000
            [Maxim] // event6, 2019-04-15 15:07:37.028
            [Maxim] // Sleeping for 800 milliseconds
            [Maxim] // event6, 2019-04-15 15:07:37.832
            [Maxim] // Sleeping for 2000 milliseconds
            [Maxim] // event6, 2019-04-15 15:07:39.836
            [Maxim] // Sleeping for 800 milliseconds
            [Maxim] // event6, 2019-04-15 15:07:40.640
            [Maxim] :Sending Touch (ACTION_DOWN): 0:(585.5,778.0)
            [Maxim] // event7, 2019-04-15 15:07:40.652
            [Maxim] :Sending Touch (ACTION_UP): 0:(585.5,778.0)
            [Maxim] // event8, 2019-04-15 15:07:40.656
            [Maxim] // Sleeping for 800 milliseconds
            [Maxim] // event8, 2019-04-15 15:07:41.459
            [Maxim] // debug, send text =qweqwe123
            [Maxim] // event9, 2019-04-15 15:07:41.791
            [Maxim] // Sleeping for 800 milliseconds
            [Maxim] // event9, 2019-04-15 15:07:42.594
            [Maxim] // Sleeping for 1000 milliseconds
            [Maxim] // event9, 2019-04-15 15:07:43.601
            [Maxim] // Sleeping for 800 milliseconds
            [Maxim] // event9, 2019-04-15 15:07:44.404
            [Maxim] :Sending Touch (ACTION_DOWN): 0:(540.0,1001.0)
            [Maxim] // event10, 2019-04-15 15:07:44.410
            [Maxim] :Sending Touch (ACTION_UP): 0:(540.0,1001.0)
            [Maxim] // event11, 2019-04-15 15:07:44.413
            [Maxim] // Sleeping for 800 milliseconds
            [Maxim] // event11, 2019-04-15 15:07:45.216
            [Maxim] // Sleeping for 1000 milliseconds
            [Maxim] // event11, 2019-04-15 15:07:46.222
            [Maxim] // Sleeping for 800 milliseconds
            [Maxim] // event11, 2019-04-15 15:07:47.025
            [Maxim] :Sending Touch (ACTION_DOWN): 0:(55.0,174.5)
            [Maxim] // event12, 2019-04-15 15:07:47.031
            [Maxim] :Sending Touch (ACTION_UP): 0:(55.0,174.5)
            [Maxim] // event13, 2019-04-15 15:07:47.036
            [Maxim] // Sleeping for 800 milliseconds

            • zhangzhao_lenovo
              zhangzhao_lenovo 9

              [Maxim] // Special Event : XPath = //[@resourceId=’com.pingan.anne.rym:id/comm_input_txt’], Index = 0, Action = INPUTTEXT, Text = 13188880000
              [Maxim] // InputMethodVisibleHeight: 53, lastInput=85, current=88
              [Maxim] ** WARNING // Device has no this key KEYCODE_T
              看 log 是 没有找到匹配 xpath 的控件。 如果找到 会打印 find it

              • zhangzhao_lenovo
                zhangzhao_lenovo 9

                请教一下,执行 max.xpath.actions 里面的 actions,日志有显示 Special Event,但是进入到这个页面后,里面的 action 没被执行,比如输入框,我想输入 123,结果输入框是随机输入字符,里面有告警信息:[Maxim] *** WARNING // Device has no this key KEYCODE_T,请问是啥原因?
                日志信息:
                [Maxim] // Selecting main activities from category android.intent.category.LAUNCHER
                [Maxim] // + Using main activity com.pingan.anne.controller.WelcomeActivity (from package com.pingan.anne.rym)
                [Maxim] // Selecting main activities from category android.intent.category.MONKEY
                [Maxim] // Add Launcher To ActivityWhiteList : com.pingan.anne.controller.WelcomeActivity
                [Maxim] // AllowPackage: com.pingan.anne.rym
                [Maxim] // AllowActivity: com.pingan.anne.controller.HomeActivity
                [Maxim] // AllowActivity: com.pingan.anydoor.rymlogin.ui.login.LoginActivity
                [Maxim] // AllowActivity: com.pingan.anydoor.hybird.activity.CacheableWebViewActivity
                [Maxim] // AllowActivity: com.pingan.anne.controller.WelcomeActivity
                [Maxim] // IncludeCategory: android.intent.category.LAUNCHER
                [Maxim] // IncludeCategory: android.intent.category.MONKEY
                [Maxim] // Special Event:
                [Maxim] // Event1:
                [Maxim] // Prob: 1.0
                [Maxim] // Actvity: com.pingan.anydoor.rymlogin.ui.login.LoginActivity
                [Maxim] // Step0:
                [Maxim] // XPath: //*[@resourceId=’com.pingan.anne.rym:id/comm_input_txt’]
                [Maxim] // XPathExpression: org.apache.xpath.jaxp.XPathExpressionImpl@bbefac6
                [Maxim] // Action: INPUTTEXT
                [Maxim] // Text: 13188880000
                [Maxim] // Throttle: 1000
                [Maxim] // Step1:
                [Maxim] // XPath: //*[@resourceId=’com.pingan.anne.rym:id/comm_input_txt’]
                [Maxim] // XPathExpression: org.apache.xpath.jaxp.XPathExpressionImpl@bdd4a87
                [Maxim] // Action: INPUTTEXT
                [Maxim] // Text: qweqwe123
                [Maxim] // Throttle: 1000
                [Maxim] // Step2:
                [Maxim] // XPath: //*[@resourceId=’com.pingan.anne.rym:id/yzt_sdk_login_login_btn’]
                [Maxim] // XPathExpression: org.apache.xpath.jaxp.XPathExpressionImpl@5580db4
                [Maxim] // Action: CLICK
                [Maxim] // Text:
                [Maxim] // Throttle: 1000
                [Maxim] // Black Widget List:
                [Maxim] // InputMethod ID: InputMethodInfo{com.baidu.input_mi/.ImeService, settings: com.baidu.input.ImeMainConfigActivity}.id
                [Maxim] // InputMethod ID: InputMethodInfo{com.github.uiautomator/.FastInputIME, settings: null}.id
                [Maxim] // InputMethod ID: InputMethodInfo{com.sohu.inputmethod.sogou.xiaomi/.SogouIME, settings: com.sohu.inputmethod.sogou.xiaomi.SogouIMESettingsLauncher}.id
                [Maxim] // InputMethod ID: InputMethodInfo{com.netease.nie.yosemite/.ime.ImeService, settings: null}.id
                [Maxim] // InputMethod ID: InputMethodInfo{com.android.adbkeyboard/.AdbIME, settings: null}.id
                [Maxim] // Find ADBKeybaord.
                [Maxim] // Device Info: Xiaomi-MI 8 UD, Android Version: 8.1.0
                [Maxim] // activityResuming(com.pingan.anne.rym)
                [Maxim] // activityResuming(com.pingan.anne.rym)
                [Maxim] // activityResuming(com.pingan.anne.rym)
                [Maxim] strategy : uiautomator-Troy.
                ————————————–下面还有一段—–
                [Maxim] // Activity : com.pingan.anydoor.rymlogin.ui.webview.LoginWebviewActivity in Intent
                [Maxim] // Rejecting start of Intent { cmp=com.pingan.anne.rym/com.pingan.anydoor.rymlogin.ui.webview.LoginWebviewActivity } in package com.pingan.anne.rym
                [Maxim] // Activity : com.pingan.anydoor.rymlogin.ui.webview.LoginWebviewActivity in Intent
                [Maxim] // Rejecting start of Intent { cmp=com.pingan.anne.rym/com.pingan.anydoor.rymlogin.ui.webview.LoginWebviewActivity } in package com.pingan.anne.rym
                [Maxim] // Special Event : XPath = //*[@resourceId=’com.pingan.anne.rym:id/comm_input_txt’], Index = 0, Action = INPUTTEXT, Text = 13188880000
                [Maxim] // InputMethodVisibleHeight: 53, lastInput=85, current=88
                [Maxim] *** WARNING // Device has no this key KEYCODE_T
                [Maxim] *** WARNING // Device has no this key KEYCODE_7
                [Maxim] *** WARNING // Device has no this key KEYCODE_7
                [Maxim] *** WARNING // Device has no this key KEYCODE_4
                [Maxim] *** WARNING // Device has no this key KEYCODE_J
                [Maxim] *** WARNING // Device has no this key KEYCODE_3
                [Maxim] *** WARNING // Device has no this key KEYCODE_1
                [Maxim] *** WARNING // Device has no this key KEYCODE_3
                [Maxim] *** WARNING // Device has no this key KEYCODE_2
                [Maxim] *** WARNING // Device has no this key KEYCODE_5
                [Maxim] *** WARNING // Device has no this key KEYCODE_1
                [Maxim] *** WARNING // Device has no this key KEYCODE_P
                [Maxim] *** WARNING // Device has no this key KEYCODE_2
                [Maxim] *** WARNING // Device has no this key KEYCODE_H
                [Maxim] *** WARNING // Device has no this key KEYCODE_6
                [Maxim] *** WARNING // Device has no this key KEYCODE_3
                [Maxim] *** WARNING // Device has no this key KEYCODE_T
                [Maxim] // Click: com.pingan.anne.rym:id/comm_input_txt, android.widget.EditText, Rect(174, 554 – 997, 678), 3ae219b787f9cfbe30cdb257e4dec4df
                [Maxim] // event57, 2019-04-12 11:12:50.212
                [Maxim] // Sleeping for 10 milliseconds
                [Maxim] // event57, 2019-04-12 11:12:50.224
                [Maxim] // Sleeping for 800 milliseconds
                [Maxim] // event57, 2019-04-12 11:12:51.026
                [Maxim] // Sleeping for 10 milliseconds
                [Maxim] // event57, 2019-04-12 11:12:51.039
                [Maxim] // Sleeping for 800 milliseconds
                [Maxim] // event57, 2019-04-12 11:12:51.842
                [Maxim] // Sleeping for 10 milliseconds
                [Maxim] // event57, 2019-04-12 11:12:51.856
                [Maxim] // Sleeping for 800 milliseconds
                [Maxim] // event57, 2019-04-12 11:12:52.659
                [Maxim] // Sleeping for 10 milliseconds
                [Maxim] // event57, 2019-04-12 11:12:52.671
                [Maxim] // Sleeping for 800 milliseconds
                [Maxim] // event57, 2019-04-12 11:12:53.475
                [Maxim] // Sleeping for 10 milliseconds
                [Maxim] // event57, 2019-04-12 11:12:53.488
                [Maxim] // Sleeping for 800 milliseconds
                [Maxim] // event57, 2019-04-12 11:12:54.292
                [Maxim] // Sleeping for 10 milliseconds
                [Maxim] // event57, 2019-04-12 11:12:54.309
                [Maxim] // Sleeping for 800 milliseconds
                [Maxim] // event57, 2019-04-12 11:12:55.112
                [Maxim] // Sending Key (ACTION_DOWN): 47 KEYCODE_S
                [Maxim] // event58, 2019-04-12 11:12:55.120
                [Maxim] // Sending Key (ACTION_UP): 47 KEYCODE_S
                [Maxim] // event59, 2019-04-12 11:12:55.150
                [Maxim] // Sleeping for 800 milliseconds
                [Maxim] // event59, 2019-04-12 11:12:55.954
                [Maxim] // Sleeping for 10 milliseconds
                [Maxim] // event59, 2019-04-12 11:12:55.966
                [Maxim] // Sleeping for 800 milliseconds
                [Maxim] // event59, 2019-04-12 11:12:56.769
                [Maxim] // Sleeping for 10 milliseconds
                [Maxim] // event59, 2019-04-12 11:12:56.782
                [Maxim] // Sleeping for 800 milliseconds
                [Maxim] // event59, 2019-04-12 11:12:57.586
                [Maxim] // Sleeping for 10 milliseconds
                [Maxim] // event59, 2019-04-12 11:12:57.598
                [Maxim] // Sleeping for 800 milliseconds
                [Maxim] // event59, 2019-04-12 11:12:58.402
                [Maxim] // Sleeping for 10 milliseconds
                [Maxim] // event59, 2019-04-12 11:12:58.415
                [Maxim] // Sleeping for 800 milliseconds
                [Maxim] // event59, 2019-04-12 11:12:59.218
                [Maxim] // Sleeping for 10 milliseconds
                [Maxim] // event59, 2019-04-12 11:12:59.230
                [Maxim] // Sleeping for 800 milliseconds
                [Maxim] // event59, 2019-04-12 11:13:00.032
                [Maxim] // Sleeping for 10 milliseconds
                [Maxim] // event59, 2019-04-12 11:13:00.044
                [Maxim] // Sleeping for 800 milliseconds
                [Maxim] // event59, 2019-04-12 11:13:00.847
                [Maxim] // Sleeping for 10 milliseconds
                [Maxim] // event59, 2019-04-12 11:13:00.860
                [Maxim] // Sleeping for 800 milliseconds
                [Maxim] // event59, 2019-04-12 11:13:01.663
                [Maxim] // Sleeping for 10 milliseconds
                [Maxim] // event59, 2019-04-12 11:13:01.676
                [Maxim] // Sleeping for 800 milliseconds
                [Maxim] // event59, 2019-04-12 11:13:02.480
                [Maxim] // Sleeping for 10 milliseconds
                [Maxim] // event59, 2019-04-12 11:13:02.492
                [Maxim] // Sleeping for 800 milliseconds
                [Maxim] // event59, 2019-04-12 11:13:03.295
                [Maxim] // Sleeping for 10 milliseconds
                [Maxim] // event59, 2019-04-12 11:13:03.308
                [Maxim] // Sleeping for 800 milliseconds
                [Maxim] // event59, 2019-04-12 11:13:04.112
                [Maxim] // Sleeping for 10 milliseconds
                [Maxim] // event59, 2019-04-12 11:13:04.128
                [Maxim] // Sleeping for 800 milliseconds
                [Maxim] // event59, 2019-04-12 11:13:04.931
                [Maxim] :Sending Touch (ACTION_DOWN): 0:(585.5,616.0)
                [Maxim] // event60, 2019-04-12 11:13:04.944
                [Maxim] :Sending Touch (ACTION_UP): 0:(585.5,616.0)
                [Maxim] // event61, 2019-04-12 11:13:04.947
                [Maxim] // Sleeping for 800 milliseconds
                [Maxim] // Special Event : XPath = //*[@resourceId=’com.pingan.anne.rym:id/comm_input_txt’], Index = 0, Action = INPUTTEXT, Text = 13188880000
                [Maxim] // InputMethodVisibleHeight: 53, lastInput=88, current=128
                [Maxim] // Click: com.pingan.anne.rym:id/comm_input_txt, android.widget.EditText, Rect(174, 716 – 997, 840), db6cf51b1433e580022c50e8954622e1

                • zhangzhao_lenovo
                  zhangzhao_lenovo 9

                  试一下?

                  • Jiizukelee
                    Jiizukelee 9

                    这个支持遍历 webview 吗?

                    • shlshl211
                      shlshl211 9

                      请问下 api 适配中 findMethod 是怎么实现的呢?可以说下吗?因为有时候用 clazz.getDeclaredMethod(xx) 不生效,setAccessible(true) 也不行,所以想知道下怎么实现的呢

                      • TD
                        TD 9

                        好的,谢谢,我试一下

                      匿名

                      发表评论

                      匿名网友
                      确定

                      拖动滑块以完成验证