zoukankan      html  css  js  c++  java
  • 记一次解决Original error: UiAutomator quit before it successfully launched

    【前言】

    在使用Appium的时候,你可能会遇见各种各样问题,如果不能很快在网上搜索解决,请耐心查看和分析Appium的输出日志,因为不同的环境以及不同的目的都会有千奇百怪的问题,也许你遇见的问题网上就没有人碰见过。

    【背景以及环境】

    我的开发环境是windows10 + Appium1.4.16.1 + IDEA + 真机测试。

    当前,我配置好了desiredCapabilities,代码如下:

     1         // desiredCapabilities
     2         capabilities = new DesiredCapabilities();
     3         capabilities.setCapability("automationName","Appium");
     4         capabilities.setCapability("platformName","Android");
     5         capabilities.setCapability("platformVersion","5.1");
     6         capabilities.setCapability("deviceName", DEVICE_UDID);
     7         capabilities.setCapability("udid", DEVICE_UDID);
     8         capabilities.setCapability("noSign", "true");
    9 //getClassesDir()私有函数,得到当前项目编译后的根目录 10 capabilities.setCapability("app", getClassesDir()+"\"+APP_PATH); 11 12 //使用aapt2来获取安装的apk的包名 13 //由于会打包,所以我先把这些工具拷贝到宿主操作系统的某处 14 Runtime runtime = Runtime.getRuntime();
    15 //copyDirectoryFromJarToDisk(directoryPath)私有函数,将项目中的文件夹拷贝到磁盘上去 16 String toolPath = copyDirectoryFromJarToDisk("tool"); 17 String apkPath = copyDirectoryFromJarToDisk("apk"); 18 String command = toolPath+"/aapt2.exe d badging " 19 +apkPath+"/"+APP_PATH.split("/")[1];

           //下面这段将aapt2 dump badging *.apk得到的apk信息导出到磁盘上的apkinfo.txt中去
    20 if(System.getProperty("os.name").toLowerCase().startsWith("win")){ 21 command += " > "+toolPath+"/apkinfo.txt"; 22 } else { 23 command += " | "+toolPath+"/apkinfo.txt"; 24 } 25 runtime.exec(command);

           // getApkInfo(infoName, apkInfoTxtPath)私有函数从apkinfo.txt文件中获取相应字段
    26 capabilities.setCapability("appPackage",getApkInfo("package",toolPath)); 27 capabilities.setCapability("appActivity",getApkInfo("launchable-activity",toolPath));

    简单说上面的主要工作是配置DesiredCapabilities,其中为了了解安装的apk的包名和启动Activity,我使用了aapt2工具,将结果导入到磁盘的某个txt文件中去。然后包名的信息就从这个文件中读。

    【问题以及解决对策,解决对策在第5点】

    运行,报错,控制台第一行出现

    Exception in thread "main" org.openqa.selenium.SessionNotCreatedException: Unable to create a new remote session. Please check the server log for more details. Original error: A new session could not be created. (Original error: UiAutomator quit before it successfully launched) (WARNING: The server did not provide any stacktrace information)

    上面的内容说的就是UiAutomator(sdk提供的一个工具)没有正常启动。后来经过搜索,发现问题千奇百怪的,解决方案也五花八门,但是都不管用。于是就自行分析查看日志。过程如下:

    1、查看appium日志,发现最早出现问题的是

    是说要从Bilibili.apk读取strings.json,但是string.json路径里面有null值,因此不成功。不过影响不大,程序可以继续执行。

    2、继续往下看

    这里应该是执行卸载命令了,不过命令 adb -s $ANDROID_SERIAL uninstall PACKAGE 是可以执行的,但是上面提示uninstall还需要一个参数。接着往下看

    3、

    这里应该是问题关键了,Appium在之前拷贝它的AppiumBootstrap.jar到Android机器的/data/local/tmp下,然后这里的第一句使用了 adb shell uiautomator runtest AppiumBootstrap.jar -c io.appium.android.bootstrap.Bootstrap -e pkg PACKAGE 的语句来执行拷贝进去的AppiumBoostrap.jar,我在cmd中执行该句,当我省略 PACKAGE 时,得到了和上面一样的错误。

    4、

    由此,我得知我传进去的包名是有问题的,再看上面的打印出来的包名,发现格式不对。然后我使用vscode查看打印出的apkinfo.txt文档,发现其编码为UTF-16 LE。但是我的执行环境是utf-8,所以得到的包名在utf-8下看起来是这样的:

    可见,每个可见字符之间隔了一个 u0000 ,由此解决方法也显而易见了。

    5、编码格式的解决方法是,对从aapt2打印的结果文字,在读取或者使用的时候进行转码,将 utf-16 LE 转为 utf-8 。最简单的方式就是除去多余的 u0000 字符。比如对从文件中读到的字符加上

    StringReadFromAAPT = StringReadFromAAPT.replace("u0000","");

    【后记】

    不管怎么说,遇到难题搜索无果时,耐心分析日志才能真正节约时间。

  • 相关阅读:
    【2020-04-03】多注意一下自己闲下来的思绪
    vue 去哪网项目 学习笔记(一)
    数据分析相关的内容
    vue 自学项目笔记
    vue 所有的指令
    vue 自学笔记(5) 列表渲染
    vue 自学笔记(4): 样式绑定与条件渲染
    vue 自学笔记(三) 计算属性与侦听器
    自学vue笔记 (二) : 实例与生命周期
    杜教BM模板
  • 原文地址:https://www.cnblogs.com/wangnig/p/11088914.html
Copyright © 2011-2022 走看看