
大型Shell脚本编写模板:测试工程师的架构指南
大约 4 分钟
大型Shell脚本编写模板:测试工程师的架构指南
当测试脚本变得复杂时,良好的结构就像建筑的钢筋骨架一样重要。一个结构清晰的脚本不仅易于维护,还能让团队协作更加顺畅。今天我们来学习如何构建一个专业级的Shell脚本模板。
脚本结构设计
一个优秀的大型Shell脚本主要分为以下几个模块:
- 注释模块 - 脚本的身份证
- 常用变量模块 - 全局配置中心
- 功能实现模块 - 核心业务逻辑
- 逻辑调用模块 - 程序入口和流程控制
#!/bin/bash
#File : full_stress.sh
#Time : 2022/09/21 21:09:06
#Author : lijiaxin.test
<<comment
需要完成的功能
1. 批量连接POD
connect_devices()
2. 实现POD的内存清理
3. 实现POD的链接
4. 批量root
5. 批量安装应用
6. 查询现在连接的POD
还需要兼容,单个POD的调试和批量POD的调试
如何调用
comment
## 脚本目录相关
CUR_DIR=$(cd "$(dirname "$0")" && pwd) ## 输出当前目录并进入该目录下
# echo "${CUR_DIR}"
# BASE_DIR=$(dirname "$CUR_DIR") ## 输出根目录
# echo "${BASE_DIR}"
tmp=$0
CUR_FILE="${tmp##*/}" ## 输出当前文件名
# echo "${CUR_FILE}"
DEVICES_INFO=iplist
PACGAGENAME=com.example.sdkdemo.boe
# echo "begin test"
# pwd
# echo "input var ${@}"
# echo "input var num : $#"
# 脚本最后使用case进行调用,或者使用if
## 总流程如下
if [ $# -eq 0 ]; then
echo '''
General Commands Manual
NAME
full_stress.sh -- stress sovle script
SYNOPSIS
full_stress.sh [-i,] [var ...]
DESCRIPTION
The following options are available:
-c 连接设备
-i optional:[pod] mandatory:[apk]安装应用
-t optional:[pod] mandatory:[x_size] mandatory:[y_size] 点击屏幕
-w optional:[pod] 查看当前应用
-ci optional:[pod] 清除iptables
-f optional:[pod] 杀掉游戏进程
-fg optional:[pod] mandatory:[PACGAGENAME] 杀掉app进程
-s optional:[pod] mandatory:[game_id] 开始游戏
-q optional:[pod] 退出游戏
-r optional:pod进行root
-m optional:[pod] mandatory:[PACGAGENAME] 用monkey运行app
-mg optional:[pod] 进入demo
'''
exit 0
fi
## 功能1 读取设备信息并打印出来 (完成)
devices_info() {
# cat "${DEVICES_INFO}"
for i in $(cat ${DEVICES_INFO}); do
echo "${i}" && adb connect "${i}"
done
}
# 功能2 进行root (完成)
adb_root() {
for i in $(cat ${DEVICES_INFO}); do
echo "${i} root " && adb -s "${i}" shell setprop debug.adb.root true &&
adb -s "${i}" root
done
}
# 功能3 清除adb的端口转发规则 (完成)
clears_iptables() {
# cat "${DEVICES_INFO}"
for i in $(cat ${DEVICES_INFO}); do
echo "${i}" && adb -s "${i}" shell iptables -F
done
}
## 功能4 开启app
monkey_app_all() {
# cat "${DEVICES_INFO}"
for i in $(cat ${DEVICES_INFO}); do
# echo "${i}" && adb -s "${i}" shell monkey -p "${1}" 1
monkey_app "${i}" "${1}"
done
}
monkey_app() {
echo "${1} star app: ${2}" && adb -s "${1}" shell monkey -p "${2}" 1
}
## 功能5 退出游戏 (完成)
quit_game_all() {
# cat "${DEVICES_INFO}"
for i in $(cat ${DEVICES_INFO}); do
# echo "${i}" && adb -s "${i}" shell "am broadcast -a com.veGame.test -e 'back' 'gameActivity'"
quit_game "${i}"
done
}
quit_game() {
echo "${1} quit " && adb -s "${1}" shell "am broadcast -a com.veGame.test -e 'back' 'gameActivity'"
}
## 功能六 杀掉app进程 (完成)
force_app_all() {
for i in $(cat ${DEVICES_INFO}); do
# echo "${i}" && adb -s "${i}" shell am force-stop "${1}"
force_app "${i}" "${1}"
done
}
force_app() {
echo "${1} foece app ${2}" && adb -s "${1}" shell am force-stop "${2}"
}
## 批量进入指定游戏(完成)
start_game_all() {
# cat "${DEVICES_INFO}"
for i in $(cat ${DEVICES_INFO}); do
# echo "${i}" && adb -s "${i}" shell "am broadcast -a com.veGame.test -e 'start' ${1}"
start_game "${i}" "${1}"
done
}
start_game() {
echo "pod : ${1} game id : ${2}" && adb -s "${1}" shell "am broadcast -a com.veGame.test -e 'start' ${2}"
}
## 查看当前app的前台的进程 (完成)
dumpsys_window_mCurrentFocus() {
echo ">>> ${1} : dumpsys_window_mCurrentFocus \n" && adb -s "${1}" shell dumpsys window | grep mCurrentFocus
}
dumpsys_window_mCurrentFocus_all() {
# cat "${DEVICES_INFO}"
for i in $(cat ${DEVICES_INFO}); do
dumpsys_window_mCurrentFocus "${i}"
# echo ">>>" "${i}" && adb -s "${i}" shell dumpsys window | grep mCurrentFocus
done
}
## 点击游戏的指定位置,比如我们需要安装游戏后把权限通过一下时 (完成)
tap_point_all() {
# cat "${DEVICES_INFO}"
for i in $(cat ${DEVICES_INFO}); do
tap_point "${i}" "${1}" "${2}"
# echo ">>>" "${i}" && adb -s "${i}" shell input tap "${1}" "${2}"
done
}
tap_point() {
# cat "${DEVICES_INFO}"
echo ">>> $1 input tap $2 $3 " && adb -s "${1}" shell input tap "${2}" "${3}"
}
## 批量安装应用 (完成)
install_app_all() {
# cat "${DEVICES_INFO}"
for i in $(cat ${DEVICES_INFO}); do
echo ">>> install ${1} to ${i}" && adb -s "${i}" shell install -r -f "${1}"
done
}
install_app() {
# cat "${DEVICES_INFO}"
echo ">>> install ${2} to ${1}" && adb -s "${1}" shell install -r -f "${2}"
}
# echo "********"
if [ "${1}" = '-c' ]; then
echo "test -i mode "
fi
case "${1}" in
c | -c | -connect | -C)
# 连接设备
devices_info
# echo?
;;
i | -i | -I | I)
## 安装应用
shift
if [ $# -eq 1 ]; then
install_app_all "$1"
else
install_app "$1" "$2"
fi
;;
-t | t | T | -T)
## 点击手机界面
shift
if [ $# -eq 2 ]; then
tap_point_all "$1" "$2"
else
tap_point "$1" "$2" "$3"
fi
;;
-w | w | W | -W)
## 查看当前的前台应用
shift
if [ $# -eq 0 ]; then
dumpsys_window_mCurrentFocus_all
else
dumpsys_window_mCurrentFocus "${1}"
fi
;;
-ci | -CI)
## 清除 ip
echo "清除iptables"
clears_iptables
;;
-f | -F | F | f)
## 杀掉游戏进程
shift
if [ $# -eq 1 ]; then
force_app_all ${PACGAGENAME}
else
force_app "$1" ${PACGAGENAME}
fi
;;
-fg | -FG)
## 杀指定app的进程
shift
if [ $# -eq 1 ]; then
force_app_all "${1}"
else
force_app "$1" "${2}"
fi
;;
-s | -S | S | s)
## 开始游戏
shift
if [ $# -eq 1 ]; then
start_game_all "${1}"
else
start_game "$1" "${2}"
fi
;;
-q | -Q | Q | q)
## 退出游戏
shift
if [ $# -eq 0 ]; then
# start_game_all ${PACGAGENAME}
quit_game_all
else
quit_game "$1"
# start_game "$1" ${PACGAGENAME}
fi
;;
-r | -R | r | R)
# 进行root
shift
if [ $# -eq 0 ]; then
adb_root
else
quit_game "$1"
# start_game "$1" ${PACGAGENAME}
fi
;;
-m | -M | M | m)
# 根据包名启动app
shift
if [ $# -eq 1 ]; then
monkey_app_all "${1}"
else
monkey_app "${1}" "${2}"
fi
;;
-mg | -MG | MG | mg)
# 根据包名启动app
shift
if [ $# -eq 0 ]; then
monkey_app_all ${PACGAGENAME}
else
monkey_app "${1}" "${PACGAGENAME}"
# quit_game "$1"
# start_game "$1" ${PACGAGENAME}
fi
;;
*)
echo "default (none of above)"
shift
echo $#
echo "$1"
echo "$2"
;;
esac