当前位置:首页>python>python+behave+openpyxl管理测试用例

python+behave+openpyxl管理测试用例

  • 2026-09-07 16:49:09
python+behave+openpyxl管理测试用例
TECH NOTE · 教程 2022.03.11

python+behave+openpyxl · behave

测试用例文本化,使用python+behave来维护测试用例

DOODLE

测试用例文本化,使用python+behave来维护测试用例

BEHAVE PYTHON

测试用例文本化,使用python+behave来维护测试用例

01

PART

背景

SECTION

一些传统公司或者项目,会使用excel来作为测试用例。

近期由于公司leader的要求:“你们测试用例要文本化,主要是方便diff,不然每次提交的都是xls文件(测试用例会提交到git仓库),不太方便去比较。如果文本化了,就能在git中直接看出这次提交修改的内容”。

基于这个需求,其实有很多更好用的excel对比工具,但是领导是研发类型的领导,更希望能够文本化处理。即通过某种方式,将写好的测试用例转成文本,然后再通过CI/CD的方式编译出我们需要的excel。

02

PART

项目介绍

SECTION

behave的介绍:BDD-python+behave自动化测试搭建

分两个部分,一个是将excel转换为behave所需要的feature,一个是将feature转换为excel,从而达到相互转换的。

03

PART

将原有的excel转化为feature

EXCEL

通常情况下,excel的模板都是固定的。同公司中,不同项目所使用的测试用应该是基于同一个模板编写的。

这里就是针对基于固定模板编写完成的测试用例文件进行分析,并转换为feature文件

项目地址:

https://gitea.kiki.kim/ha/excel2feature.git

目录结构

...shell

+--excel2feature/

|   +--bin/      

|   |    +-- e2f.py   # -- 主程序

|   +--excel_files/   # -- 测试用例文件夹

|   |    +-- *.xlsx  # 测试用例

|   +--templates/   # -- features模板

|   |    +-- *feature.j2  # 模板文件

|   +--output/   # -- 转换后的feature

核心代码:

...python

        #获取所有的数据

        work_book = xlrd.open_workbook(self.xlsx_file_path)

        #为了让py2字典的顺序与py3一致

        all_data = OrderedDict()

        for i, sheet_obj in enumerate(work_book.sheets()):

            all_data[sheet_obj.name] = [sheet_obj.row_values(row)

                                        for row in range(sheet_obj.nrows)]

.........

.........

    def get_feature_data(self, datas, sheet_name):

        """

        根据sheet_name 处理数据

        """

        context_temp = OrderedDict()

        if sheet_name == "封面":

            context_temp['project'] = self.project

            context_temp['sheet_name'] = sheet_name

            # 处理更新记录

            Scenario_table = []

            lines = datas[4:]

            for line in lines:

                cells = line

                # 处理换行

                for index, cell in enumerate(cells):

                    #因为py2的编码问题,不能判断str

                    #isinstance(cell,str)

                    if not isinstance(cell,(int,float)):

                        cells[index] = cell.replace('\n', '\\n')

                Scenario_table.append(cells)

            context_temp['Scenario_table'] = Scenario_table

        elif sheet_name == "统计表":

            context_temp['project'] = self.project

            context_temp['sheet_name'] = sheet_name

.........

.........

    def feature_tpl(self):

        """

        拿处理后的数据来渲染指定的模板

        """

        # 读取模板

        tpl = os.path.join(self.templates_dir, self.feature_name + ".j2")

        tpl_data = io.open(tpl, encoding="utf-8").read()

        # 渲染模板

        env = Environment()

        text = env.from_string(tpl_data).render(self.context)

        # 保存文件

        xl2fe.save_feature(self, text)

04

PART

将feature转换为excel

FEATURE

由于提交的都是feature文件,这种方式是无法直接去使用的。因此,需要再将其转为excel文件。

项目地址:

https://gitea.kiki.kim/ha/behave-test-case.git

项目结构:

...shell

+--behave-test-case/

|   +--bin/      

|   |    +-- behave_main.py   # -- 主程序

|   +--features/  

|   |    +-- *.feature  # 转换后的测试用例

|   +--fixtures/   # 模板文件目录

|   |    +-- test_case_template.xlsx  # 模板文件

|   +--output/   # -- 转换后的目录

核心代码:

...shell

#激活sheet页

@step(u'I active "{title}"')

def i_active_title(context,title):

    # context.project_file = os.path.join(context.output_dir,context.file)

    # context.wb = load_workbook(context.project_file)

    #print(title)

    context.ws = context.wb.get_sheet_by_name(title)

.........

.........

#自动合并单元格

@step(u'I auto_merge_cells "{col}" start at "{startnum}"')

def i_auto_merge_cells(context,col,startnum):

    status = True

    startnum = int(startnum)

    endnum = startnum + 1

    #print(endnum)

    while status:

        startcol = col + str(startnum)

        endcol = col +str(endnum)

        if context.ws[endcol].value == None or context.ws[endcol].value == '':

            status = False

            #continue

        if context.ws[startcol].value == context.ws[endcol].value:

            endnum = endnum +1

        else:

            endnumtmp = endnum -1

            endcoltmp = col +str(endnumtmp)

            cells = startcol + ":" + endcoltmp

            context.ws.merge_cells(cells)

            context.ws[startcol].alignment = my_alignment('center', 'center')

            startnum = endnum

            endnum = endnum +1

.........

.........

#写入数据

@step(u'I load the table')

def i_load_table(context):

    table = context.table

    #print(table)

    if context.text:

        title = table.headings

        context.ws.append(title)

    lists = table.rows

    for cells_list in lists:

        cells = cells_list.cells

        values = []

        for cell in cells:

            #换行符被转义了,再处理回来

            cell_value = cell.replace('\\n','\n')

            values.append(cell_value)

        #print(values)

        context.ws.append(values)

我是 小梦同学,一个爱折腾技术的测试工程师,专注分享踩坑经验

如果你觉得今天这篇有收获,欢迎点赞、在看、转发三连,我们下篇见。

如果你觉得今天这篇有收获,欢迎点赞、在看、转发三连,我们下篇见。

赞
在看
收藏

THANKS FOR READING

最新文章

随机文章