web自动化测试进阶篇05 ——— 界面交互场景测试
😏作者简介:博主是一位测试管理者,同时也是一名对外企业兼职讲师。
📡主页地址:【Austin_zhai】
🙆目的与景愿:旨在于能帮助更多的测试行业人员提升软硬技能,分享行业相关最新信息。
💎声明:博主日常工作较为繁忙,文章会不定期更新,各类行业或职场问题欢迎大家私信,有空必回。

阅读目录
- 1. 目的
- 2. 作用
- 3. 实操
- 3.1 场景介绍与拆分
- 3.2 GWT表设计
- 3.3 代码设计
- 4. 后话
1. 目的
界面交互作为黑盒测试内容中重要的一环,在广大的测试人员群体中几乎成了入行的第一个接触内容,执行测试任务时站在客户角的度出发是每个测试人员都必须做到的基本条件,而模拟客户的日常业务操作,界面交互操作就成为了重中之重。同样的在自动化测试中,我们该如何更好的将界面交互操作融入到实际的自动化测试代码和框架中呢,今天博主就带着大家来看一看界面交互的一些进阶设计方法。
2. 作用
那么在自动化测试中界面交互具体的实际意义有哪些呢?首先从业务层面来看,测试人员为了更接近真实用户的日常业务行为,必定需要设计一系列的对应界面交互操作,因为复杂交互测试会涉及多个元素之间的复杂交互和页面状态的变化,更接近真实用户在web被测对象中的实际操作,比起无计划的胡乱操作,通过特定的界面交互操作可以有效的模拟用户实际的使用场景,从而更全面地验证应用程序的功能和用户体验。那么与之相呼应的就是一旦形成有明确目的性的界面交互操作规划之后,该功能模块的测试覆盖率自然而然的就会被提升上来,我们所熟知的界面交互,除了一些组件的操作之外,动态内容、异步请求、页面跳转、弹出框交互等等也是经常会涉及到。有了这些元素的交叉与组合,测试人员就可以发现更多的潜在问题,从而提高测试的覆盖率。
另外,除了界面的基础交互之外,数据的交换(前端与后端的逻辑处理)同样也可以借由界面交互的检查来进行验证。当然,这需要之前的有效交互操作规划来作为大前提。比如通过数据表单提交和后台数据的处理,可以验证前后端数据的传递是否正确,这样的场景相信大家应该都不会陌生,那么如何有效的排列组合各类的表单提交与数据检查就成为了是否成功执行该类测试场景的核心因素之一。
3. 实操
好了,以上是对于界面交互的一些大致内容进行了一些了解,那我们接下来以一个实际的业务案例来进行界面交互在自动化测试中的应用方法。
3.1 场景介绍与拆分
测试业务场景:某金融系统中,用户希望申请一笔贷款。贷款申请涉及填写个人信息、选择贷款产品、填写贷款金额、选择还款期限、上传必要资料等步骤,同时系统会根据用户信息和贷款产品进行额度计算和还款计划展示。在申请过程中,可能会遇到不同的验证和提示信息,用户需要正确填写和处理各项信息,以成功提交贷款申请。
那接下来我们将业务场景进行最基本的业务流步骤拆解,这与我们设计测试代码的覆盖范围与执行步骤、界面交互有很重要的联系,所以拆解需要尽量的清晰与简洁。
- 用户登录金融系统账户。
- 导航到贷款申请页面。
- 填写个人信息,包括姓名、身份证号、手机号等,并进行格式验证。
- 选择贷款产品类型,例如个人消费贷款、车辆抵押贷款等。
- 填写贷款金额,并验证金额范围。
- 选择还款期限,例如12个月、24个月等,并验证还款期限与贷款产品的对应关系。
- 上传必要资料,例如身份证扫描件、工资单等,验证上传的文件格式和大小。
- 系统进行额度计算和还款计划展示,并与预期结果进行对比。
- 处理风险提示,如还款风险、借贷条款等,确认并同意。
- 提交贷款申请。
- 验证贷款申请状态,确保申请成功。
对应的预期结果
- 用户能够成功登录账户并导航到贷款申请页面。
- 用户填写的个人信息和贷款信息符合格式和范围要求。
- 贷款额度计算和还款计划展示与预期结果一致。
- 用户成功提交贷款申请,并能够查看申请状态。
3.2 GWT表设计
基于以上的业务场景与步骤拆解,我们已经可以明确的看到其中的对应测试范围与功能点了,那么在此基础上我们就可以将以上这些进行系统的输出,形成对应的测试故事了。
场景:用户进行普通贷款申请
场景描述: 作为贷款申请者,用户希望能够成功申请一笔贷款,从而展开的一系列申请业务所需步骤。
Given:
用户已经登录到自己的金融账户
用户还未进行对应的信息登记(姓名、身份证号、手机号)
用户所拥有的所有认证信息均有效且登记成功
When:
用户进入贷款申请页面
用户使用有效的个人信息填写表单
用户选择一种贷款产品类型
用户输入符合允许范围的贷款金额
用户选择有效还款期限
用户上传必要的文件
Then:
被测对象应该计算贷款金额并展示还款计划
用户查看并接受贷款条款和条件
用户提交贷款申请
用户应该看到他的贷款申请状态为成功
3.3 代码设计
当我们整理出以上的这些信息之后,就可以正式的开始设计对应的测试代码了,当然这里只是简单的演示传统业务下我们该如何将界面交互测试的内容融入自动化测试框架中,其中的很多步骤(测试用例的设计,代码的单元测试,优化迭代)这里碍于篇幅就不展开细说了,有疑问的可以留言或私信博主。
与大部分的UI自动化测试框架一样,我们可以将需要测试的业务部分拆分成三部分,base、page_objects、test_loan_application分别对应三个python脚本,base就不用多说了,一些基础驱动方法都是放在这里面的,page_objects看到名字就知道我们基于PO模式将页面的元素封装在这里面,而test_loan_application当然就是我们的测试用例啦。
话不多说,我们先来设计base脚本:
from selenium import webdriver
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as ECclass BasePage:def __init__(self, driver):self.driver = driverdef wait_for_element_to_be_visible(self, by, locator, timeout=10):wait = WebDriverWait(self.driver, timeout)return wait.until(EC.visibility_of_element_located((by, locator)))class BaseTest:@classmethoddef setUpClass(cls):cls.driver = webdriver.Chrome()cls.driver.implicitly_wait(5)cls.driver.maximize_window()@classmethoddef tearDownClass(cls):cls.driver.quit()
base脚本没什么好多说的,属于是常规操作了,需要说明的就是base中加入了对应异步通信的显式等待,这个大家见仁见智,自由发挥即可。接下来是page_objects,页面上的可见对象(测试对象)包括一些常见组件(按钮、下拉框等)全部封装在其中,方便后续的测试用例中的复用。
from selenium.webdriver.common.by import By
from base import BasePageclass LoginPage(BasePage):def __init__(self, driver):super().__init__(driver)self.username_input = (By.ID, "username")self.password_input = (By.ID, "password")self.login_button = (By.ID, "login_button")def login(self, username, password):self.driver.get("https://example-bank.com/login")self.driver.find_element(*self.username_input).send_keys(username)self.driver.find_element(*self.password_input).send_keys(password)self.driver.find_element(*self.login_button).click()class LoanApplicationPage(BasePage):def __init__(self, driver):super().__init__(driver)self.product_type_dropdown = (By.ID, "product_type")self.loan_amount_input = (By.ID, "loan_amount")self.repayment_period_dropdown = (By.ID, "repayment_period")self.upload_file_input = (By.ID, "upload_file")self.submit_button = (By.ID, "submit_button")def apply_for_loan(self, product_type, loan_amount, repayment_period, file_path):self.driver.get("https://example-bank.com/loan_application")self.driver.find_element(*self.product_type_dropdown).send_keys(product_type)self.driver.find_element(*self.loan_amount_input).send_keys(loan_amount)self.driver.find_element(*self.repayment_period_dropdown).send_keys(repayment_period)self.driver.find_element(*self.upload_file_input).send_keys(file_path)self.driver.find_element(*self.submit_button).click()def click_calculate_button(self):calculate_button = self.wait_for_element_to_be_visible(By.ID, "calculate_button")calculate_button.click()def select_repayment_period(self, period):repayment_period_dropdown = self.wait_for_element_to_be_visible(By.ID, "repayment_period")select = Select(repayment_period_dropdown)select.select_by_visible_text(period)def accept_risk_warning(self):accept_button = self.wait_for_element_to_be_visible(By.ID, "accept_button")accept_button.click()def risk_assessment(self):assessment_button = self.wait_for_element_to_be_visible(By.ID, "assessment_button")assessment_button.click()
在test_loan_application中,我们主要对测试额度计算、还款计划展示、贷款的申请结果进行断言,在断言之前我们针对业务流程进行对应的界面交互操作,当然真实的业务肯定远远不止如此,大家只需要理解如何封装各类组件并在用例中有计划的调用即可。
import unittest
from base import BaseTest
from page_objects import LoginPage, LoanApplicationPageclass TestLoanApplication(BaseTest):def test_loan_application(self):login_page = LoginPage(self.driver)login_page.login("testuser", "testpass")loan_application_page = LoanApplicationPage(self.driver)loan_application_page.apply_for_loan("Personal Loan", "5000", "12 months", "path/to/uploaded/file.pdf")# 添加异步通信和显式等待,等待贷款申请状态显示并验证loan_application_page.wait_for_element_to_be_visible(By.ID, "loan_application_status", timeout=20)status = self.driver.find_element(By.ID, "loan_application_status").textassert "Successful" in status, "贷款申请状态错误"# 测试额度计算和还款计划展示loan_amount = "5000"repayment_period = "12 months"expected_loan_amount = "5000"expected_repayment_plan = "Monthly Installments: 12\nAmount per Installment: 416.67"loan_application_page.fill_loan_amount_and_repayment_period(loan_amount, repayment_period)loan_application_page.click_calculate_button()loan_application_page.wait_for_element_to_be_visible(By.ID, "calculated_loan_amount", timeout=10)calculated_loan_amount = self.driver.find_element(By.ID, "calculated_loan_amount").textassert calculated_loan_amount == expected_loan_amount, "额度计算错误"repayment_plan = self.driver.find_element(By.ID, "repayment_plan").textassert repayment_plan == expected_repayment_plan, "还款计划展示错误"# 处理风险提示risk_warning = loan_application_page.get_risk_warning_text()if risk_warning:loan_application_page.accept_risk_warning()else:# 如果没有风险提示,进行投资风险评估loan_application_page.risk_assessment()# 选择还款期限new_repayment_period = "24 months"loan_application_page.select_repayment_period(new_repayment_period)# 提交贷款申请loan_application_page.submit_loan_application()loan_application_page.wait_for_element_to_be_visible(By.ID, "loan_application_status", timeout=20)status = self.driver.find_element(By.ID, "loan_application_status").textassert "Successful" in status, "贷款申请状态错误"if __name__ == "__main__":unittest.main()
4. 后话
看完以上的这个实操例子之后不知道对大家是否有所启发,其实不是说一定要用以上的方法来进行测试任务的拆解,在这里只想告诉大家,在自动化UI测试中,面对界面交互场景的测试时,我们需要有计划的对界面交互操作进行设计与实施,至于方法,这里只是给出了其中的一种思路而已,相信大家在日后的工作中一定会整理总结出适用与自己与团队的一套设计与执行的方法。
相关文章:

web自动化测试进阶篇05 ——— 界面交互场景测试
😏作者简介:博主是一位测试管理者,同时也是一名对外企业兼职讲师。 📡主页地址:【Austin_zhai】 🙆目的与景愿:旨在于能帮助更多的测试行业人员提升软硬技能,分享行业相关最新信息。…...

NICE-SLAM: Neural Implicit Scalable Encoding for SLAM论文阅读
论文信息 标题:NICE-SLAM: Neural Implicit Scalable Encoding for SLAM 作者:Zihan Zhu, Songyou Peng,Viktor Larsson — Zhejiang University 来源:CVPR 代码:https://pengsongyou.github.io/nice-slam…...

cmake 配置Visual studio的调试命令
配置代码如截图: set_property(TARGET ${TARGET_NAME} PROPERTY VS_DEBUGGER_COMMAND "./consoleTest.exe") set_property(TARGET ${TARGET_NAME} PROPERTY VS_DEBUGGER_COMMAND_ARGUMENTS "./config/labelDriver.cfg") set_propert…...

MPDIoU: A Loss for Efficient and Accurate Bounding BoxRegression--论文学习笔记
超越GIoU/DIoU/CIoU/EIoU MPDIoU让YOLOv7和YOLACT双双涨点 目标检测上的指标对比: 论文地址: [2307.07662] MPDIoU: A Loss for Efficient and Accurate Bounding Box Regression (arxiv.org) 摘要 边界框回归(Bounding Box Regression&am…...

【Uniapp 的APP热更新】
Uniapp 的APP热更新功能依赖于其打包工具 HBuilder,具体步骤如下: 1. 在 HBuilder 中构建并打包出应用程序 具体步骤: 1.点击发行,点击制作wgt包 2.根据需求修改文件储存路径和其他配置,点击确定 3.等待打包完成&a…...

MySQL主从复制配置
Mysql的主从复制至少是需要两个Mysql的服务,当然Mysql的服务是可以分布在不同的服务器上,也可以在一台服务器上启动多个服务。 (1)首先确保主从服务器上的Mysql版本相同 (2)在主服务器上,创建一个充许从数据库来访问的用户slave,密码为:123456 ,然后使用REPLICATION SLAV…...

Linux - 添加普通用户为信任用户
1.添加用户 在Linux系统中,可以使用以下步骤添加用户: 打开终端并以root用户身份登录 输入以下命令以创建新用户(请将username替换为您想要创建的用户名): adduser username 设置该用户的密码,使用以下命…...

flask----路由系统
# 1 flask路由系统是基于装饰器的:参数如下 # 2 转换器: # 3 路由系统本质 # 4 endpoint 不传会怎么样,不传会以视图函数的名字作为值,但是如果加了装饰器,所有视图函数名字都是inner,就会出错,使用wrapp…...

驶向专业:嵌入式开发在自动驾驶中的学习之道
导语: 自动驾驶技术在汽车行业中的快速发展为嵌入式开发领域带来了巨大的机遇。作为自动驾驶的核心组成部分,嵌入式开发在驱动汽车的智能化和自主性方面发挥着至关重要的作用。本文将探讨嵌入式开发的学习方向、途径以及未来在自动驾驶领域中的展望。 一、学习方向:…...

Go语言入门:从零开始的快速指南(一)
文章目录 引言Go语言的诞生背景Go 语言的特性安装Go语言环境集成开发环境安装第一个Go程序Go 源代码的特征解读 引言 Go语言(也称为Golang)是一种开源的、静态类型的编程语言,由Google开发。它的设计目标是简单、高效、安全、并且易于学习和…...

Windows7+内网, 安装高版本nodejs,使用vite+vue3+typescript开发项目
前言:vite只支持高版本的nodejs,而高版本的nodejs只支持windows8及以上,且vite还对浏览器版本有兼容问题。以下均为vite官网截图 1、安装好低版本的nodejs win7系统建议安装13.及以下,我的是12.12.0这个版本。nodejs低版本官网下载…...

【C语言day14】
#include<stdio.h>int fun(char* s) {char* t s;while (*t);return(t - s); }int main() {char s[] "abc";int n fun(s);printf("%d\n", n);//4return 0; }循环在*t为0时停止,同时t,t最后会停在字符串结束的’\0’之后的一…...

暑假刷题第19天--8/1
170. 加成序列 - AcWing题库(dfs迭代加深--重点理解) #include<iostream> using namespace std; int n; int a[11]; int dfs(int x,int h){if(x>h1)return 0;if(a[x-1]n)return 1;bool st[130]{};for(int i1;i<x-1;i){for(int j1;j<i;j)…...

Java开发中的------修改密码+忘记密码
目录 1.修改密码 客户端响应 前端vue 后端 controller层 ServiceImpl实现层 2.忘记密码 客户端响应 后端 controller层 serviceImpl实现层 本章需要准备:springcloud项目,依赖,数据库.... 数据库SQL SET FOREIGN_KEY_CHECKS0;-- -…...

ffmpeg安装
简介 FFmpeg是一个开源的音视频处理库,它提供了一系列的工具和API,可以用于处理音视频文件。你可以使用FFmpeg的命令行工具来执行各种音视频处理操作,比如转码、剪辑、合并等。FFmpeg的命令格式通常是:ffmpeg [全局选项] {[输入文…...

Mac电脑目录
System(系统)Applications(应用程序)应用程序目录,默认所有的GUI应用程序都安装在这里User(用户)存放用户的个人资料和配置。每个用户有自己的单独目录Library(资料库)系…...

一起学算法(栈篇)
1.栈的概念 1.栈的定义 栈是仅限在表尾进行插入和删除的线性表,栈又被称为先进后出的线性表,简称“LIFO” 我们这次用数组作为我们栈的底层数据结构,代码会放到结尾供大家参考使用 2.栈顶的定义 栈是一个线性表,我们允许插入…...

Ubuntu开机自启服务systemd.service配置教程(Ubuntu服务)(Linux服务)upstart
文章目录 为什么要将程序配置成服务?1. 自动启动2. 后台运行3. 定时重启4. 简化管理5. 整合系统 版本支持1. Ubuntu 14.04及更早版本:使用upstart作为默认的init系统/etc/rc.local旧版本新版本 2. Ubuntu 15.04到16.04版本:默认使用systemd作…...

大数据课程E4——Flume的Channel
文章作者邮箱:yugongshiye@sina.cn 地址:广东惠州 ▲ 本章节目的 ⚪ 了解Channel的作用和配置; ⚪ 掌握Channel的使用方法; ⚪ 掌握Channel的File Channel; ⚪ 掌握Channel的JDBC Channel; ⚪ 掌握Channel的Spillable Memory Channel; 一、Memory Ch…...

es6中的Map和Set数据结构
Map Map对象可以用于保存键值对 1.创建 一个Map对象 const map new Map() 2.Map的一些方法 set(key,value):通过键值对向Map对象中添加元素get(key):通过建拿到对应的值size:返回Map对象中所包含的键值对的个数has(key):判断Map对象中是否有对应的key,返回一个…...

MyBatis 框架基本的增删改查
提示:写代码要严谨 文章目录 前言前期准备MyBatis CRUD操作流程增加功能删除功能修改功能查询功能#{} 占位符${} 占位符两种占位符的区别❗ 映射文件总结❗ mapper 代理方式实现CRUDmapper代理开发规范增加功能删除功能修改功能查询功能 前言 提示:myba…...

Javascript--JSON
什么是 JSON? JavaScript中的JSON(JavaScript Object Notation)是一种轻量级的数据交换格式,用于存储和表示结构化的数据。JSON使用键值对的方式组织数据,并支持基本数据类型(字符串、数字、布尔值、数组和对象&…...

Rust: error: failed to run custom build command for `openssl-sys v0.9.71`
error: failed to run custom build command for openssl-sys v0.9.71 解决 windows : openssl 不要选Light版 设置环境变量 cmd: set OPENSSL_DIR“C:\Program Files\OpenSSL-Win64” OPENSSL_DIR:C:\Program Files\OpenSSL-Win64 linux:…...

Excel修改日期格式,改变日期的筛选方式
我们有两列日期数据: 左边这一列筛选会显示: 右边这一列筛选会显示: 修改格式,将【日期1】改为【日期2】 将【日期1】的格式修改为文本格式即可 修改格式,将【日期2】改为【日期1】 选中日期2,点击【数据…...

【RabbitMQ(day2)】默认(直连)交换机的应用
文章目录 一、第一种模型(Hello World)二、第二种模型(work queue)自动确认机制的后果和公平分配 三、阐述默认交换机 这篇博客是以下资料学后的总结: 不良人的RabbitMQ的教学视频 官方启动教程 RabbitMQ中文文档 一、…...

谷粒商城第八天-商品服务之品牌管理的整体实现(直接使用逆向生成的代码;含oss文件上传)
目录 一、总述 二、前端部分 2.1 创建好品牌管理菜单 2.2 复制组件 编辑2.3 复制api 编辑 2.4 查看效果 编辑2.5 需要优化的地方 2.6 具体优化实现 2.6.1 优化一:将表格的状态列(这里是是否显示列)修改为开关ÿ…...

阿里云率先荣获容器集群稳定性先进级认证
7 月 25 日,由中国信通院发起的“2023 稳保体系”评估结果在可信云大会现场公布,阿里云容器服务 ACK 成为首批通过“云服务稳定运行能力-容器集群稳定性”评估的产品,并荣获“先进级”认证。 云原生技术正在激活应用构建新范式,构…...

【SpringBoot笔记37】SpringBoot基于@ServerEndpoint、@OnMessage等注解的方式集成WebSocket
这篇文章,主要介绍SpringBoot基于@ServerEndpoint、@OnMessage等注解的方式集成WebSocket。 目录 一、基于注解集成WebSocket 1.1、WebSocket常见注解 1.2、创建WebSocket服务端 1.3、配置ServerEndpointExpor...

PyTorch(安装及卸载)
目录 1. 安装 2. 卸载 参考文献 为什么用PyTorch:简单来说,19年之前tensorflow是大哥,19年tensorflow和PyTorch双龙并行,20年之后PyTorch一往无前。宗旨,哪个用的人多用哪个。 1. 安装 1. 先打开Anaconda Prompt&…...

webScoket
webScoket是什么? 支持端对端通讯可以由客户端发起,也可以有服务端发起用于消息通知、直播间讨论区、聊天室、协同编辑等 做一个简单的webScoket 客户端配置: 1、新建一个页面叫web-scoket.html <!DOCTYPE html> <html lang"…...