Web自动化实践

发表于:2021-5-07 09:29

字体: | 上一篇 | 下一篇 | 我要投稿

 作者:桃子    来源:51Testing软件测试网原创

  本文主要内容包括以下几个功能的实现:
  ·文章发布
  ·删除单条文章用例
  ·删除所有文章用例
  ·添加ID标签实现元素定位
  ·登录功能验证码识别

  添加文章
  添加文章页面:

  实现思路:
  用例设计:包括添加成功和添加失败两条case。
  1.元素定位
  2.写标题->内容->点击发布
  3.验证:toast弹窗文本内容正确
  脚本实现:
from selenium.webdriver import ActionChains 
from selenium.webdriver.common.by import By 
from selenium.webdriver.support.wait import WebDriverWait 
from selenium.webdriver.support import expected_conditions as EC 
from time import sleep 
 
from basic.admin_login import Test_admin_login 
 
class TestArticle(object): 
    def __init__(self, login): 
        self.login = login 
 
    # 测试添加文章 
    def test_add_ok(self): 
        title = '我的文章' 
        content = '我的文章内容' 
        expected = '文章保存成功。' 
        #定位左侧文章列表 
        #文章 
        self.login.driver.find_element_by_xpath('//*[@id="sidebar-menu"]/li[4]/a/span[1]').click() 
        sleep(1) 
        #文章管理 
        self.login.driver.find_element_by_xpath('//*[@id="sidebar-menu"]/li[4]/ul/li[1]/a').click() 
        sleep(1) 
        #新建 
        self.login.driver.find_element_by_xpath('/html/body/div/div/section[3]/div/div/div/div[1]/div/div/a').click() 
        sleep(1) 
 
        #定位文章区域 
        #标题 
        self.login.driver.find_element_by_id('article-title').send_keys(title) 
        sleep(1) 
        #进入iframe 
        frame1=self.login.driver.find_element_by_xpath('//*[@id="cke_1_contents"]/iframe') 
 
        self.login.driver.switch_to.frame(frame1) 
        sleep(1) 
        #文章内容 
        self.login.driver.find_element_by_xpath('/html/body').send_keys(content) 
        #退出frame 
        self.login.driver.switch_to.default_content() 
        #发布按钮 
        self.login.driver.find_element_by_class_name('btn-primary').click() 
    #toast定位 
        loc=(By.CLASS_NAME,"toast-message") 
        #等待toast出现 
        WebDriverWait(self.login.driver,5).until(EC.visibility_of_element_located(loc)) 
        #toast文本 
        message=self.login.driver.find_element(*loc).text 
        #断言判断toast文本和期望值相等 
        assert message==expected

  注意点:
  1.frame弹窗的切入切出
  2.文章内容定位页面检查时到/html,需要自己手动添加到body下'/html/body'
  3.发送失败toast弹窗消失很快,可以多次点击几下定位

  删除单条文章用例
  删除文章页面:

  实现思路:
  用例设计:删除成功。
  1.鼠标悬停在文章标题
  2.点击垃圾箱
  3.验证:验证删除后文章数=删除前文章数-1
  脚本实现:
article.py
    # 测试删除单篇文章
    def test_delete_one_article_ok(self):
        # 文章管理
        self.login.driver.find_element_by_xpath('//*[@id="sidebar-menu"]/li[4]/ul/li[1]/a').click()
        sleep(1)
        #删除前文章数
        beforenumber=len(self.login.driver.find_elements_by_class_name('jp-actiontr'))
        #鼠标悬停文章内容
        a=self.login.driver.find_element_by_xpath('/html/body/div/div/section[3]/div/div/div/div[2]/table/tbody/tr[2]/td[2]/strong/a')
        ActionChains(self.login.driver).move_to_element(a).perform()
        #删除
        self.login.driver.find_element_by_xpath('/html/body/div/div/section[3]/div/div/div/div[2]/table/tbody/tr[2]/td[2]/div/div/a[3]').click()
        sleep(1)
        #删除后文章数
        afternumber=len(self.login.driver.find_elements_by_class_name('jp-actiontr'))
        #验证删除后文章数=删除前文章数-1
        assert beforenumber==afternumber+1

  技术难点:
  1.鼠标悬停操作:
ActionChains(self.login.driver).movetoelement(a).perform()

  2.文章数目使用len()函数确认
  3.所有文章数目确认通过self.login.driver.findelementsbyclassname定位一组elements确认

  删除所有文章用例
  删除所有文章页面:

  实现思路:
  用例设计:删除成功。
  1.点击全选复选框
  2.点击批量删除
  3.验证:验证文章数目=0
  实现脚本:
# 测试删除所有文章
    def test_delete_all_article_ok(self):
        #文章管理
        self.login.driver.find_element_by_xpath('//*[@id="sidebar-menu"]/li[4]/ul/li[1]/a').click()
        #点击全部复选框
        self.login.driver.find_element_by_xpath('/html/body/div/div/section[3]/div/div/div/div[2]/table/tbody/tr[1]/th[1]/input').click()
        sleep(1)
        self.login.driver.find_element_by_id('batchDel').click()
        sleep(1)
        WebDriverWait(self.login.driver,5).until(EC.alert_is_present())
        alert = self.login.driver.switch_to.alert
        alert.accept()
        sleep(1)
        #文章数目=0
        afternumber = len(self.login.driver.find_elements_by_class_name('jp-actiontr'))
        sleep(1)
        assert afternumber==0
if __name__ == '__main__':
    login = Test_admin_login()
    login.login_success()
    testArticle = TestArticle(login)
    testArticle.test_add_ok()
    #testArticle.test_delete_one_article_ok()
    testArticle.test_delete_all_article_ok()

  总结:
  通过上面我们可以发现,自动化用例的实现及用例和功能测试用例基本上是一样的,相同的操作步骤,相同的验证方法。只不过是通过脚本的方式展现出来,通过下面的表格再次加深一下印象。

  添加ID标签实现元素定位
  问题情境:
  在本地环境util工具类里有一个封装好的图片验证码类,实现识别图片中的验证码,需要传入参数id。
  但前端页面没有id属性,需要添加一个id属性,如下图:

  那么,怎么样才能向前端页面添加属性值呢?这里我们使用JS语法。
  添加id的思路如下:
  首先,通过上图的img标签找到要处理的HTML元素;
  然后,操作这个元素,通过setAttribute添加属性及属性值;
  注意:js脚本需要放到一个变量中,然后通过self.driver.execute_script(js)执行脚本。
  实现脚本:
js="document.getElementsByTagName('img')[0].setAttribute('id','captchaimg')"
self.driver.execute_script(js)

  验证是否添加成功:
  1.Chrome浏览器F12,找到console,输入脚本:
document.getElementsByTagName('img')[0].setAttribute('id','captchaimg')


  2.返回element tab下,查看存在id属性如下图:

  上面获取元素的方法除了标签名称还有其他方式如:
  ·getElementById()
  ·getElementByName()
  ·getElementByTagName()
  ·getElementByClassName()
  至于何种方法可以根据源码查看,源码有什么用什么方法。

  报错信息
javascript error: Cannot read property 'setAttribute' of undefined

  数组越界
  源代码:
js="document.getElementsByTagName('img')[1].setAttribute('id','captchaimg')"

  文档中一共有一个img标签,下标从0开始,所以将1改为0。
  修改后:
js="document.getElementsByTagName('img')[0].setAttribute('id','captchaimg')"

  上面提供一种处理问题的思路,当我们需要某种元素标签时,并且这种标签不存在的情况下我们可以自己利用js语法添加标签并实现调用。
  同时,在遇到selenium本身语法无法解决的问题,可以借助js脚本完成,比如页面上下滑动、处理时间空间等等。

  登录功能验证码识别
  一般web网站登录页面都会有验证码识别功能 ,如果是公司内部测试,可以让开发人员通过屏蔽验证码或者留后门方式轻松跳过,大可不必把时间浪费在验证码识别上。
  但是,大部分小伙伴一般刚开始接触自动化时都是自己找的项目,基本上述两种方法不适用。
  下面推荐两种常用的验证码识别方式:
  第一种OCR自动识别方式,缺点较复杂的验证码识别不出来。
  第二种,第三方API使用,我这里使用的是打码平台的,除此之外百度识别或者万维易源(缺点:调用繁琐、费用较高)。
  场景:识别下图的验证码。

  OCR自动识别的原理
  在这里我们需要使用pytesseract,它是一款用于光学字符识别(OCR)的python工具,即从图片中识别出其中嵌入的文字。
  整个过程分为截取登录页面->获取验证码的位置坐标->打开截图->从截图中截取验证码的区域->使用pytesseract工具识别验证码,这里直接使用pytesseract转换介绍。
  1.安装Pillow
pip install Pillow

  2.安装pytesseract
pip install pytesseract

  3.实现代码
from PIL import Image  导入Image函数
import pytesseract  导入pytesseract
def get_file_content(filePath):
    # 3.验证码处理-使用OCR自动识别
    qq = Image.open("D://software//project//jpress//testcases//basic//test.png")  # 打开jpg验证码图片
    text = pytesseract.image_to_string(qq).strip()

  运行查看结果返回为空,所以说这种方法对于简单的验证码还可以,复杂一点的可以直接放弃。

  第三方API接口
  打码平台链接地址:
  http://www.ttshitu.com/docs/index.html?spm=null
  首先需要注册一个账号,其次充值,1块钱够用挺长时间,找到对应的语言(如python),拷贝代码:



版权声明:本文出自《51测试天地》第六十一期。51Testing软件测试网及相关内容提供者拥有51testing.com内容的全部版权,未经明确的书面许可,任何人或单位不得对本网站内容复制、转载或进行镜像,否则将追究法律责任
《2023软件测试行业现状调查报告》独家发布~

关注51Testing

联系我们

快捷面板 站点地图 联系我们 广告服务 关于我们 站长统计 发展历程

法律顾问:上海兰迪律师事务所 项棋律师
版权所有 上海博为峰软件技术股份有限公司 Copyright©51testing.com 2003-2024
投诉及意见反馈:webmaster@51testing.com; 业务联系:service@51testing.com 021-64471599-8017

沪ICP备05003035号

沪公网安备 31010102002173号