1. 程式人生 > >python數據驅動-ddt

python數據驅動-ddt

使用步驟 traceback 並且 實現 ise war parse clas 使用

目錄

[TOC]

一、數據驅動介紹

數據驅動,我的理解,說的簡單一點,就是數據測試數據的參數化。

二、DDT基本使用介紹

2.0 測試基類

class Test:
    def __init__(self, a, b):
        self.a = a
        self.b = b

    def add(self):
        return self.a + self.b

    def sub(self):
        return self.a - self.b

    def multi(self):
        return self
.a * self.b def div(self): return self.a / self.b

2.1 使用步驟

  1. 導包

    from ddt import ddt, data, unpack
  2. 使用ddt

2.1 ddt讀取單個數據

這種方式應用的不多

2.2.1 案例

@ddt
class TestExample0428(unittest.TestCase):
    def setUp(self):
        pass

    @data(1, 2, 3)
    def test_add(self, *args, **kwargs):
        print
(*args)

打印3次,分別為1, 2, 3

2.2 ddt讀取組合中的數據(@unpack)

這種方式是較為常見的方式,可以實現多參數用例的參數化

2.2.1 加unpack

@ddt
class TestExample0428(unittest.TestCase):
    def setUp(self):
        pass
        
    @data((1, 2, 3), (2, 3, 5), (1, 1, 1))
    @unpack
    def test_dict(self, *args, **kwargs):
        print
("開始打印數據") # print(*args, **kwargs) print(*args)

打印結果

開始打印數據
1 2 3
開始打印數據
2 3 5
開始打印數據
1 1 1

2.2.2 不加unpack

@ddt
class TestExample0428(unittest.TestCase):
    def setUp(self):
        pass
        
    @data((1, 2, 3), (2, 3, 5), (1, 1, 1))
    def test_dict(self, *args, **kwargs):
        print("開始打印數據")
        # print(*args, **kwargs)
        print(*args)

打印結果

開始打印數據
(1, 2, 3)
開始打印數據
(2, 3, 5)
開始打印數據
(1, 1, 1)

2.3 讀取字典

@ddt
class TestExample0428(unittest.TestCase):
    def setUp(self):
        pass
        
    @data({"name":"gupan", "length":"170cm"}, {"age":"12"})
    def test_dict(self, *args, **kwargs):
        print("開始打印數據")
        print(*args, **kwargs)

打印結果

開始打印數據
{‘name‘: ‘gupan‘, ‘length‘: ‘170cm‘}
開始打印數據
{‘age‘: ‘12‘}

三、DDT和Excel結合

3.1 excel解析類寫法

# -*- coding:utf-8 -*-
# __author__ = ‘gupan‘

from config import settings
import os
import sys
from src.utils import utils
import xlrd
import traceback

class ExcelParse:
    """
    EXCEL解析類

    self.file_path:測試數據存放路徑
    self.workbook:打開的excel對象
    self.sheet_obj:打開的表單對象
    self.nrows:表單有數據的行數
    self.ncols:表單有數據的列數

    __init__(self, file_path):
    aquire_cell_data(self, row, col):獲取一個單元格的數據,不需要-1
    heads(self, *args, **kwargs):獲取測試數據表頭
    aquire_methodName_col(self):獲取測試方法名
    aquire_each_col_type(self):獲取每一個數據列的數據類型
    datas(self, *args, **kwargs):獲取所有的測試數據,根據方法名按字典存儲
    """

    def __init__(self, file_path):
        ‘‘‘
        :param file_path: 測試數據存放路徑
        ‘‘‘
        self.file_path = file_path
        if not os.path.exists(self.file_path):
            utils.print_log_error(self.file_path + "不存在,請確認路徑!!!!!")
            sys.exit(1)
        try:
            self.workbook = xlrd.open_workbook(self.file_path)
        except Exception as err:
            utils.print_log_error("文件應為xls格式的數據\n")
            utils.print_log_error(traceback.format_exc())
            raise err
        # 默認一個Excel表中只存儲一個表單,並且,所以只需要獲取第一個表單即可
        self.sheet_obj = self.workbook.sheets()[0]

        # 獲取表單行數
        self.nrows = self.sheet_obj.nrows
        # 獲取表單列數
        self.ncols = self.sheet_obj.ncols

        if self.nrows == 1 or self.ncols == 0:
            utils.print_log_error(file_path + "表單為空,請填寫測試數據!!!!!")
            sys.exit(1)

    def aquire_cell_data(self, row, col):
        ‘‘‘
        獲取單元格數據
        :param row: 單元格所在行數(不必主動-1)
        :param col: 單元格所在列數(不必主動-1)
        :return: 該單元格數據(str類型)
        ‘‘‘
        return self.sheet_obj.cell_value(row - 1,col - 1)

    def heads(self, *args, **kwargs):
        ‘‘‘
        獲取表頭
        :param args:
        :param kwargs:
        :return: 表頭列表
        ‘‘‘
        heads_info = []
        for col in range(0, self.ncols):
            heads_info.append(self.sheet_obj.cell_value(0, col))
        return heads_info

    def aquire_methodName_col(self):
        ‘‘‘
        獲取測試方法名鎖占據的列數
        :return: 測試方法名存放路徑
        ‘‘‘
        heads = self.heads()
        try:
            idx = heads.index(settings.method_desc)
        except IndexError as err:
            utils.print_log_error(self.file_path+"中不存在"+settings.method_desc + \n)
            utils.print_log_error(traceback.format_exc())
            raise err
        return idx

    def aquire_each_col_type(self):
        ‘‘‘
        獲取測試方法名鎖占據的列數
        :return: 獲取每一個數據列的數據類型,以列表形式返回
        ‘‘‘
        col_type_desc_list = []
        for col in range(0, self.ncols):
            col_type_desc_list.append(self.sheet_obj.cell_value(settings.desc_type_row - 1, col))
        return col_type_desc_list

    def datas(self, *args, **kwargs):
        ‘‘‘
        獲取測試數據,根據測試方法名按字典返回
        :param args:
        :param kwargs:
        :return: 字典格式的測試數據,每一個測試方法名對應的key值為列表形式
        ‘‘‘
        test_datas = {}
        # 測試數據開始數據列數
        data_begin_col = settings.data_begin_col - 1

        # 獲取測試開始數據行數
        data_begin_row = settings.data_begin_row - 1

        # 獲取每一列數據對應的數據類型列表
        type_list = self.aquire_each_col_type()

        # 測試測試方法名所在列數
        method_col = self.aquire_methodName_col()

        # 初始化測試方法名字
        pre_method_name = self.sheet_obj.cell_value(data_begin_row, method_col)


        # 存儲一個method的測試數據
        method_datas = []
        method_count = 0

        # 表頭無測試數據,去除表頭
        for row in range(settings.data_begin_row - 1, self.nrows):
            row_data = []
            cur_method_name = self.sheet_obj.cell_value(row, method_col)
            # 開始獲取數據
            for col in range(data_begin_col, self.ncols):
                type_desc = type_list[col]
                cell_data = self.sheet_obj.cell_value(row, col)
                cell_data = utils.type_switch(cell_data, type_desc)
                row_data.append(cell_data)

            if pre_method_name == cur_method_name:
                method_datas.append(row_data)
                method_count += 1

            else:
                test_datas[pre_method_name] = method_datas.copy()

                # 測試方法改變後,測試數據前置條件清空
                method_datas.clear()
                method_count = 0
                pre_method_name = cur_method_name
                method_datas.append(row_data)

        # 不為0表示有些數據沒有加上去
        if method_count != 0:
            test_datas[pre_method_name] = method_datas

        return test_datas

3.2 ddt和excel結合案例

@ddt
class TestExample0428(unittest.TestCase):
    def setUp(self):
        pass
    @data(*test_datas[‘test_add‘])
    @unpack
    def test_add(self, *args, **kwargs):
        p1, p2, value = args
        result = Test(p1, p2).add()
        try:
            self.assertEqual(result, value, "加法錯誤,請重新輸入")
            utils.print_log_info("加法測試成功")
        except AssertionError as err:
            err_str = traceback.format_exc()
            utils.print_log_error(err_str)
            raise err

測試結果

test_add_1__2__2__4_ (src.test.case.testExample.TestExample0428) ... 加法測試成功
ok
加法測試成功
test_add_2__2__2__4_ (src.test.case.testExample.TestExample0428) ... ok
加法測試成功
test_add_3__3__3__6_ (src.test.case.testExample.TestExample0428) ... ok
加法測試成功
test_add_4__4__4__8_ (src.test.case.testExample.TestExample0428) ... ok
test_dict (src.test.case.testExample.TestExample0428) ... ok
test_div (src.test.case.testExample.TestExample0428) ... ok
test_multi (src.test.case.testExample.TestExample0428) ... ok
test_sub (src.test.case.testExample.TestExample0428) ... ok

python數據驅動-ddt