使用yaml文件管理测试数据

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了使用yaml文件管理测试数据相关的知识,希望对你有一定的参考价值。

参考技术A 知道ddt的基本使用方法之后,练习把之前用excel文件来维护的接口测试用例改用unittest+ddt来实现。

这里我选用yaml文件来管理接口参数,开始本来想用json,但是json无法添加注释,可读性不好。

下面截图是接口文档中的各个接口,每个接口都有一个固定的序号,所以在设计每个接口的测试数据时,以序号来区分不同接口

yaml文件内容如下,需要注意的是yaml的语法:

(1)键值对用冒号分割,但是冒号后需要加一个空格

(2)禁止使用tab缩进,只能使用空格键;缩进长度没有限制,只要元素对齐就表示这些元素属于一个层级

(3)字符串可以不用引号标注,也可以加引号,如果想把数字变为字符串,加引号即可

(4)使用#表示注释

详情可以参考博客: https://blog.csdn.net/vincent_hbl/article/details/75411243

2. 简单 demo : python 读取 yaml 文件,取出接口参数

import yaml

fp = open('../dataconfig/信息互动模块接口.yaml', encoding='utf-8')   #有中文字符的话,加编码格式

                testdata = yaml.load(fp)

t = testdata['5.2.1.4']

print(t)

(1)封装读取yaml文件方法

handle_yaml.py

# coding: utf-8

# author: hmk

importyaml

importos

classHandleYaml:

    def __init__(self,file_path=None):

        if file_path:

           self.file_path = file_path

        else:

            root_dir =os.path.dirname(os.path.abspath('.'))

            # os.path.abspath('.')表示获取当前文件所在目录;os.path.dirname表示获取文件所在父目录;所以整个就是项目的所在路径self.file_path = root_dir +'/dataconfig/信息互动模块接口.yaml'  #获取文件所在的相对路径(相对整个项目)

        #elf.data = self.get_data()

    def get_data(self):

        fp =open(self.file_path, encoding='utf-8')

        data =yaml.load(fp)

        return data

if __name__ == '__main__':

    test = HandleYaml()

    p = test.get_data()

    print(p['5.2.1.1'])

[if !vml][endif]

(2)封装requests请求方法

[if !vml][endif]

# coding: utf-8

# author: Archer

importrequests

importjson

classRunMethod:

    defpost_main(self, url, data, header=None):if header is notNone:

             res =requests.post(url=url, data=data, headers=header)

        else:

            res =requests.post(url=url, data=data)

        # print(res.status_code)

        # return res.json()

        return res    #为了方便后面断言,这里不再对服务器响应进行json格式编码

def get_main(self, url, data=None, header=None):if header is notNone:

            res =requests.get(url=url, params=data, headers=header)

        else:

            res =requests.get(url=url, params=data)

            print(res.status_code)

        # return

res.json()

        return res

    def run_main(self, method, url, data=None, header=None):

    if method== 'POST':

            res =self.post_main(url, data, header)

        else:

            res =self.get_main(url, data, header)

        returnres

        # returnjson.dumps(res, indent=2, sort_keys=False, ensure_ascii=False)  #使用json模块格式化显示结果

[if !vml][endif]

(3)一个接口测试用例

[if !vml][endif]

# coding: utf-8

# author: Archer

importunittest

importddt

from base.run_method importRunMethod

from utils.handle_yaml importHandleYaml

get_data = HandleYaml()  # 从yaml文件中取出该接口的参数

params = get_data.get_data()['5.2.1.4']

@ddt.ddt

classTest(unittest.TestCase):

    """加载咨询详情接口"""

    defsetUp(self):

        self.url ='http://localhost:8088/ApprExclusiveInterface/api/enterprise/info/consult/loadDetail.v'

        self.run =RunMethod()

    @ddt.data(*params)

    deftest(self, value):

        r =self.run.run_main("GET", self.url, value)

        print(r)

       self.assertTrue(value['assert'] inr.text)

if __name__ == '__main__':

    unittest.main()

(4)利用htmlTestRunner生成测试报告

run_report.py

# coding: utf-8

# author: hmk

from HTMLTestRunner importHTMLTestRunner

importunittest

importtime, os

root_dir = os.path.dirname(os.path.abspath('.'))  # 获取当前文件所在目录的父目录的绝对路径,也就是项目所在路径E:\DDT_Interface

case_dir = root_dir + '/test_case/'  # 根据项目所在路径,找到用例所在的相对项目的路径

print(root_dir)

print(case_dir)

"""定义discover方法"""

discover = unittest.defaultTestLoader.discover(case_dir,

pattern='test*.py', top_level_dir=None)

"""

1.case_dir即测试用例所在目录

2.pattern='test_*.py' :表示用例文件名的匹配原则,“*”表示任意多个字符

3.top_level_dir=None:测试模块的顶层目录。如果没顶层目录(也就是说测试用例不是放在多级目录中),默认为None

"""

if __name__ == "__main__":

    """直接加载discover"""

    now = time.strftime("%Y-%m-%d%H_%M_%S")

    filename = root_dir +'/report/' + now + '_result.html'  #定义报告存放路径

    print(filename)

    fp = open(filename,'wb')

    runner =HTMLTestRunner(stream=fp, title='个人网企业网接口测试报告', description='测试结果如下: ')

    runner.run(discover)

    fp.close()

ok ,unittest+ddt进行接口测试就完成了,还有很多不足,yaml配置文件还可以继续设计优化,例如可以把请求url也加进去。

其实感觉如何设计测试用例,组织测试数据也是一件很有意思的事情,很多事情都必须先有一个良好的设计思路才会进行的更顺畅。总之勤于思考,多参考他人的思路。不是有句话吗,学而不思则罔,思而不学则殆。

python+appium+yaml安卓UI自动化测试分享

一、实现数据与代码分离,维护成本较低,先看看自动化结构,大体如下:

技术图片

  • testyaml管理用例,实现数据与代码分离,一个模块一个文件夹

  • public 存放公共文件,如读取配置文件、启动appium服务、读取Yaml文件、定义日志格式等

  • page 存放最小测试用例集,一个模块一个文件夹

  • results 存放测试报告及失败截图

  • testcase 存放测试用例
  • runtest.py 运行所有测试用例

运行的结果:

技术图片

三、yaml格式介绍

  • element_info:定位元素信息

  • find_type:属性,id、xpath、text、ids

  • operate_type: click、wait_activity、send_keys、back、swipe_up、sleep、clickbox(有弹框就关闭,没有就跳过),check(经常预期结果),暂时就八种

    上面三个必填,operate_type必填!!!!!!

  • send_content:send_keys 时用到

  • index:ids时用到  (定位是复式的时候可以索引)

  • times: 返回次数或者上滑次数

技术图片

代码部分

公共部分

个人觉得核心的就是公共部分,相当于建房子,公共部分搞好了,后面仅仅是调用即可,建房子把架子搭好,后面就添砖加瓦吧。

读取配置文件readconfig.py
设置日志格式logs.py
获取设备GetDevices.py
这几个通用的就不做介绍了

  • 读取yaml文件 GetYaml.py
  • #coding=utf-8
    #author=‘Shichao-Dong‘
    
    import sys
    reload(sys)
    sys.setdefaultencoding(utf8)  #设置编码格式
    import yaml
    import codecs
    import random
    from random import choice
    
    def rand( total, num):
        ‘‘‘生成不重复的随机数,total总数,num生成的个数‘‘‘
        li = [i for i in range(total)]
        res = []
        for i in range(num):
            t = random.randint(i, total - 1)
            res.append(li[t])
            li[t], li[i] = li[i], li[t]
        return res
    def random_phonenumber():
        # 生成随机手机号码
        area_num = 399999
        # area_number = choice(area_num)
        seed = "1234567890"
        sa = []
        for i in range(6):
            sa.append(choice(seed))
        last_eightnumber = ‘‘.join(sa)
        phone = str(area_num) + last_eightnumber
        return phone
    
    
    class getyaml:
        def __init__(self,path):
            self.path = path
    
        def getYaml(self):
            ‘‘‘
            读取yaml文件
            :param path: 文件路径
            :return:
            ‘‘‘
            try:
                f = open(self.path)
                data =yaml.load(f)
                f.close()
                return data
            except Exception:
                print(u"未找到yaml文件")
    
        def alldata(self):
            ‘‘‘
            获取yaml里面所有的数据
            :return:
            ‘‘‘
            data =self.getYaml()
            return data
    
        def caselen(self):
            ‘‘‘
            获取元素定位的个数
            :return:
            ‘‘‘
            data = self.alldata()
            length = len(data[testcase])
            return length
    
        def get_elementinfo(self,i):
            ‘‘‘
            获取yaml里面的element_info
            i:想要获取的索引
            :param i:
            :return:
            ‘‘‘
            data = self.alldata()
            # print data[‘testcase‘][i][‘element_info‘]
            return data[testcase][i][element_info]
    
        def get_findtype(self,i):
            ‘‘‘
           获取yaml里面的find_type
           i:想要获取的索引
           :param i:
           :return:
           ‘‘‘
            data = self.alldata()
            # print data[‘testcase‘][i][‘find_type‘]
            return data[testcase][i][find_type]
    
        def get_operate_type(self,i):
            ‘‘‘
           获取yaml里面的operate_type
           i:想要获取的索引
           :param i:
           :return:
           ‘‘‘
            data = self.alldata()
            # print data[‘testcase‘][i][‘operate_type‘]
            return data[testcase][i][operate_type]
    
        def get_index(self, i):
            ‘‘‘
              获取yaml里面的operate_type
              i:想要获取的索引
              :param i:
              :return:
              ‘‘‘
            data = self.alldata()
            if self.get_findtype(i) == ids:
                 text_yaml = data[testcase][i][index]
                 if  str(text_yaml) == listtext:
                     list_text = rand(10,5)
                     return list_text
                 elif str(text_yaml) == random:
                     list_text = random.randint(1, 10)
                     return list_text
                 else:
                     return text_yaml
            if self.get_findtype(i) == class_name:
                text_yaml = data[testcase][i][index]
                if str(text_yaml) == listtext:
                    list_text = rand(10, 5)
                    return list_text
                elif str(text_yaml) == random:
                    list_text = random.randint(1, 10)
                    return list_text
                else:
                    return text_yaml
            else:
                pass
    
        def get_send_content(self,i):
            ‘‘‘
             获取yaml里面的send_content
             i:想要获取的索引
             :param i:
             :return:
             ‘‘‘
            data = self.alldata()
            # print data[‘testcase‘][i][‘send_content‘]
            if self.get_operate_type(i) == send_keys:
                 text_yaml  = data[testcase][i][send_content]
                 if str(text_yaml) == phone_number:
                     text = random_phonenumber()
                     return str(text)
                 elif str(text_yaml) == random:
                     text = random.randint(1, 10)
                     return text
                 else:
                    # text = text_yaml.decode(‘utf-8‘)
                    return str(text_yaml)
            else:
                pass
    
        def get_sleeptime(self, i):
            ‘‘‘
           获取yaml里面的operate_type
           i:想要获取的索引
           :param i:
           :return:
           ‘‘‘
            data = self.alldata()
            # print data[‘testcase‘][i][‘operate_type‘]
            return data[testcase][i][sleeptime]
    
        def get_backtimes(self, i):
            data =  self.alldata()
            if self.get_operate_type(i)==back or self.get_operate_type(i)==swipe_up:
                return data[testcase][i][times]
            elif self.get_operate_type(i)==swipe_down:
                return data[testcase][i][times]
            elif self.get_operate_type(i)==swipe_left:
                return data[testcase][i][times]
            elif self.get_operate_type(i) == swipe_right:
                return data[testcase][i][times]
            else:
                pass
    
        def get_title(self):
            data = self.alldata()
            # print data[‘testinfo‘][0][‘title‘]
            return  data[testinfo][0][title]
    

     

  • 启动appium服务 StartAppiumServer.py
    主要是启动appium并返回端口port,这个port在下面的driver中需要
  • #coding=utf-8
    #author=‘Shichao-Dong‘
    
    from logs import log
    import random,time
    import platform
    import os
    from GetDevices import devices
    
    log = log()
    dev = devices().get_deviceName()
    
    
    class Sp:
        def __init__(self, device):
            self.device = device
    
        def __start_driver(self, aport, bpport):
            """
           3. 多设备执行
            1. 安卓下多设备执行意味着每一个设备需要对应一个appium服务端,并且脚本部分需要实现多线程访问,appium服务端启动命令如下:
            appium -p 4490 -bp 3456 -U xxxx
            -p 表示服务端和脚本通信的端口
            -bp 表示服务端和设备的AppiumBootStrap.jar进行通信的端口
            -U 表示当前服务是针对哪一台设备的
            2. ios在xcode8以下不支持多设备执行原因是instruments不支持多实例
            """
            if platform.system() == Windows:    #获取操作系统名称
                import subprocess
                subprocess.Popen("appium -p %s -bp %s -U %s" %(aport, bpport, self.device), shell=True)
    
    
    
        def start_appium(self):
            """
            启动appium
            p:appium port
            bp:bootstrap port
            :return: 返回appium端口参数
            """
            aport = random.randint(4700, 4900)
            bpport = random.randint(4700, 4900)
            self.__start_driver(aport, bpport)
    
            log.info( start appium :p %s bp %s device:%s %(aport, bpport, self.device))
            time.sleep(10)
            return aport
    
        def main(self):
            """
            :return: 启动appium
            """
            return self.start_appium()
    
    
        def stop_appium(self):
            ‘‘‘
            停止appium
            :return:
            ‘‘‘
            if platform.system() == Windows:
                os.popen("taskkill /f /im node.exe")
    
    
    if __name__ == __main__:
        s = Sp(dev)
        s.main()
    获取driver GetDriver.py
    platformName、deviceName、appPackage、appActivity这些卸载配置文件config.ini文件中,可以直接通过readconfig.py文件读取获得。
    appium_port有StartAppiumServer.py文件返回
  • #coding=utf-8
    #author=‘Shichao-Dong‘
    
    import time
    from appium import webdriver
    from selenium.common.exceptions import WebDriverException
    import readConfig
    import GetDevices
    from StartAppiumServer import Sp
    from logs import log
    import os
    
    log = log()
    conf = readConfig.Readconfig()
    
    platformName =conf.getConfigValue(platformName).encode(ascii)
    apppackage = conf.getConfigValue(appPackage).encode(ascii)
    appactivity = conf.getConfigValue(appactivity).encode(ascii)
    platformversion =conf.getConfigValue(platformversion).encode(ascii)
    devicename = conf.getConfigValue(devicename).encode(ascii)
    
    # s = Sp(devicename)
    # appium_port = s.main()   #启动appium
    
    def mydriver1():
        os.system(call adb shell input keyevent 82)
        desired_caps = {
                    platformName:platformName,
                    deviceName:devicename,
                    platformVersion:platformversion,
                    appPackage:apppackage,
                    appActivity:appactivity,
                    unicodeKeyboard:True,
                    resetKeyboard:True,
                    # ‘noReset‘:True,
                    newCommandTimeout:180
                    }
        try:
            driver = webdriver.Remote(http://127.0.0.1:4723/wd/hub, desired_caps)
            # driver = webdriver.Remote(‘http://127.0.0.1:%s/wd/hub‘%appium_port,desired_caps)
            time.sleep(4)
            log.info(获取driver成功)
            return driver
        except WebDriverException:
            print No driver
    
    def mydriver2():
        os.system(call adb shell input keyevent 82)
        desired_caps = {
                    platformName:platformName,
                    deviceName:devicename,
                    platformVersion:platformversion,
                    appPackage:apppackage,
                    appActivity:appactivity,
                    unicodeKeyboard:True,
                    resetKeyboard:True,
                    noReset:True,
                    newCommandTimeout:180
                    }
        try:
            driver = webdriver.Remote(http://127.0.0.1:4723/wd/hub, desired_caps)
            # driver = webdriver.Remote(‘http://127.0.0.1:%s/wd/hub‘%appium_port,desired_caps)
            time.sleep(4)
            log.info(获取driver成功)
            return driver
        except WebDriverException:
            print No driver

     

  • BaseOperate.py 重新封装find等命令,里面主要是一些上滑、返回、find等一些基础操作
  • #coding=utf-8
    #author=‘Shichao-Dong‘
    
    from selenium.webdriver.support.ui import WebDriverWait
    from appium.webdriver.webelement import WebElement
    from selenium.webdriver.support import expected_conditions
    from selenium.webdriver.common.by import By
    from logs import log
    import os
    import time
    import random
    from random import choice
    from appium.webdriver.mobilecommand import MobileCommand
    
    
    
    ‘‘‘
    一些基础操作:滑动、截图、点击页面元素等
    ‘‘‘
    
    log = log()
    # driver = GetDriver.mydriver()
    
    class BaseOperate:
        def __init__(self,driver):
            self.driver = driver
    
        def back(self):
            ‘‘‘
            返回键
            :return:
            ‘‘‘
            os.popen("adb shell input keyevent 4")
    
        def get_window_size(self):
            ‘‘‘
            :return:返回屏幕的大小
            ‘‘‘
            x=self.driver.get_window_size()[width]
            y=self.driver.get_window_size()[height]
            return(x,y)
    
        def swipe_up(self):
            ‘‘‘
            :return:向上滑动
            ‘‘‘
            try:
                l=self.get_window_size()
                x1=int(l[0]*0.5)
                y1=int(l[0]*0.9)
                y2=int(l[1]*0.2)
                self.driver.swipe(x1,y1,x1,y2,1000)
            except:
                log.error(u"上滑动异常")
    
        def swipe_down(self):
            ‘‘‘
            :return:向下滑动
            ‘‘‘
            try:
                l=self.get_window_size()
                x1=int(l[0]*0.5)
                y1=int(l[0]*0.2)
                y2=int(l[1]*0.8)
                self.driver.swipe(x1,y1,x1,y2,1000)
            except:
                log.error(u"下滑动异常")
    
        def swipe_right(self):
            ‘‘‘
            :return:向右滑动
            ‘‘‘
            try:
                l=self.get_window_size()
                x1=int(l[0]*0.2)
                x2=int(l[0]*0.8)
                y1=int(l[1]*0.5)
                self.driver.swipe(x1,y1,x2,y1,1000)
            except:
                log.error(u"右滑动异常")
    
        def swipe_left(self):
            ‘‘‘
            :return:向左滑动
            ‘‘‘
            try:
                l=self.get_window_size()
                x1=int(l[0]*0.8)
                x2=int(l[0]*0.2)
                y1=int(l[1]*0.5)
                self.driver.swipe(x1,y1,x2,y1,1000)
            except:
                log.error(u"左滑动异常")
    
        def screenshot(self):
            now=time.strftime("%y%m%d-%H-%M-%S")
            PATH = lambda p: os.path.abspath(os.path.join(os.path.dirname(__file__), p))
            screenshoot_path = PATH(../results/screenshoot/failpic)
            self.driver.get_screenshot_as_file(screenshoot_path+now+.png)
    
        def find_id(self,id):
            ‘‘‘
            寻找元素
            :return:
            ‘‘‘
            # 判断元素是否显示
            try:
                self.driver.find_element_by_id(id).is_enabled()
                return True
            except :
                # self.screenshot()
                return False
    
        def find_name(self,name):
            ‘‘‘
            判断页面是否存在某个元素
            :param name: text
            :return:
            ‘‘‘
            findname = "//*[@text=‘%s‘]"%(name)
            try:
                self.driver.find_element_by_xpath(findname).is_enabled()
                return True
            except :
                # self.screenshot()
                return False
    
    
        def get_name(self,name):
            ‘‘‘
            定位页面text元素
            :param name:
            :return:
            ‘‘‘
            findname = "//*[@text=‘%s‘]"%(name)
            try:
                # element = WebDriverWait(self.driver, 10).until(lambda x: x.find_element_by_xpath(findname))
                WebDriverWait(self.driver, 15).until(lambda driver: driver.find_element_by_xpath(findname).is_displayed())
                element = self.driver.find_element_by_xpath(findname)
                return element
            except:
                # self.screenshot()
                log.error(未定位到元素:+%s%(name))
    
        def getname_text(self,name):
            ‘‘‘
            定位页面text元素
            :param name:
            :return:
            ‘‘‘
            findname = "//*[@text=‘%s‘]"%(name)
            try:
                # element = WebDriverWait(self.driver, 10).until(lambda x: x.find_element_by_xpath(findname))
                WebDriverWait(self.driver, 15).until(lambda driver: driver.find_element_by_xpath(findname).is_displayed())
                element_text = self.driver.find_element_by_xpath(findname).text
                return element_text
            except:
                # self.screenshot()
                log.error(未定位到元素:+%s%(name))
    
        def getid_text(self,id):
            ‘‘‘
            定位页面resouce-id元素文本
            :param id:
            :return:
            ‘‘‘
            try:
                # element = WebDriverWait(self.driver, 10).until(lambda x: x.find_element_by_xpath(xpath))
                WebDriverWait(self.driver, 20).until(lambda driver: driver.find_element_by_id(id).is_displayed())
                element_text = self.driver.find_element_by_id(id).text
                return element_text
            except:
                # self.screenshot()
                # self.driver.get_screenshot_as_file("D:/error.png")
                log.error(未定位到元素:+%s%(id))
    
        def getids_text(self,id):
            ‘‘‘
            定位页面resouce-id元素组
            :param id:
            :return:列表
            ‘‘‘
            try:
                elements = WebDriverWait(self.driver, 20).until(lambda x: x.find_elements_by_id(id))
                self.driver.implicitly_wait(2)
                return elements
            except:
                # self.screenshot()
                log.error(未定位到元素:+%s%(id))
    
    
        def get_id(self,id):
            ‘‘‘
            定位页面resouce-id元素
            :param id:
            :return:
            ‘‘‘
            try:
                # element = WebDriverWait(self.driver, 10).until(lambda x: x.find_element_by_xpath(xpath))
                WebDriverWait(self.driver, 20).until(lambda driver: driver.find_element_by_id(id).is_displayed())
                element = self.driver.find_element_by_id(id)
                return element
            except:
                # self.screenshot()
                # self.driver.get_screenshot_as_file("D:/error.png")
                log.error(未定位到元素:+%s%(id))
    
        def get_id_closebox(self, id):
            ‘‘‘
            专门关闭弹框的
            :param id:
            :return:
            ‘‘‘
            try:
                # elements = self.driver.find_elements_by_id(id)
                element = WebDriverWait(self.driver, 20).until(lambda x: x.find_element_by_id(id))
                self.driver.implicitly_wait(2)
                return element
            except:
                pass
    
        def get_text_closebox(self, name):
            ‘‘‘
            专门关闭弹框的
            :param :text
            :return:
            ‘‘‘
            findname = "//*[@text=‘%s‘]" % (name)
            try:
                # element = WebDriverWait(self.driver, 10).until(lambda x: x.find_element_by_xpath(xpath))
                WebDriverWait(self.driver, 20).until(lambda driver: driver.find_element_by_id(findname).is_displayed())
                element = self.driver.find_element_by_id(findname)
                return element
            except:
                pass
    
        def get_xpath(self,xpath):
            ‘‘‘
            定位页面xpath元素
            :param id:
            :return:
            ‘‘‘
            try:
                # element = WebDriverWait(self.driver, 10).until(lambda x: x.find_element_by_xpath(xpath))
                WebDriverWait(self.driver, 20).until(lambda driver: driver.find_element_by_xpath(xpath).is_displayed())
                element = self.driver.find_element_by_xpath(xpath)
                return element
            except:
                # self.screenshot()
                log.error(未定位到元素:+%s%(xpath))
    
        def get_classname(self, classname):
            ‘‘‘
            定位页面xpath元素
            :param id:
            :return:
            ‘‘‘
            try:
                elements = WebDriverWait(self.driver, 20).until(lambda x: x.find_elements_by_class_name(classname))
                self.driver.implicitly_wait(2)
                return elements
            except:
                # self.screenshot()
                log.error(未定位到元素: + %s % (classname))
    
        def get_ids(self,id):
            ‘‘‘
            定位页面resouce-id元素组
            :param id:
            :return:列表
            ‘‘‘
            try:
                # elements = self.driver.find_elements_by_id(id)
                elements = WebDriverWait(self.driver, 20).until(lambda x: x.find_elements_by_id(id))
                self.driver.implicitly_wait(2)
                return elements
            except:
                # self.screenshot()
                log.error(未定位到元素:+%s%(id))
    
        def  get_webcss(self,css):
            ‘‘‘
                   定位约单的web页面
                   :param id:
                   :return:
            ‘‘‘
            try:
                self.driver.execute(MobileCommand.SWITCH_TO_CONTEXT, {"name": "WEBVIEW_com.yuedan"})
                WebDriverWait(self.driver, 30).until(lambda driver: driver.find_element_by_css_selector(css).is_displayed())
                element = self.driver.find_element_by_css_selector(css)
                element.click()
                self.driver.execute(MobileCommand.SWITCH_TO_CONTEXT, {"name": "NATIVE_APP"})
            except:
                # self.screenshot()
                # self.driver.get_screenshot_as_file("D:/error.png")
                log.error(未定位到元素: + %s % (id))
    
        def  get_webcss_list(self,css,random):
            ‘‘‘
                   定位约单的web页面,
                   :param id:
                   :return:list
            ‘‘‘
            try:
                self.driver.execute(MobileCommand.SWITCH_TO_CONTEXT, {"name": "WEBVIEW_com.yuedan"})
                elements = WebDriverWait(self.driver, 20).until(lambda x: x.find_elements_by_css_selector(css))
                elements[random].click()
                self.driver.execute(MobileCommand.SWITCH_TO_CONTEXT, {"name": "NATIVE_APP"})
            except:
                # self.screenshot()
                # self.driver.get_screenshot_as_file("D:/error.png")
                log.error(未定位到元素:+%s%(id))
    
    
    
        def page(self):
            ‘‘‘
            返回至指定页面
            :return:
            ‘‘‘
            i=0
            while i<10:
                i=i+1
                findname = self.find_id(com.yuedan:id/th_home_page)
                if findname:
                    self.driver.find_element_by_id(com.yuedan:id/th_home_page).click()
                    self.driver.implicitly_wait(2)
                    break
                os.popen("adb shell input keyevent 4")
                istext = self.find_id("com.yuedan:id/bt_ok")
                if istext:
                    self.driver.find_element_by_id("com.yuedan:id/bt_ok").click()
    
    
        def rand(self,total, num):
            ‘‘‘生成不重复的随机数,total总数,num生成的个数‘‘‘
            li = [i for i in range(total)]
            res = []
            for i in range(num):
                t = random.randint(i, total - 1)
                res.append(li[t])
                li[t], li[i] = li[i], li[t]
            return res
    
        def random_phonenumber(self):
            # 生成随机手机号码
            area_num = 399999
            # area_number = choice(area_num)
            seed = "1234567890"
            sa = []
            for i in range(6):
                sa.append(choice(seed))
            last_eightnumber = ‘‘.join(sa)
            phone = str(area_num) + last_eightnumber
            return phone
  • Operate.py
  • 最关键的一步了,后面没有page都是调用这个文件进行测试,主要是根据读取的yaml文件,然后进行if...else...判断,根据对应的operate_type分别进行对应的click、sendkeys等操作
  • #coding=utf-8
    #author=‘Shichao-Dong‘
    
    from GetYaml import getyaml
    from BaseOperate import BaseOperate
    from logs import log
    import time
    
    log = log()
    
    
    class Operate:
        def __init__(self,path,driver):
            self.path = path
            self.driver = driver
            self.yaml = getyaml(self.path)
            self.baseoperate=BaseOperate(driver)
    
    
        def check_operate_type(self):
            ‘‘‘
            读取yaml信息并执行
            element_info:定位元素信息
            find_type:属性,id、xpath、text、ids
            operate_type: click、sendkeys、back、swipe_up 为back就是返回,暂时就三种
                        增加check  用于校验
            上面三个必填,operate_type必填!!!!!!
    
            send_content:send_keys 时用到
            index:ids时用到
            times:
            :return:
            ‘‘‘
    
            for i in range(self.yaml.caselen()):
                print(self.driver.current_activity)
                if self.yaml.get_operate_type(i) == click:
                    self.driver.implicitly_wait(15)
                    self.driver.wait_activity(self.driver.current_activity, 15)
                    try:
                        if self.yaml.get_findtype(i) == text:
                            self.baseoperate.get_name(self.yaml.get_elementinfo(i)).click()
                        elif self.yaml.get_findtype(i) == id:
                            self.baseoperate.get_id(self.yaml.get_elementinfo(i)).click()
                        elif self.yaml.get_findtype(i) == xpath:
                            self.baseoperate.get_xpath(self.yaml.get_elementinfo(i)).click()
                        elif self.yaml.get_findtype(i) == class_name:
                            self.baseoperate.get_classname(self.yaml.get_elementinfo(i))[self.yaml.get_index(i)].click()
                        elif self.yaml.get_findtype(i) == ids:
                            self.baseoperate.get_ids(self.yaml.get_elementinfo(i))[self.yaml.get_index(i)].click()
                    except:
                        self.baseoperate.page()
    
    
                elif self.yaml.get_operate_type(i) == sleep:
                    time.sleep(self.yaml.get_sleeptime(i))
                elif self.yaml.get_operate_type(i) == wait_activity:
                    self.driver.wait_activity(self.yaml.get_elementinfo(i), 30)
    
                elif self.yaml.get_operate_type(i) == send_keys:
                    self.driver.implicitly_wait(5)
                    self.driver.wait_activity(self.driver.current_activity, 15)
                    try:
                        if self.yaml.get_findtype(i) == text:
                            self.baseoperate.get_name(self.yaml.get_elementinfo(i)).send_keys(self.yaml.get_send_content(i))
                        elif self.yaml.get_findtype(i) == id:
                            self.baseoperate.get_id(self.yaml.get_elementinfo(i)).send_keys(self.yaml.get_send_content(i))
                        elif self.yaml.get_findtype(i) == xpath:
                            self.baseoperate.get_xpath(self.yaml.get_elementinfo(i)).send_keys(self.yaml.get_send_content(i))
                        elif self.yaml.get_findtype(i) == ids:
                            self.baseoperate.get_ids(self.yaml.get_elementinfo(i))[self.yaml.get_index(i)].send_keys(
                                self.yaml.get_send_content(i))
                        elif self.yaml.get_findtype(i) == idSpecial:
                            a = True
                            while a:
                                self.baseoperate.get_id(self.yaml.get_elementinfo(i)).send_keys(self.yaml.get_send_content(i))
                                self.driver.find_element_by_id(com.yuedan:id/tv_re_sent).click()
                                isreg = self.baseoperate.find_id(com.yuedan:id/message)
                                log.info(isreg)
                                if isreg:
                                    self.driver.find_element_by_id(com.yuedan:id/bt_ok).click()
                                else:
                                    a = False
                    except:
                        self.baseoperate.page()
    
    
    
                elif self.yaml.get_operate_type(i) == cycleclick:
                    self.driver.implicitly_wait(15)
                    self.driver.wait_activity(self.driver.current_activity, 15)
                    try:
                        if self.yaml.get_findtype(i) == ids:
                            yaml_text = self.yaml.get_index(i)
                            if isinstance(yaml_text,list):
                                for j in range(len(yaml_text)):
                                    self.baseoperate.get_ids(self.yaml.get_elementinfo(i))[j].click()
                            else:
                                self.baseoperate.get_ids(self.yaml.get_elementinfo(i))[self.yaml.get_index(i)].click()
                        else:
                            pass
                    except:
                        self.baseoperate.page()
    
                elif self.yaml.get_operate_type(i) == webclick:
                    self.driver.implicitly_wait(15)
                    self.driver.wait_activity(self.driver.current_activity, 15)
                    try:
                        if self.yaml.get_findtype(i) == css:
                            self.baseoperate.get_webcss(self.yaml.get_elementinfo(i))
                        elif self.yaml.get_findtype(i) == ids:
                            self.baseoperate.get_webcss_list(self.yaml.get_elementinfo(i),self.yaml.get_index(i))
                    except:
                        self.baseoperate.page()
    
    
                elif self.yaml.get_operate_type(i) == swipe_up:
                    self.driver.implicitly_wait(15)
                    self.driver.wait_activity(self.driver.current_activity, 15)
                    try:
                        for i in range(self.yaml.get_backtimes(i)):
                            self.baseoperate.swipe_up()
                    except:
                        self.baseoperate.page()
                elif self.yaml.get_operate_type(i) == swipe_down:
                    self.driver.implicitly_wait(15)
                    self.driver.wait_activity(self.driver.current_activity, 15)
                    try:
                        for i in range(self.yaml.get_backtimes(i)):
                            self.baseoperate.swipe_down()
                    except:
                        self.baseoperate.page()
                elif self.yaml.get_operate_type(i) == swipe_left:
                    self.driver.implicitly_wait(15)
                    self.driver.wait_activity(self.driver.current_activity, 15)
                    for i in range(self.yaml.get_backtimes(i)):
                        self.baseoperate.swipe_left()
                elif self.yaml.get_operate_type(i) == swipe_right:
                    self.driver.implicitly_wait(15)
                    self.driver.wait_activity(self.driver.current_activity, 15)
                    for i in range(self.yaml.get_backtimes(i)):
                        self.baseoperate.swipe_right()
    
                elif  self.yaml.get_operate_type(i) == clickbox:
                    self.driver.implicitly_wait(15)
                    self.driver.wait_activity(self.driver.current_activity, 15)
                    try:
                        if self.yaml.get_findtype(i) == id:
                            isbox = self.baseoperate.find_id(self.yaml.get_elementinfo(i))
                            log.info("弹框%s"%isbox)
                            if isbox:
                                self.baseoperate.get_id_closebox(self.yaml.get_elementinfo(i)).click()
                        elif self.yaml.get_findtype(i) == text:
                            isbox = self.baseoperate.find_name(self.yaml.get_elementinfo(i))
                            if isbox:
                                self.baseoperate.get_text_closebox(self.yaml.get_elementinfo(i)).click()
                    except:
                        self.baseoperate.page()
    
    
    
    
        def check_result(self):
            caselen =  self.yaml.caselen()
            if self.yaml.get_operate_type(caselen-1) == check:
                self.driver.implicitly_wait(15)
                if self.yaml.get_findtype(caselen-1)  == id:
                    result = self.baseoperate.find_id(self.yaml.get_elementinfo(caselen - 1))
                    return result
                elif self.yaml.get_findtype(caselen-1)  == text:
                    result = self.baseoperate.getid_text(self.yaml.get_elementinfo(caselen - 1))
                    return result
                elif self.yaml.get_findtype(caselen-1)  == ids:
                    result = self.baseoperate.getids_text(self.yaml.get_elementinfo(caselen - 1))[self.yaml.get_index(caselen-1)].text
                    return result
            else:
                pass
    
    
        def back_home(self):
            ‘‘‘
            返回首页
            :return:
            ‘‘‘
            self.baseoperate.page()
    
        def isloginapp(self):
            ‘‘‘判断是否登录成功‘‘‘
            log_eable = self.baseoperate.find_id(com.yuedan:id/login)  # 登录是否显示
            return log_eable
    

     

Page部分:是最小用例集,一个模块一个文件夹,以首页为例,首页写了4个用例,每个用例一个.py文件

技术图片

 

 

运行首页用例:

技术图片

运行所有用例runtest.py:

#coding=utf-8
#author=‘Shichao-Dong‘

import time,os
import unittest
import HTMLTestRunner
import smtplib
import datetime
from public.readConfig import Readconfig
from public.Sendemail import Email
from email.mime.text import MIMEText
from email.mime.application import MIMEApplication
from email.header import Header
from email.mime.multipart import MIMEMultipart

from testcase.LoginTest import login
from testcase.HomeTest import home
from testcase.HostTest import host
from testcase.DemandTest import demand
from testcase.PersonalTest import personal
from testcase.ServiceTest import service


PATH = lambda p: os.path.abspath(os.path.join(os.path.dirname(__file__), p))

def testsuit():
    suite = unittest.TestSuite()
    suite.addTests([
                    unittest.defaultTestLoader.loadTestsFromTestCase(login),
                    unittest.defaultTestLoader.loadTestsFromTestCase(home),
                    unittest.defaultTestLoader.loadTestsFromTestCase(host),
                    unittest.defaultTestLoader.loadTestsFromTestCase(demand),
                    unittest.defaultTestLoader.loadTestsFromTestCase(personal),

])

    # runner = unittest.TextTestRunner(verbosity=2)
    # runner.run(suite)

    now=time.strftime("%y-%m-%d-%H-%M-%S")
    dirpath = PATH("./results/yuedan-")

    filename=dirpath + now +result.html
    fp=open(filename,wb)
    runner=HTMLTestRunner.HTMLTestRunner(stream=fp,title=约单自动化报告,description=u结果:)

    runner.run(suite)
    fp.close()


def send_email():
    #定义发件箱
    conf = Readconfig()
    smtpsever = conf.getemailValue(smtpsever)
    user = conf.getemailValue(user)
    password = conf.getemailValue(password)
    sender = conf.getemailValue(sender)
    receiver = conf.getemailValue(receiver)

    sendemail = Email()
    msg=sendemail.email()

    #发送邮件
    smtp=smtplib.SMTP()
    smtp.connect(smtpsever)
    smtp.login(user,password)
    smtp.sendmail(sender,receiver.split(,),msg.as_string())
    smtp.quit()
    print(u邮件发送成功)

if __name__ =="__main__":
    testsuit()
    # send_email()

 

 




以上是关于使用yaml文件管理测试数据的主要内容,如果未能解决你的问题,请参考以下文章

YAML 文件介绍

Python配置文件管理之ini和yaml文件读取

SaltStack配置管理和YAML

linux12k8s --> 04资源管理和YAML 文件详解

接口自动化测试:yaml文件中变量替换

python+appium+yaml安卓UI自动化测试分享