seleuium 自动测试工具

seleuium 自动测试工具

基础操作对象
import time
from selenium import webdriver
from selenium.webdriver.chrome.webdriver import WebDriver
from selenium.webdriver.common.by import By
from selenium.webdriver.support import expected_conditions
from selenium.webdriver.support.wait import WebDriverWait

from pages.Login import Login
from pages.config import config


class BasePage:
    _baseurl = 'https://ipark-sit.bgy.com.cn/welcome'

    def __init__(self, driver=None, op=1):
        self._baseurl = config.get("home-page")
        """
        初始化启动浏览器
        :param driver: 解决继承的子类重复初始化打开浏览器问题
        :param op: 0为复用流量器启动driver,1为打开新的浏览器复用旧的cookie
        """
        if driver is None:
            if op == 0:
                self.driver = self.options_chrome()
            elif op == 1:
                self.driver = self.cookie_chrome()
        else:
            self.driver: WebDriver = driver
        time.sleep(1)  # 新打开一个页面强制等待3秒
        Login().login(self.driver)  # 将登录后的cookie写进cookie.yml
        # Login().set_login_cookie(self.driver.get_cookies())  # 将登录后的cookie写进cookie.yml
        self.driver.implicitly_wait(10)  # 设置隐式断言10秒

    def options_chrome(self):
        """复用浏览器"""
        chrome_options = webdriver.ChromeOptions()
        chrome_options.add_experimental_option("debuggerAddress", "127.0.0.1:9222")
        self.driver = webdriver.Chrome(options=chrome_options)
        self.driver.get(self._baseurl)
        return self.driver

    def cookie_chrome(self):
        """读取cookie复用登录状态"""
        self.driver = webdriver.Chrome()
        self.driver.get(self._baseurl)  # 打开首页
        cookie = Login().get_login_cookie()
        if cookie is not None:
            cookies = self.driver.get_cookies()
            print(cookies)
            for e in cookie:
                print(e)
                self.driver.add_cookie(e)  # 将cookie添加到打开的浏览器中
        # self.driver.refresh()  # 刷新浏览器
        return self.driver

    def my_locator(self, by, locator=None):
        """
        封装元素为止传参,使可兼容多种传参
        :param by: css,id,xpath,class_name,link_text,partial_link_text,tag_name
        :param locator:
        :return:
        """
        if locator is None:
            by, value = by[0], by[1]
        else:
            by, value = by, locator

        if by.upper() == 'CSS':
            by = By.CSS_SELECTOR
        elif by.upper() == 'ID':
            by = By.ID
        elif by.upper() == 'XPATH':
            by = By.XPATH
        elif by.upper() == 'CLASS_NAME':
            by = By.CLASS_NAME
        elif by.upper() == 'LINK_TEXT':
            by = By.LINK_TEXT
        elif by.upper() == 'PARTIAL_LINK_TEXT':
            by = By.PARTIAL_LINK_TEXT
        elif by.upper() == 'TAG_NAME':
            by = By.TAG_NAME
        else:
            by = by
        return by, value

    def find_ele(self, by, locator=None):
        """
        查找元素,支持传(By.type, value),也支持传入By.type, value;
        :param by: css,id,xpath,class_name,link_text,partial_link_text,tag_name
        :param locator:
        :return:
        """
        if locator is None:
            by, value = by[0], by[1]
        else:
            by, value = by, locator

        if by.upper() == 'CSS':
            by = By.CSS_SELECTOR
        elif by.upper() == 'ID':
            by = By.ID
        elif by.upper() == 'XPATH':
            by = By.XPATH
        elif by.upper() == 'CLASS_NAME':
            by = By.CLASS_NAME
        elif by.upper() == 'LINK_TEXT':
            by = By.LINK_TEXT
        elif by.upper() == 'PARTIAL_LINK_TEXT':
            by = By.PARTIAL_LINK_TEXT
        elif by.upper() == 'TAG_NAME':
            by = By.TAG_NAME
        else:
            by = by
        self.wait_clickable(by, value)
        return self.driver.find_element(by, value)

    def find_ele_list(self, by, locator=None):
        """
        查找元素,支持传(By.type, value),也支持传入By.type, value;
        :param by: css,id,xpath,class_name,link_text,partial_link_text,tag_name
        :param locator:
        :return:
        """
        if locator is None:
            by, value = by[0], by[1]
        else:
            by, value = by, locator

        if by.upper() == 'CSS':
            by = By.CSS_SELECTOR
        elif by.upper() == 'ID':
            by = By.ID
        elif by.upper() == 'XPATH':
            by = By.XPATH
        elif by.upper() == 'CLASS_NAME':
            by = By.CLASS_NAME
        elif by.upper() == 'LINK_TEXT':
            by = By.LINK_TEXT
        elif by.upper() == 'PARTIAL_LINK_TEXT':
            by = By.PARTIAL_LINK_TEXT
        elif by.upper() == 'TAG_NAME':
            by = By.TAG_NAME
        else:
            by = by
        return self.driver.find_elements(by, value)

    def wait_clickable(self, by, locator=None, time=30):
        """
        显式等待
        :param by:css,id,xpath,class_name,link_text,partial_link_text,tag_name
        :param locator: 等待元素可点击为止,这里需要传入元素的locator
        :param time: 等待时间
        :return:
        """
        WebDriverWait(self.driver, time).until(expected_conditions.element_to_be_clickable(self.my_locator(by, locator)))

    def wait_visibility(self, by, locator=None, time=30):
        """
        显式等待
        :param by: css,id,xpath,class_name,link_text,partial_link_text,tag_name
        :param locator: 等待元素可见为止,这里需要传入元素的locator
        :param time: 等待时间
        :return:
        """
        WebDriverWait(self.driver, time).until(expected_conditions.visibility_of_element_located(self.my_locator(by, locator)))

    def ele_click(self, by, locator=None):
        """
        点击元素,支持传(By.type, value),也支持传入By.type, value;
        :param by: css,id,xpath,class_name,link_text,partial_link_text,tag_name
        :param locator:
        :return:
        """
        self.find_ele(by, locator=locator).click()

    @property
    def baseurl(self):
        return self._baseurl


登录页处理
import time

from selenium.webdriver.common.by import By

from pages.OperationYaml import OperationYaml
from pages.config import config

_COOKIEYMAL = '../file/cookie.yml'  # 用来放登录后获取的cookie


class Login:
    def login(self, driver):
        driver.find_element(By.XPATH, "//div[@id='root']/div/div[2]/div[2]/div/img").click()
        time.sleep(1)  # 新打开一个页面强制等待3秒
        username = driver.find_element(By.ID, "j_username")
        username.clear()
        username.send_keys(config.get("username"))
        passwd = driver.find_element(By.ID, "j_password")
        passwd.clear()
        print(config.get("passwd"))
        passwd.send_keys(config.get("passwd"))
        driver.find_element(By.CLASS_NAME, "loginBt").click()

    """处理cookie使免登陆"""

    def get_login_cookie(self):
        """读取yaml文件,将cookie读取出来"""
        cookie = OperationYaml().get_yaml(_COOKIEYMAL)
        if isinstance(cookie, list):
            cookies_list = cookie
        else:
            cookies_list = self.str_to_list(cookie)
        return cookies_list

    def set_login_cookie(self, cookies):
        """往yaml文件中写入cookie"""
        if isinstance(cookies, list):
            cookies_list = cookies
        else:
            cookies_list = self.str_to_list(cookies)
        OperationYaml().set_w_yaml(cookies_list, _COOKIEYMAL)

    def str_to_list(self, cookies):
        """将文本的cookie进行处理,返回的是一个列表"""
        if cookies is not None:
            l_list = cookies.split('; ')
            cookies_list = []
            for i in l_list:
                key, value = i.split('=', 1)
                cookie = {'domain': '.bgy.com.cn', 'name': key, 'path': '/', 'value': value}
                cookies_list.append(cookie)
            return cookies_list
        else:
            return None
主方法运行
import logging
import time

from selenium.webdriver import ActionChains
from selenium.webdriver.common.by import By

from pages.BasePage import BasePage


class Runner:

    def __init__(self):
        self.BasePage = BasePage()
        self.driver = self.BasePage.driver
        self.baseurl = self.BasePage.baseurl

    def runner(self, data):
        """
        执行步骤
        :param data: dict
        :return:
        """
        # 1.点击我的空间
        # pro_list = self.driver.find_elements_by_css_selector("ant-menu-overflow-item ant-menu-item "
        #                                                      "ant-menu-item-selected ant-menu-item-only-child")
        # 2.依次点击每个项目,然后点击生成
        pro_list = self.driver.find_elements(By.XPATH, "//div[@class='ant-spin-container']/div/div[2]/div")
        pl_idx = 2
        while pl_idx < len(pro_list):
            pl = pro_list[pl_idx]
            pl.click()
            time.sleep(1)
            self.driver.find_element(By.XPATH, "//div[@class='ant-spin-container']/div/div[2]/div[2]/div").click()
            time.sleep(1)
            self.driver.find_elements(By.CLASS_NAME, "ant-menu-item")[1].click()
            time.sleep(2)
            self.driver.find_elements(By.CLASS_NAME, "ant-menu-item")[2].click()
            confirm = self.driver.find_element(By.XPATH, "//div[@class='ant-modal-confirm-btns']/button[2]")
            # 点击不能直接用click,否则没有用
            if confirm:
                self.driver.execute_script("arguments[0].click();", confirm)
                # ActionChains(self.driver).move_to_element(confirm).click().perform()  # 使用鼠标点击的方式
            time.sleep(3)
            self.driver.find_elements(By.CLASS_NAME, "ant-menu-item")[3].click()
            time.sleep(1)
            self.driver.find_elements(By.CLASS_NAME, "ant-menu-overflow-item")[0].click()
            time.sleep(2)
            pro_list = self.driver.find_elements(By.XPATH, "//div[@class='ant-spin-container']/div/div[2]/div")
            pl_idx += 1

        logging.info("执行完成....")


if __name__ == "__main__":
    data = {"action": "click", "by": "xx"}
    Runner().runner(data)

读取配置
#!/usr/bin/env python
# -*- coding: utf-8 -*-
# @Date    : 2021-09-06 17:48:59
# @Author  : wangmian05
# @Link    : [email protected]
# @Version : $Id$
import base64
import os
import sys

sys.path.append("..")

import logger as log

config = {}


def start_with(cont, param):
    cont = cont.lstrip()
    if param in cont and (cont.index(param) == 0 or cont.index(param) == 1):
        return True
    return False


env = sys.argv[1] if len(sys.argv) > 1 else None
service_port = sys.argv[2] if len(sys.argv) > 2 else 0

log.debug("current env:{},service_port:{}", env, service_port)

env_prefix = env if env and len(env) > 0 else "sit"

log.debug("profile:{}", env_prefix)
current_path = os.path.abspath(__file__)

father_path = os.path.abspath(os.path.dirname(current_path) + os.path.sep + ".")

ph = str(father_path)
pwd = ph if ph.rindex("keyword") == 0 else ph[0:(ph.index("keyword") + len("keyword"))]
case_file_path = pwd + "/server-" + env_prefix + ".conf"
with open(case_file_path, "rb") as fs:
    for f in fs:
        content = f.decode('utf-8').replace("\r", '').replace("\n", '')
        if len(content) == 0 or start_with(content, "#"):
            continue
        ct_idx = content.index("=")
        isp = [content[0:ct_idx], content[ct_idx + 1:]]
        dbc = isp[1]
        if isp[0] == "passwd":
            encrypt_code = base64.decodebytes(dbc[1:len(dbc) - 1].encode("utf-8"))
            isp[1] = "".join((list(encrypt_code.decode())[::-1])[0:len(list(encrypt_code.decode())) - 6])
        config[isp[0]] = isp[1]

if __name__ == "__main__":
    str = "pass.passwd"
    dy = None
    miwen = base64.encodebytes("".join(list(str)[::-1]).encode("utf-8"))
    print(miwen.decode())

##### 配置文件

# server 配置项
home-page=https://xx.com.cn/welcome/
username=user
passwd='ZHdzc2FwZHJvd3NzYXA='
必要依赖处理
async-generator==1.10
atomicwrites==1.4.0
attrs==21.3.0
certifi==2021.10.8
cffi==1.15.0
colorama==0.4.4
cryptography==36.0.1
et-xmlfile==1.1.0
h11==0.12.0
idna==3.3
iniconfig==1.1.1
openpyxl==3.0.9
outcome==1.1.0
packaging==21.3
pluggy==1.0.0
py==1.11.0
pycparser==2.21
pyOpenSSL==21.0.0
pyparsing==3.0.6
pytest==6.2.5
PyYAML==6.0
selenium==4.1.0
six==1.16.0
sniffio==1.2.0
sortedcontainers==2.4.0
toml==0.10.2
trio==0.19.0
trio-websocket==0.9.2
urllib3==1.26.7
wsproto==1.0.0

你可能感兴趣的:(测试工具,python,开发语言)