Selenium(6)-webUI自动化的PO模式及基类封装(浏览器封装,页面基本操作封装)...

PO模式

PO模式:指在编写自动化代码的时候,以每一个页面为对象建立一个py文件的设计模式,PO(英文名称:Page Object),每一个页面都对应的有一个PO类,且在这个页面的类中,包含了对该页面的的元素定位以及操作方法,以便于提高代码的可读性和可维护性。

po设计模型可分为三成:

  • 表现层:页面中可捡的元素(元素的定位编写)
  • 操作层:对页面可见元素的操作,例如点击,输入文本,获取文本(元素的基本操作,基类封装)
  • 业务层:表现层和操作层组合而成的,由操作层操作表现层的元素来实现某些功能即业务层需要完成的
    测试用例:结合以上三层,操作多个页面的元素完成指定的功能,关系如下所示:

    PO模型

    项目结构如下:请自行在本地建立如下的项目结构

    项目结构

基类的封装

基类封装

浏览器封装

步骤:
1、获取浏览器的方法get_driver
2、通过参数控制浏览器的默认类型(兼容性测试)
3、通过参数控制浏览器的模式,可以无头运行
4、通过参数控制隐式等待时间(设置隐式等待可以避免元素未加载出来就被操作了的情况)
5、优化:单例实现(参数化登录用例发现打开多个页面后改进)
封装如下:

from selenium import webdriver
from configs.env import Env

class Single(object):
    '''
    单例是一种设计模式
    1.直接用
    2.要去理解_new__init_type
    3.单例的应用场景:log、自动化测试的时候浏览器、配置器、播放器
    '''
    _instance = None  # 实例

    def _new_(cls, *args, **kwargs):
        if cls._instance is None:
            cls._instance = super().__new__(cls)
        return cls._instance


class Single1(object):
    def _new_(cls, *args, **kwargs):
        if not hasattr(cls, ' instance'):  # instance 私有的
            cls._instance = super().__new__(cls)
        return cls._instance


class CommDriver(Single):
    """
    功能:打开一个浏览器
    1.测试多种浏览器
    2.配置参数:浏览器类型,是否有头,隐式等待时间
    """
    driver = None

    def get_driver(self, browser_type=Env.BROWSER_TYPE,
                   headless_flag=Env.HEADLESS_FLAG):
        '''
        :param browser_type:浏览器类型,取配置文件中的值作为默认值
        :param headless flag:是否有头,取配置文件中的值作为默认值
        :return: 返回一个浏览器对象
        '''
        if self.driver is None:  # 如果没有打开过浏览器,就去打开
            if headless_flag:  # 如果有头模式
                if browser_type == 'chrome':
                    self.driver = webdriver.Chrome()
                elif browser_type == 'firefox':
                    self.driver = webdriver.Firefox()
                # 其他的浏览器测试可以再添加
            else:
                raise Exception(f'暂不支持当前的{browser_type}')
        else:
            if browser_type == 'chrome':
                __option = webdriver.ChromeOptions()  # _option前面_是建议私有
                __option.add_argument('--headless')  # 添加一个--headless参数
                self.driver = webdriver.Chrome(options=self.__option)
            elif browser_type == 'firefox':
                option = webdriver.FirefoxOptions()
                option.add_argument('--headless')
                self.driver = webdriver.Firefox(options=self.__option)
            else:
                raise Exception(f'暂不支持当前的{browser_type}')
            self.driver.maximize_window()  # 最大化
            self.driver.implicitly_wait(Env.IMPLICITLY_WAIT_TIME)  # 隐式等待
        return self.driver  # 如果打开过了,就直接返回



if __name__ == '__main__':
    brower = CommDriver().get_driver().get('www.baidu.com')

配置文件(configs/env)如下:设置常见的参数,后续可能会新增

class Env:
    BROWSER_TYPE = 'chrome'  # CTRL+SHIFT+U 大写  #默认浏览器类型
    HEADLESS_FLAG = True  # 默认是有头   #  True是有头
    PAGE_LOAD_TIMEOUT = 30  # 页面加载超时
    IMPLICITLY_WAIT_TIME =30 # 隐式等待30
    HOST = 'http://49.4.78.178:28/metric/view/login.html'  # 被测网站首页
    GET_ELEMENT_TIMEOUT = 5  # 显式等待默认超时时间
    SMP_FREQUENCY = 0.5  # 显式等待默认轮询时间
    MAINPAGE_URL = 'http://49.4.78.178:28/metric/view/HTML/page.html'  # 登录后首页的URL

基类封装(常见操作)

基类分装需要完成如下操作:
打开浏览器,输入网址,定位元素(获取元素添加等待,以免出现定位不到元素的情况),输入文本,点击元素(等待后点击)

from selenium.webdriver.support.wait import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
from Common.Commom import CommDriver


class BasePage():
    '''
    一般步骤:打开浏览器-->输入网址-->定位元素-->操作元素(输入文本/点击元素)
    '''

    def __init__(self):
        self.driver = CommDriver().get_driver()  # 打开浏览器的方法
        self.locators = get_yaml_data(SMP_Path.common_path / 'allelements.yaml')[self.__class__.__name__] # 初始化就打开定位元素的
        #  把元素的名字设置为当前页面的属性
        for elementname, locator in self.locators.items():
            # allelements.yaml为所有页面的元素集合
            # locators 所有的定位元素,是一个字典key:value  分别对应 elementname,locator
            # locators = {
            #     'login_button': ['css selector', '.btn_sign_up'],
            #     'message_text': ['id', 'content_ics'],
            setattr(self, elementname, locator)

    def open_url(self, url):
        self.driver.get(url)

    def get_element(self,locator,timeout=Env.GET_ELEMENT_TIMEOUT,
                    smp_frequency=Env.SMP_FREQUENCY, desc='') -> WebElement:
        '''
        locator: 定位器,如:(By.ID,'username')['id','username']
        return:返回元素
        '''
        try:
            return WebDriverWait(self.driver, timeout, smp_frequency). \
                until(EC.visibility_of_element_located(locator))
            # return self.driver.find_element(*locator)
        except:
            # 定位不到元素时,截图:文件的命名(定位哪一个元素+时间)
            curtime = time.strftime('%Y%m%d%H%M%S')
            self.driver.save_screenshot(f'{SMP_Path.screenshots_path} / {desc}{curtime}.png')

    def input_text(self, locator, text, append=False):
        '''
        locator:定位器
        text:输入的文本
        append:是否是追加输入,Ture追加输入,False清空后输入
        '''
        if not append:
            self.get_element(locator).clear()  # 如果存在文本,则清空
            self.get_element(locator).sendkeys(text)  # 输入文本信息
        else:
            self.get_element(locator).sendkeys(text)

    def click_element(self, locator):
        self.get_element(locator).click()

    def get_element_text(self, locator):
        return self.get_element(locator).text

    def wait_click_element(self, locator):  # 等待后点击元素
        WebDriverWait(self.driver, 5, 0.5).until(EC.visibility_of_element_located(locator)).click()  # 设置超市时间和轮询时间

    def wait_click_element_text(self, locator):  # 等待后获取元素文本
        return WebDriverWait(self.driver, 5, 0.5).until(EC.visibility_of_element_located(locator)).text
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

媛媛要加油呀

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值