zoukankan      html  css  js  c++  java
  • Shell脚本 | 健壮性测试之空指针检查

    通过 "adb shell am start" 遍历安卓应用所有的 Activity,可以检查是否存在空指针的情况。

    以下为梳理后的测试流程:

    1. 通过 apktool 反编译 apk(输入参数 apk 路径)
    2. 得到反编译后的 AndroidManifest.xml 文件
    3. 通过 FindActivity.py 得到 Activity_List(activity 列表)
    4. 删除 Activity_List 中含有 "loader.a.ActivityN1/loader.a.ActivityP0/loader.a.ActivityP1/loader.a.ActivityP2" 的 activity(部分 App 反编译后的 activity 列表中有类似名字的无意义 activity,可以删除)
    5. 运行 NullPointer.py,输出 log 在指定文件夹
    6. 手动分析 log

    写了个脚本将以上步骤串了起来。

    运行方式:

    • sh +x check_nullpointer.sh

    前提条件:

    • MacBook
    • python
    • apktool
    • aapt

    运行示例:

    脚本如下:
    check_nullpointer.sh

    #!/usr/bin/env bash
    # 如果有反编译后的文件夹存在,先清空当前环境
    if [[ -d "apkFile" ]]; then
        rm -r AC_list_filter Activity_List apkFile log.txt all_log.txt
    fi
    # 当前路径
    WORKSPACE=`pwd`
    # apk地址
    echo "Please enter the apk file address:"
    read apk_address
    # 通过aapt获取包名
    pkg_name=$(aapt dump badging ${apk_address} | grep package: | sed 's/ //g' | tr -d $'
    ' | cut -d"'" -f2)
    # 通过apktool反编译,反编译后的文件输出到apkFile文件夹
    apktool d ${apk_address} -o apkFile
    # 获取安卓manifest文件
    ANDROID_MANIFEST=${WORKSPACE}/apkFile/AndroidManifest.xml
    # 通过FindActivity.py获取Activity列表
    python FindActivity.py ${ANDROID_MANIFEST}
    # 删除包含"loader.a.ActivityN1/loader.a.ActivityP0/loader.a.ActivityP1/loader.a.ActivityP2"的Activity
    sed '/loader.a.ActivityN1/d;/loader.a.ActivityP0/d;/loader.a.ActivityP1/d;/loader.a.ActivityP2/d' Activity_List > AC_list_filter
    # 运行NullPointer.py,遍历启动activity,输出log在指定文件夹
    echo "Starting..."
    python NullPointer.py ${pkg_name}
    # 全部log
    adb logcat -d -v threadtime > ${WORKSPACE}/all_log.txt
    # error log
    adb logcat -d -v long "AndroidRuntime:E" "*:S" > ${WORKSPACE}/log.txt
    echo "log文件:${WORKSPACE}/log.txt"
    

    FindActivity.py

    import xml.dom.minidom as minidom
    import sys
    def find_activities(filePath):
        xml = minidom.parse(filePath)
        root = xml.getElementsByTagName('manifest')
        appNode = None
        for node in root[0]._get_childNodes():
            if(node._get_localName() == "application"):
                appNode = node
                break
        content = ''
        for item in appNode._get_childNodes():
            if(item._get_localName() == 'activity'):
                content = content + item.getAttribute("android:name") + '
    '
    
        fs = open("Activity_List", 'w')
        fs.write(content)
        fs.close()
    if __name__ == '__main__':
        filePath = sys.argv[1]
        find_activities(filePath)
    

    NullPointer.py

    #!/usr/bin/env python
    # -*- coding: utf-8 -*- 
    import os
    import sys
    import time
    import threading
    # 当前路径
    PATH = sys.path[0]
    # 应用包名
    PKG_NAME = sys.argv[1]
    # 先判断设备是否连接
    os.popen("adb wait-for-device")
    # 遍历文件获得activities 的值
    def CheckNullPoint():
        f = open(PATH + "/" + "AC_list_filter", "r")
        for line in f.readlines():
            os.popen('adb shell am start -n %s/%s' % (PKG_NAME, line))
            # print("adb shell am start -n %s/%s" % (PKG_NAME, line))
        time.sleep(3)
        f.close()
    # back键退出应用
    def quit_app():
        os.popen('adb shell input keyevent 4')
    # 清空log
    def clear_log():
        os.popen('adb logcat -c')
    clear_log()
    CheckNullPoint()
    print "Success"
    # back键退出应用
    for i in range(10):
        quit_app()
    

    欢迎关注微信公众号"测试开发Stack"

  • 相关阅读:
    CSS Sprite笔记
    前端分页页码静态部分制作
    有趣的网页小部件笔记
    Lintcode 85. 在二叉查找树中插入节点
    Lintcode 166. 主元素
    网页失去焦点标题变化效果
    Lintcode 166. 链表倒数第n个节点
    Lintcode 157. 判断字符串是否没有重复字符
    Lintcode 175. 翻转二叉树
    Lintcode 372. O(1)时间复杂度删除链表节点
  • 原文地址:https://www.cnblogs.com/liushengchieh/p/10578776.html
Copyright © 2011-2022 走看看