Appium的基础API介绍

一、引言

1.1、介绍

  1. Appium是一款开源、跨平台的移动端自动化测试框架,专为测试iOS/Android移动端应用设计(也支持Windows/macOS桌面应用)。
  2. 它基于WebDriver协议(W3C标准),允许开发者用Python、Java、JavaScript、Java等主流编程语言编写自动化脚本,无需修改被测应用的源码,即可实现对移动端应用的自动化操作(点击、输入、滑动、断言等)。
  3. 简单来说:Appium是移动端的Selenium,像Selenium操作网页一样,Appium操作手机APP。

1.2、Appium解析

1.2.1、Appium工作原理

开发者编写的脚本(Client) → Appium Server → 底层自动化引擎 → 移动设备 → 结果返回

1.2.2、Appium底层原理

Appium将脚本代码转换成adb命令来控制设备。

1.2.3、核心组件拆解

|------------------|----------------------------------------------------------------------------------------------------------|
| 组件 | 作用 |
| Appium Client | 各语言的客户端库(如 Python 的 appium-python-client),封装了WebDriver API,让脚本能通过HTTP请求向Server发送指令 |
| Appium Server | 核心中间层(用 Node.js开发),负责: (1)接收Client的指令 (2)根据平台(iOS/Android)转发给对应的底层引擎 (3)接收设备的执行结果,返回给Client |
| 底层自动化引擎 | 真正操作设备的"执行者" Android:UiAutomator2(主流,支持 Android 5+)、Espresso(更轻量) iOS:XCUITest(iOS 9+,替代旧的 UIAutomation) |
| Appium Inspector | 可视化工具(类似浏览器开发者工具),用于查看APP的元素属性(id、xpath、className 等),方便写元素定位表达式 |

二、环境搭建和初始化

2.1、环境安装

2.1.1、安装JDK

2.1.2、安装AndroidSDK

2.1.3、安装Appium

2.2、Appium连接初始化

2.2.1、初始化参数

在Appium中,这些初始化参数被称为Desired Capabilities。你可以把它们理解为一组告诉Appium Server"我想要测试哪个设备、哪个应用,以及用什么方式进行测试"的键值对。Appium Server在接收到这些参数后,会根据它们来启动相应的设备和应用,并初始化测试会话(Session)。

|-----------------------------|------------------------------------------------------------------------|-----------------------------------|
| 参数 | 作用 | 示例 |
| platformName | 指定测试的操作系统 | platformName="Android" |
| platformVersion | 指定设备的操作系统版本 | platformVersion="12" |
| deviceName | 指定测试设备的名称(可以随便填) | deviceName="Mumu" |
| app | 指定要安装和启动的应用的绝对路径或URL | |
| appPackage (Android特有) | 指定应用的包名 | appPackage="com.android.settings" |
| appActivity (Android特有) | 指定应用启动时的主 Activity 名称 | appActivity=".Settings |
| autoGrantPermissions | 可自动授予App所有申请的运行时权限 默认为False,不授权。 | autoGrantPermissions=True |
| automationName | 指定要使用的自动化引擎 | automationName="UiAutomator2" |
| bundleId (iOS特有) | 用于指定要测试的iOS应用的唯一标识符 | |
| noReset | 控制在测试会话开始前是否重置应用状态。 true: 不重置应用的缓存、登录状态等将会被保留。 false (默认): 重置,相当于清除数据。 | noReset=True |
| fullReset | 比noReset更彻底的重置。 它会在测试前后卸载并重新安装应用。 | fullReset=True |
| unicodeKeyboard (Android特有) | 是否启用 Unicode 输入法。 启用后,可以输入任何Unicode字符(如中文、特殊符号等)。 | unicodeKeyboard=True |
| resetKeyboard (Android特有) | 在测试结束后,是否将设备的输入法重置为默认。 通常与unicodeKeyboard配合使用。 | resetKeyboard=True |

2.2.2、案例

在获取连接之前:

  1. 必须通过adb连接到指定的设备。
  2. 必须开启Appium Server。
python 复制代码
def get_app_driver():
    """
    获取驱动
    """
    desired_caps = dict(
        # 获取设备的名字
        deviceName="Mumu",
        # 获取设备的系统
        platformName="Android",
        # 获取设备系统版本
        platformVersion="12",
        # app的名字
        appPackage="com.android.settings",
        # app的界面名
        appActivity=".Settings"
    )
    # 转换成Options对象
    options = UiAutomator2Options().load_capabilities(desired_caps)
    # 初始化驱动
    driver = webdriver.Remote('http://127.0.0.1:4723/wd/hub', options=options)
    # 返回驱动
    return driver

三、基础操作

3.1、App的基础API

使用方式:driver.xxx

|------------------------|--------------|
| 属性/方法 | 说明 |
| start_activity(包名,界面名) | 应用跳转 |
| current_package | 获取当前的app的包名 |
| current_activity | 获取当前的app的界面名 |
| quit() | 关闭driver驱动 |
| close_app() | 关闭app |
| install_app(app_path) | 安装app |
| remove_app(包名) | 卸载app |
| is_app_installed(包名) | 判断app是否安装 |
| background_app(second) | 将app置于后台 |

3.2、元素定位

元素的定位操作:

  1. 定位单个元素:element = driver.find_element(By.XXX, "XXX")
  2. 定位一批元素(返回列表):elements = driver.find_elements(By.XXX, "XXX")

3.2.1、id定位

python 复制代码
el = driver.find_element(By.ID, resource-id属性值)

3.2.2、name定位

python 复制代码
el = driver.find_element(By.NAME, name属性值)

3.2.3、class定位

python 复制代码
el = driver.find_element(By.CLASS, class属性值)

3.2.4、xpath定位

python 复制代码
el = driver.find_element(By.XPATH, xpath属性值)
  1. xpath匹配规则,使用的是相对路径。
  2. //表示使用相对路径,匹配指定或所有//后面的标签。
  3. *代表匹配所有标签,也可以自己指定,button、input、TextView等等。
  4. @后面的属性也可以自己指定,id、text、class、resource-id等。

|--------------------|----------------|
| xpath表达式 | 说明 |
| //*[@text='登录'] | 匹配文本内容为"登录"的标签 |
| //*[@id='wd'] | 匹配id属性为"wd"的标签 |

3.2、元素基本操作

3.2.1、点击 - click()

python 复制代码
element = driver.find_element(By.ID, "foo")
element.click()

3.2.2、输入 - send_keys()

python 复制代码
form_textfield = driver.find_element(By.NAME, "username")
form_textfield.send_keys("admin")

3.2.3、获取文本 - text

python 复制代码
element = driver.find_element(By.ID, "foo")
print(element.text)

3.2.4、获取位置 - location

  1. 返回值类型:字典。
  2. 返回值:元素的x和y坐标。
python 复制代码
loc = element.location

3.2.5、获取大小 - size

  1. 返回值类型:字典。
  2. 返回值:元素的宽和高。
python 复制代码
size = element.size

3.2.6、获取属性值 - get_attribute()

python 复制代码
is_active = "active" in target_element.get_attribute("class")

3.3、滑动和拖拽

3.3.1、swipe滑动

python 复制代码
driver.swipe(start_x,start_y,end_x,end_y,duration)
  1. 从一个坐标位置滑动到另一个坐标位置,只能是两点之间的滑动。
  2. 使用时最好与获取屏幕大小,配合使用。
  3. 注意:坐标只支持整型,duration的单位是ms。
python 复制代码
size = driver.get_window_size()  # 获取屏幕的大小
width = size['width']
height = size['height']

# 执行滑动操作
driver.swipe(int(width*0.8), int(height*0.5), int(width*0.2), int(height*0.5), duration=1000)

3.3.2、scroll滑动

python 复制代码
driver.scroll(orig_el,dest_el,duration) 
# orig_el:起始元素
# dest_el:目的元素
# duration持续时间,单位ms
  1. 从一个元素滑到另一个元素,直到页面自动停止。
  2. 惯性很大,有原生滚动惯性。
python 复制代码
orig_el = driver.find_element(By.XPATH, "//*[@text='壁纸']")
dest_el = driver.find_element(By.XPATH, "//*[@text='网络和互联网']")
driver.scroll(orig_el, dest_el, duration=1000)

3.3.3、drag_and_drop拖拽

python 复制代码
driver.drag_and_drop(orig_el,dest_el) 
  1. 从一个元素滑动到另一个元素,第二个元素代替第一个元素原本屏幕上的位置。
  2. 无惯性,匀速拖拽。
python 复制代码
orig_el = driver.find_element(By.XPATH, "//*[@text='壁纸']")
dest_el = driver.find_element(By.XPATH, "//*[@text='网络和互联网']")
driver.drag_and_drop(orig_el, dest_el)

3.4、自定义手势

3.4.1、使用方式

使用方式:

  1. 创建ActionBuilder的对象,并且传入driver
  2. 通过ActionBuilder的对象来获取触摸源
  3. 通过返回的触摸源来构造以系列操作序列
  4. 通过ActionBuilder的对象来调用preform()方法执行

3.4.2、W3C Actions API

|---------------|-------------------------------------------------------------------------|
| 对象 | 作用 |
| PointerInput | 定义触摸输入源(如 "手指 1""手指 2"),指定输入类型(kind="touch")和设备类型(pointerType="touch")。 |
| ActionBuilder | 管理多个 PointerInput,组合成同步 / 异步动作序列。 |
| Interaction | 定义单个动作(press/move_to/release/wait),指定时长、坐标等。 |

3.4.3、操作:长按拖拽

python 复制代码
def long_press_drag_w3c(driver, start_x, start_y, end_x, end_y, press_dur=1000, move_dur=500):
    """
    W3C 版长按拖拽(游戏常用)
    :param press_dur: 长按时长(ms)
    :param move_dur: 移动时长(ms)
    """
    # 1. 创建动作构建器
    action_builder = ActionBuilder(driver)
    # 2. 获取触摸输入源
    touch = action_builder.add_pointer_input(interaction.POINTER_TOUCH, "finger1")
    
    # 3. 构建动作序列:按下 → 长按等待 → 移动 → 释放
    touch.create_pointer_move(x=start_x, y=start_y, duration=0)  # 移动到起始点(瞬时)
    touch.create_pointer_down(button=interaction.POINTER_BUTTON_LEFT)  # 按下(模拟手指按下)
    touch.create_pointer_move(x=start_x, y=start_y, duration=press_dur)  # 长按等待(坐标不变)
    touch.create_pointer_move(x=end_x, y=end_y, duration=move_dur)  # 拖拽到目标点
    touch.create_pointer_up(button=interaction.POINTER_BUTTON_LEFT)  # 释放
    
    # 4. 执行动作(源码中会转换为 W3C 协议发送给驱动)
    action_builder.perform()

# 调用示例:将技能从 (W/2, H*0.8) 拖拽到 (W/2, H*0.4)
long_press_drag_w3c(driver, W/2, H*0.8, W/2, H*0.4, press_dur=1000, move_dur=500)

3.4.4、操作:自定义路径

python 复制代码
def custom_path_move_w3c(driver, start_x, start_y, path_points, total_dur=1000):
    """
    W3C 版自定义路径移动(游戏:角色走位)
    :param path_points: 路径坐标列表,如 [(x1,y1), (x2,y2), (x3,y3)]
    :param total_dur: 总移动时长(ms)
    """
    segment_dur = total_dur // len(path_points)  # 每段路径时长
    
    action_builder = ActionBuilder(driver)
    touch = action_builder.add_pointer_input(interaction.POINTER_TOUCH, "finger1")
    
    # 起始点按下
    touch.create_pointer_move(x=start_x, y=start_y, duration=0)
    touch.create_pointer_down(button=interaction.POINTER_BUTTON_LEFT)
    
    # 按路径点依次移动
    for (x, y) in path_points:
        touch.create_pointer_move(x=x, y=y, duration=segment_dur)
    
    # 释放
    touch.create_pointer_up(button=interaction.POINTER_BUTTON_LEFT)
    action_builder.perform()

# 调用示例:角色沿三角形路径走位
path = [(W*0.3, H*0.4), (W*0.7, H*0.4), (W*0.5, H*0.6)]
custom_path_move_w3c(driver, W/2, H/2, path, total_dur=1500)

3.5、其他操作

3.5.1、获取屏幕大小

python 复制代码
size = driver.get_window_size()
# 获取屏幕的长度:size.get("height")
# 获取屏幕的宽度:size.get("width")

3.5.2、获取屏幕分辨率

python 复制代码
driver.get_window_size()

3.5.3、获取屏幕截图

python 复制代码
driver.get_screenshot_as_file(filename)

注意事项:使用时,必须先要创建目录,不会自动创建目录。

python 复制代码
driver.get_screenshot_as_file("../imgs/screenshot.png")

3.5.4、获取网络状态

python 复制代码
driver.network_connection  # 获取手机网络类型

|-------------------|----------|----------|-------------------|
| Value(Alias) | Data | Wifi | Airplane Mode |
| 0(None) | 0 | 0 | 0 |
| 1(Airplane Mode) | 0 | 0 | 1 |
| 2(Wifi only) | 0 | 1 | 0 |
| 4(Data only) | 1 | 0 | 0 |
| 6(All network on) | 1 | 1 | 0 |

3.5.5、手机按键操作

python 复制代码
driver.press_keycode(keycode)  # 手机默认键码

键码表

|-------------|--------|-------------|--------|-------------|--------|
| keycode | 说明 | keycode | 说明 | keycode | 说明 |
| 3 | home键 | 4 | 返回键 | 24 | 音量增加键 |
| 25 | 音量减小键 | 26 | 电源键 | 66 | 回车键 |

3.5.6、通知栏操作

  1. 打开通知栏的操作就是从顶部下滑手机屏幕,显示信息栏。
  2. 但是没有关闭操作,可以自定屏幕往上滑或按返回键。
python 复制代码
driver.open_notifications()  # 打开通知栏

3.5.7、获取toast信息

  1. Toast是Android系统的轻量级提示(显示时间短、无焦点、无法通过常规控件定位)。
  2. Appium定位Toast需依赖 UiAutomator2 引擎 + XPath 文本匹配,核心是利用Toast的系统属性和文本特征。
  3. 注意:必须在初始化中加入:automationName="UiAutomator2"。
    EC导包:from selenium.webdriver.support import expected_conditions as EC
python 复制代码
toast = (WebDriverWait(driver, timeout=10, poll_frequency=0.1)
         .until(EC.presence_of_element_located((By.XPATH, "//android.widget.toast[@text='登录成功']"))))
print("捕获到toast文本:", toast.text)

四、KDT封装

相关推荐
凌盛羽2 小时前
用Python非常流行的openpyxl库对Excel(.xlsx格式)文件进行创建、读取、写入、显示等操作
数据库·python·链表·excel
编织幻境的妖2 小时前
Python对象序列化和反序列化方法总结
开发语言·python
Cherry的跨界思维2 小时前
8、Python正则表达式精准搜索实战:从模糊匹配到精准定位
开发语言·python·正则表达式·django·flask·pygame·tornado
软件开发技术深度爱好者2 小时前
Python + Ursina设计3D小游戏
开发语言·python
清静诗意2 小时前
Django REST Framework(DRF)PATCH 方法部分更新全解析与实战
后端·python·django
黑客思维者2 小时前
Python 3.14(2025最新版)的核心语法特性分析
服务器·开发语言·python·多线程
每日出拳老爷子2 小时前
[Python自动化] 用 Python + Selenium 做一个“浏览器重复操作录制器”:录一次,自动点一百次(附GUI+源码)
python·selenium·自动化
阿蔹2 小时前
Selenium
软件测试·selenium·测试工具·自动化
Aspect of twilight2 小时前
LeetCode华为2025年秋招AI大模型岗刷题(三)
python·算法·leetcode