Python自動化Selenium單元測試page object設計模式框架設計流程

本文章將Selenium單元測試page object設計模式框架表述完整流程

本章來測試,github登錄小功能

設計架構:

在這裏插入圖片描述

目錄結構:

在這裏插入圖片描述

代碼流程描述:

1. 創建AutoTest_project 主目錄

在這裏插入圖片描述

2. 創建driver 目錄

實現功能 設計啓動瀏覽器驅動方法

1 導入啓動瀏覽器驅動(我用的是chromedriver).
創建 driver.py

from selenium import webdriver
# 在無頭瀏覽器中使用
# from selenium.webdriver.chrome.options import Options

def browser():
    driver = webdriver.Chrome(
            executable_path='/home/lbc/PycharmProjects/new_system/simplicity/util/AutoTest_project/driver/chromedriver'
        )
    # driver = webdriver.PhantomJS()
    # driver = webdriver.Firefox()

    # driver.get("http://www.baidu.com")


    return driver
if __name__ == '__main__':
    browser()

# chrome 無頭瀏覽器
# chrome_options = Options()
# chrome_options.add_argument('--headless')
# driver = webdriver.Chrome(
#     executable_path='/home/lbc/PycharmProjects/new_system/simplicity/util/AutoTest_project/driver/chromedriver'
#     , chrome_options=chrome_options
# )
# 打印頁面源碼
# print(driver.page_source)
3. 創建Website 目錄

實現功能 目錄包含 test_case目錄,test_report目錄
test_case目錄功能: 包含 model目錄,page_object目錄
test_login: 測試登錄用例 設計登錄方式 調用各類模塊 截圖 存報告 發郵箱
run_test.py: 執行test_login:.py用例
model目錄:
function.py: 測試快照截圖,檢測時間爲最新的報告文件,郵箱自動發送:發送內容及附件文件
myunit.py: unittest方法的起始執行 結束執行
test_send_png.py: 自行創建 爲了設計測試快照截圖文件的發送位置 而進行的測試文件(與主文件無關)
page_object目錄:
BasePage.py: page_object設計模式從調用 driver目錄 啓動chromedriver驅動 發送鏈接
效驗鏈接 打開瀏覽器 執行元素選中
Login_Page.py: 繼承BasePage.py方法 設置子鏈接 封裝定位器設計元素名字 清理元素框內容並輸入內容的一類封裝方法 方便後期調用 效驗登錄模塊 成功後的兩值是否相同
test_report目錄: 包含測試報告文件 screenshot截圖文件目錄

4. 創建test_case 目錄
創建 model 目錄

創建 function.py

from selenium import webdriver
import os

import smtplib  # 發送郵件模塊
from email.mime.text import MIMEText  # 定義郵件內容
from email.header import Header  # 定義郵件標題
from email.mime.multipart import MIMEMultipart # 附件文件

# 截圖
def insert_img(driver,filename):
    # 獲取模塊當前路徑
    func_path = os.path.dirname(__file__)
    # print(func_path)

    # 獲取上一級目錄
    base_dir = os.path.dirname(func_path)
    # 轉爲字符串
    base_dir = str(base_dir)

    # 如果是windows系統路徑就解開 windos系統 \\轉義 /
    # base_dir = base_dir.replace('\\','/')

    # 分割爲 /home/lbc/PycharmProjects/new_system/simplicity/util/AutoTest_project
    base = base_dir.split("/Website")[0]
    # 進行拼接 絕對路徑
    # /home/lbc/PycharmProjects/new_system/simplicity/util/AutoTest_project + /Website/test_report/screenshot + 圖片名稱.png
    filepath = base + "/Website/test_report/screenshot/" + filename
    # 進行截圖
    driver.get_screenshot_as_file(filepath)



# 找出最新時間報告文件
def latest_report(report_dir):
    lists = os.listdir(report_dir)

    # 按時間順序對該目錄文件夾下面的文件進行排序
    lists.sort(key=lambda fn: os.path.getatime(report_dir + '/' + fn))

    file = os.path.join(report_dir, lists[-1])
    # print(file[12:])
    return file

# 郵箱發送
def send_mail(latest_report):
    f = open(latest_report,'rb')
    mail_content = f.read()
    # print(latest_report.file)
    # print(mail_content)
    f.close()
    # 發送郵件

    # 發送郵箱服務器
    smtpserver = "smtp.qq.com"

    # 發送郵箱用戶名密碼
    user = "[email protected]"
    # 你的smtp授權碼
    password = "*****"

    # 發送和接收郵箱
    sender = "[email protected]"
    receive = "[email protected]"
    # 多用戶發送
    # receive = ["[email protected]","[email protected]"]

    # 發送郵件主題內容
    subject = "自動化測試報告"
    # 構造附件內容
    # 發送測試報告html文件
    send_file = open(latest_report, 'rb').read()
    att = MIMEText(send_file, 'base64', 'utf-8')
    att["Content-Type"] = 'application/octet-stream'
    att["Content-Disposition"] = 'attachment;filename="{}"'.format(latest_report[90:])
	
	# 發送截圖快照文件
    root_path = '/home/lbc/PycharmProjects/new_system/simplicity/util/AutoTest_project/Website/test_report/screenshot/'
    list_path = os.listdir(root_path)
    # print(list_path)
    wbc = []
    for names in enumerate(list_path):
        # print(names)
        pic_names = '/home/lbc/PycharmProjects/new_system/simplicity/util/AutoTest_project/Website/test_report/screenshot/{}' \
            .format(names[1])

        send_file2 = open(pic_names, 'rb').read()
        att2 = MIMEText(send_file2, 'base64', 'utf-8')
        att2["Content-Type"] = 'application/octet-stream'
        att2["Content-Disposition"] = 'attachment;filename="{}"'.format(pic_names[101:])
        wbc.append(att2)



    msgRoot = MIMEMultipart()
    msgRoot.attach(MIMEText(mail_content, 'html', 'utf-8'))
    msgRoot['Subject'] = Header(subject, 'utf-8')
    msgRoot['From'] = "[email protected]"
    msgRoot['To'] = receive
    # 生成的 快照截圖文件
    msgRoot.attach(att)
    # 遍歷 生成的多個圖片
    for atts2 in wbc:
        msgRoot.attach(atts2)


    # SSL協議端口號使用456
    smtp = smtplib.SMTP_SSL(smtpserver, 465)

    # 向服務器標識用戶身份
    smtp.helo(smtpserver)
    # 服務器返回結果確認
    smtp.ehlo(smtpserver)
    # 登錄郵箱賬戶密碼
    smtp.login(user, password)

    print('開始發送郵件')

    smtp.sendmail(sender, receive, msgRoot.as_string())
    smtp.quit()
    print('郵件發送完成')

# if __name__ == '__main__':
#     driver = webdriver.Chrome(
#         executable_path='./chromedriver',
#     )
#     driver.get("http://www.baidu.com")
#     insert_img(driver,'baidu.png')
#     driver.quit()

創建 myunit.py

import unittest
from driver import *

class StartEnd(unittest.TestCase):
    def setUp(self):
        self.driver = browser()
        print('開始執行')
        self.driver.implicitly_wait(3)
        self.driver.maximize_window()

    def tearDown(self):
        self.driver.quit()
        print('結束執行')

創建 test_send_png.py(測試文件,生成快照截圖路徑,與主體項目無關)

import os

root_path = '/home/lbc/PycharmProjects/new_system/simplicity/util/AutoTest_project/Website/test_report/screenshot/'
list_path = os.listdir(root_path)
# print(list_path)

for names in enumerate(list_path):
    # print(names)
    pic_names = '/home/lbc/PycharmProjects/new_system/simplicity/util/AutoTest_project/Website/test_report/screenshot/{}'\
        .format(names[1])
    print(pic_names)
    # print(len('/home/lbc/PycharmProjects/new_system/simplicity/util/AutoTest_project/Website/test_report/screenshot/'))
    abc = open(pic_names,'rb').read()
    print(abc)
創建 page_object 目錄

創建 BasePage.py

# 設置初始化 傳入地址 並比對地址
# 打開指定地址 進行元素檢查
from time import sleep

class Page():
    def __init__(self,driver):
        self.driver = driver
        self.base_url = 'https://github.com'
        self.timeout = 5

    def _open(self,url):
        url_ = self.base_url + url
        print('Test page is {}'.format(url_))
        self.driver.maximize_window()
        self.driver.get(url_)
        sleep(2)
        assert self.driver.current_url == url_ ,'Did not land on {}'.format(url_)

    def open(self):
        self._open(self.url)
    def find_element(self,*loc):
        return self.driver.find_element(*loc)



創建 LoginPage.py

# 調用BasePage下的Page類 傳入url
# 選擇元素進行定位
from Website.test_case.page_object.BasePage import *
from selenium.webdriver.common.by import By

class LoginPage(Page):
    # 首頁登錄頁面
    url = '/login'

    # 定位器
    username_loc = (By.NAME,'login')
    password_loc = (By.NAME,'password')
    submit_loc = (By.NAME,'commit')


    # 檢查清理元素選擇框裏的內容
    # 用戶輸入框元素
    def type_username(self,username):
        self.find_element(*self.username_loc).clear()
        self.find_element(*self.username_loc).send_keys(username)

    # 用戶輸入框元素
    def type_password(self, password):
        self.find_element(*self.password_loc).clear()
        self.find_element(*self.password_loc).send_keys(password)

    # 登錄按鈕元素
    def type_submit(self):
        self.find_element(*self.submit_loc).click()


    def Login_action(self,username,password):
        self.open()
        self.type_username(username)
        self.type_password(password)
        self.type_submit()

    loginPass_loc = (By.LINK_TEXT,'Pull requests')
    loginFail_loc = (By.NAME,'login')

    def type_loginPass_hint(self):
        return self.find_element(*self.loginPass_loc).text

    def type_loginFail_hint(self):
        return self.find_element(*self.loginFail_loc).text


創建 測試用例,及執行測試用例方法文件

創建 test_login.py

import unittest
from test_case.model import function,myunit
# from test_case.page_object.BasePage import *
from test_case.page_object.LoginPage import *

from time import sleep

class LoginTest(myunit.StartEnd):
	# 執行正確的方法
    def test_login1_normal(self):
        """username and password is normal"""
        print("test_login1_normal is start test...")

        po = LoginPage(self.driver)
        po.Login_action('[email protected]','123456')
        sleep(2)
        self.assertEqual(po.type_loginPass_hint(),'Pull requests')
        function.insert_img(self.driver,"test_login1_normal.png")

        print("test login end!!!")

	# 帳號輸入正確 密碼輸入錯誤
    # @unittest.skip("跳過當前")
    def test_login2_PasswdError(self):
        """username is ok password is error"""
        print("test_login2_PasswdError is start test...")

        po = LoginPage(self.driver)
        po.Login_action('[email protected]', 'g1346')
        sleep(2)
        self.assertEqual(po.type_loginFail_hint(), '')
        function.insert_img(self.driver, "test_login2_PasswdError.png")

        print("test login end!!!")
	# 帳號密碼都爲空
    def test_login3_empty(self):
        """username and password is empty"""
        print("test_login3_empty is start test...")

        po = LoginPage(self.driver)
        po.Login_action('', '')
        sleep(2)
        self.assertEqual(po.type_loginFail_hint(), '')
        function.insert_img(self.driver, "test_login3_empty.png")

        print("test login end!!!")

if __name__ == '__main__':
    unittest.main()

創建 run_test.py

import unittest
from Website.test_case.model.function import *
from BSTestRunner import BSTestRunner
import time

# 執行test*py 用例方法 
test_dir = './'
discover = unittest.defaultTestLoader.discover(test_dir, pattern='test*py')
# runner = unittest.TextTestRunner()
# runner.run(discover)

report_dir = '/home/lbc/PycharmProjects/new_system/simplicity/util/AutoTest_project/Website/test_report'
now = time.strftime("%Y-%m-%d %H_%M_%S")
report_name = report_dir + '/' + now +'result.html'

# 生成測試報告
with open(report_name,'wb') as f:
    runner = BSTestRunner(stream=f,title="test Report",description="Test case result")
    runner.run(discover)
    f.close()
# 傳遞report_dir路徑交給 function.py下的latest_report方法 找出最新時間測試報告 並返回 測試報告路徑
latest_report = latest_report(report_dir)
# 閱讀latest_report路徑 打開內容 並將主題 內容 最新測試報告 快照截圖文件發送到指定郵箱
send_mail(latest_report)

4. 創建test_report 目錄
這個目錄負責存儲 測試數據 測試報告 快照截圖

在這裏插入圖片描述

找到 run_test.py 運行整套項目

在這裏插入圖片描述

郵箱結果

在這裏插入圖片描述
在這裏插入圖片描述

大功告成!!!

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章