pytest测试框架使用基础07 fixture—parametrize获取参数的几种常用形式

【pytest】parametrize获取参数的几种常用形式:

a.数据结构
b.文件
c.数据库
d.conftest.py配置

一、直接在标签上传参

1.1 一个参数多个值

@ pytest.mark.parametrize("参数", (参数值1, 参数值2, 参数值3))

示例:


import pytest
# 单个参数的情况
@pytest.mark.parametrize("a", (1, 2, 3, 4))
def test_add(a):
    print("\na的值")

输出:

============================= test session starts =============================
collecting ... collected 4 items

parametrize01.py::test_add[1] PASSED                                     [ 25%]
a的值

parametrize01.py::test_add[2] PASSED                                     [ 50%]
a的值

parametrize01.py::test_add[3] PASSED                                     [ 75%]
a的值

parametrize01.py::test_add[4] PASSED                                     [100%]
a的值


============================== 4 passed in 0.04s ==============================

Process finished with exit code 0

1.2 多个参数多个值的情况

@ pytest.mark.parametrize("参数a, 参数b", ([a1, b1], [a2, b2], [a3, b3]))

示例:

@pytest.mark.parametrize("b,c,d", ([1, 2, 3], [4, 5, 6], [7, 8, 0]))
def test_add2(b, c, d):
    print("\nb,c,d的值分别为:", f'{b},{c},{d}')

输出:

============================= test session starts =============================
collecting ... collected 3 items

parametrize01.py::test_add2[1-2-3] PASSED                                [ 33%]
b,c,d的值分别为: 1,2,3

parametrize01.py::test_add2[4-5-6] PASSED                                [ 66%]
b,c,d的值分别为: 4,5,6

parametrize01.py::test_add2[7-8-0] PASSED                                [100%]
b,c,d的值分别为: 7,8,0


============================== 3 passed in 0.03s ==============================

Process finished with exit code 0

二、数据结构

2.1 列表(list)形式

示例:

import pytest

# 单个参数的情况
data1 = [1, 2, 3, 4]


@pytest.mark.parametrize("a", data1)
def test_add(a):
    print('\na的值:', a)


# 多个参数多个值得情况

data2 = [
    (1, 2, 3),
    (4, 5, 6),
    (0, 8, 9)
]


@pytest.mark.parametrize("a,b,c", data2)
def test_add2(a, b, c):
    print('\na,b,c的值分别为:', f'{a},{b},{c}')

输出:

============================= test session starts =============================
collecting ... collected 7 items
parametrize02_list.py::test_add[1] PASSED                                [ 14%]
a的值: 1
parametrize02_list.py::test_add[2] PASSED                                [ 28%]
a的值: 2
parametrize02_list.py::test_add[3] PASSED                                [ 42%]
a的值: 3
parametrize02_list.py::test_add[4] PASSED                                [ 57%]
a的值: 4
parametrize02_list.py::test_add2[1-2-3] PASSED                           [ 71%]
a,b,c的值分别为: 1,2,3
parametrize02_list.py::test_add2[4-5-6] PASSED                           [ 85%]
a,b,c的值分别为: 4,5,6
parametrize02_list.py::test_add2[0-8-9] PASSED                           [100%]
a,b,c的值分别为: 0,8,9
============================== 7 passed in 0.05s ==============================
Process finished with exit code 0

列表的基本操作:列表读取,列表添加

# 试验1:列表操作
# 列表定义

list1 = ['physics', 'chemistry', 'english', 'artist']
list2 = [1, 2, 3, 4, 5]

# 列表读取
# 方法1
for data in list1:
    print(data)
# 方法2
for i in range(0, len(list2)):
    print(list2[i])

# 列表元素追加
list1.append('history')
print(list1)

输出:

D:\ApiTest3\.venv\Scripts\python.exe D:\ApiTest3\Pytest_session\test_parametrize\list_test.py 
physics
chemistry
english
artist
1
2
3
4
5
['physics', 'chemistry', 'english', 'artist', 'history']

Process finished with exit code 0

2.2 字典(dictionary)形式

import pytest

userinfo = [
    {"username": "小李", "password": "123456"},
    {"username": "大白", "password": "894561"}
]


@pytest.mark.parametrize('info', userinfo)
def test_add(info):
    print(info)

输出:

============================= test session starts =============================
collecting ... collected 2 items

parametrize03_dic.py::test_add[info0] PASSED                             [ 50%]{'username': '小李', 'password': '123456'}

parametrize03_dic.py::test_add[info1] PASSED                             [100%]{'username': '大白', 'password': '894561'}


============================== 2 passed in 0.03s ==============================

Process finished with exit code 0

关于字典的一些基本操作如下:字典键值的获取,字典元素的追加

# 试验2:数据字典操作
# 数据字典定义

userinfo = {
    "username": "钟无艳",
    "password": "54674567"
}

# 字典读取
# 方法1:读取key
for key in userinfo.keys():
    print(key)

# 方法2:读取value
for val in userinfo.values():
    print(val)

# 方法3:读取所有内容
for key in userinfo:
    print(key,userinfo[key])
# 方法4:读取键值对
for data in userinfo.items():
    print(data)

# 字典元素追加
userinfo["phone"] = '13855455444'
print(userinfo)

输出:

D:\ApiTest3\.venv\Scripts\python.exe D:\ApiTest3\Pytest_session\test_parametrize\dic_test.py 
username
password
钟无艳
54674567
username 钟无艳
password 54674567
('username', '钟无艳')
('password', '54674567')
{'username': '钟无艳', 'password': '54674567', 'phone': '13855455444'}

Process finished with exit code 0

2.3 元组(tuple)形式

# 元组形式:
import pytest

data1 = [(1, 2, 3), (4, 5, 6)]


@pytest.mark.parametrize("a,b,c", data1)
def test_case1(a, b, c):
    print(a, b, c)

输出:

============================= test session starts =============================
collecting ... collected 2 items

parametrize04_tuple.py::test_case1[1-2-3] PASSED                         [ 50%]1 2 3

parametrize04_tuple.py::test_case1[4-5-6] PASSED                         [100%]4 5 6


============================== 2 passed in 0.03s ==============================

Process finished with exit code 0

三、json形式

有些数据是通过json文件来保存的,我们可以读取json文件的内容,然后将其转换为字典格式传参,下面讲一下如何从json文件读取参数。
大体分为以下四步

  1. 通过读取.json文件来达到数据分离
  2. 使用pytest中的parametrize参数化来读取json文件的内容
  3. 通过requests来指定请求方法,请求参数等
  4. 通过返回结果来判断json文件中的response是否包含(或者相等)/断言
  5. json数据
    整体代码:
    interface.json:
{
  "item": [
    {
      "request": {
        "url": "http://192.xxx.xxx18/Account/Login",
        "body": {
          "username": "lipan",
          "password": "E10ADC*********BE56E057F20F883E",
          "isRememberme": false,
          "validateCode": ""
        }
      },
      "response": {
        "status": 1,
        "msg": "",
        "data": null,
        "datas": null,
        "errCode": 0
      }
    }
  ]
}

parametrize05_json.py

# json形式:
import json
import pytest
import requests


# 1 读取json文件
# 由于需要的数据在item下面一层级,所以在读取时,需要指定位置
def rade_json():
    return json.load(open('interface.json', 'r'))['item']


# 通过pytest的parametrize参数化来使用read_json()里面的内容
@pytest.mark.parametrize('data', rade_json())
def test_json_login(data):
    # 通过requests来指定请求方法
    r = requests.post(
        # 通过指定read_json()里面对应的url
        url=data['request']['url'],
        # 通过指定read_json()里面对应的body
        json=data['request']['body'])

    # 通过判断返回的json数据判断read_json()里面response内容
    # 通过使用assert来断言判断是否满足预期结果
    assert r.json()['status'] == data['response']["status"]
    print(r.json())


if __name__ == '__main__':
    pytest.main('-s', '-v', 'parametrize05_json.py')

输出:

============================= test session starts =============================
collecting ... collected 1 item

parametrize05_json.py::test_json_login[data0] 

============================== 1 passed in 0.42s ==============================
PASSED                     [100%]{'status': 1, 'msg': '', 'data': None, 'datas': None, 'errCode': 0}

Process finished with exit code 0

四、文件

4.1 txt文件

file = open("文件名.txt", "r", encoding="utf-8")
content = file.read()
print(content)

示例,从下面txt文件中获取所有权限然后传参:

代码如下:

# txt文件传参:
import json
import pytest
import requests


# 获取权限列表方法
def get_txt():
    # 从文件中读取权限
    authoList = []
    # 打开txt文件
    txt_file = open('my_test.txt', 'r', encoding='utf-8')
    # 读取txt文件
    con = txt_file.read()
    print(con)

    result = con[1: -1].split(',')
    for autho in result:
        authoList.append(autho[1: -1])
        print(authoList)
    return authoList


@pytest.mark.parametrize('autho', get_txt())
def test_add_group(autho):
    print(autho)

4.2 csv文件

读取csv文件要导入csv库,基本格式如下:

# 读取csv文件
file1 = open("文件名.csv", "r")
content = csv.reader(file)
file1.close()
 
# 写入csv文件内容
file2 = open("文件名.csv""w")
write = csv.writer(file2)
file2.close()

示例,从以下csv表格中获取参数那列的值:
在这里插入图片描述

代码如下:

# csv文件传参:
import pytest
import csv


# 打开文件
def get_userdata():
    # 登入数据列表
    dataList = []
    file1 = open('login_params.csv', 'r')
    # 读文件
    readers = csv.reader(file1)
    # 跳过首行
    readers.__next__()
    for row in  readers:
        print(type(row[2]))
        # 将字符串类型转为字典类型
        userdata = eval(row[2])
        print(type(userdata),userdata)
        dataList.append(userdata)
    print(dataList)
    return dataList


@pytest.mark.parametrize('userinfo',get_userdata())
def test_add_group(userinfo):
    print(userinfo['username'])
    print(userinfo['password'])
    print(userinfo['state'])

输出:

============================= test session starts =============================
collecting ... collected 3 items

parametrize07_csv.py::test_add_group[userinfo0] PASSED                   [ 33%]test1
123456
1

parametrize07_csv.py::test_add_group[userinfo1] PASSED                   [ 66%]
123456
0

parametrize07_csv.py::test_add_group[userinfo2] PASSED                   [100%]test2

0


============================== 3 passed in 0.04s ==============================

Process finished with exit code 0

4.3 Excel 文件读取

读取Excel文件要导入pandas库,基本格式如下:

# 导入类库
import pandas as pd
 
# 读取Excel
df = pd.read_excel("文件名.xlsx")
 
# 提取对应行的内容
row = df.loc[[1, 3]].values  # 从0开始,0是首行,所以这里读取的是第1行和第4行的内容
 
# 提取对应列的内容
colum = df['列的标题'].values

示例,从以下Excel文件中获取参数那一列的内容:

# Excel文件传参:
import pandas
import pandas as pd
import pytest


def get_userdata():
    # 打开文件
    df = pd.read_excel("test_login.xlsx")
    # row = df.loc[[0, 2]].values
    # print(row)

    # 读文件
    cloum = df['输入参数'].values
    list_data = cloum.tolist()
    print(type(list_data), list_data)
    return list_data


@pytest.mark.parametrize("userinfo", get_userdata())
def test_add_group(userinfo):
    # 将其转换为字典类型
    userinfo_dic = eval(userinfo)
    print(userinfo_dic["username"])
    print(userinfo_dic["password"])

输出:

============================= test session starts =============================
collecting ... collected 4 items

parametrize08_Excel.py::test_add_group[{"username":"test1", "password":"123456"}] PASSED [ 25%]test1
123456

parametrize08_Excel.py::test_add_group[{"username":"", "password":"123456"}] PASSED [ 50%]
123456

parametrize08_Excel.py::test_add_group[{"username":"test3", "password":""}] PASSED [ 75%]test3


parametrize08_Excel.py::test_add_group[{"username":"test4", "password":""}] PASSED [100%]test4



============================== 4 passed in 2.08s ==============================

Process finished with exit code 0

五、数据库

读取数据库文件要导入pymysql库,基本格式如下:

# mysql数据库传参:

import pymysql
import pytest

"""
# 连接数据库
db = pymysql.connect(host="127.0.0.1", db="my_test", user="root", passwd="123456", charset="utf8")
# 访问数据库
cursor = db.cursor()
# 读取数据库对应内容
cursor.execute('select * from test_user')
data = cursor.fetchone()
print(data)
# 关闭数据库
db.close()
"""


def get_db_data():
    # 连接数据库
    db = pymysql.connect(host='127.0.0.1', db='my_test', user='root', password='123456', charset='utf8')
    # 访问数据库
    cursor = db.cursor()
    # 查询数据
    cursor.execute('select username, password from test_user')
    data = cursor.fetchall()
    print(data)  # 取出的数据类型是元组

    db.close()
    return data


@pytest.mark.parametrize("userinfo", get_db_data())
def test_add_group(userinfo):
    print(type(userinfo))  # 输入的是元组类型
    print(userinfo[0])
    print(userinfo[1])

输出:

============================= test session starts =============================
collecting ... collected 3 items

parametrize09_mysql.py::test_add_group[userinfo0] PASSED                 [ 33%]<class 'tuple'>
xiaoliu
123456

parametrize09_mysql.py::test_add_group[userinfo1] PASSED                 [ 66%]<class 'tuple'>
zhangshan
456187

parametrize09_mysql.py::test_add_group[userinfo2] PASSED                 [100%]<class 'tuple'>
chengyi
4536187


============================== 3 passed in 0.08s ==============================

Process finished with exit code 0

六、配置conftest.py文件

如果有多处文件都要使用同一个数据,可以将数据放在conftest.py文件下,与fixture固件结合,其他文件就可以直接使用,而不需要导入文件了。
注意点:

  • conftest.py文件名字是固定的,不可以做任何修改
  • conftest.py文件所在目录必须存在__init__.py文件
  • conftest.py文件不能被其他文件导入
  • 所有同目录测试文件运行前都会执行conftest.py文件
  • 用了fixture固件,方法上就不能再使用parametrize标签了
    示例:在conftest.py文件中
# conftest.py文件

import pytest


# 获取权限列表方法
@pytest.fixture(scope='session')
def get_autho():
    # 从文件中读取权限
    authoList = []
    # 打开txt文件
    f1 = open('my_test.txt', 'r', encoding='utf-8')
    # 读取txt文件
    con = f1.read()
    resule = con[1: -1].split(',')

    for autho in resule:
        authoList.append(autho[1: -1])
    return authoList

同目录下其他文件可直接引用(parametrize10_conftest.py)

import pytest


class TestDemo:
    def test_add_group(self, get_autho):
        for autho in get_autho:
            print(autho)


if __name__ == '__main__':
    pytest.main('parametrize10_conftest.py', '-s')

七、分析总结

  1. 私有数据放在对于的脚本中进行统一维护。
  2. 共有的数据:
    方案1:
    – 如果数据种类比较少,不超过5类以上
    –可以放在一个独立的脚本中,编写DDT的方法即可。
    方案2:
    – 需要的数据种类非常多,可以分类存放
    – 建议一个com数据层,创建多个.py文件
    方案3:
    –数据种类不多,复用性特别高
    –直接放在conftest.py中
  3. 一般来说,数据读取的方法和数据文件在相同路径下

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mfbz.cn/a/440236.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

如何向各大媒体网站投稿 海外媒体发稿平台有哪些

在数字化时代&#xff0c;各大媒体网站是企业推广和个人展示的重要平台。通过在媒体网站上发布文章&#xff0c;可以有效地扩大影响力和提升知名度。但是&#xff0c;如何投稿到各大媒体网站呢&#xff1f;以下是一些常用的方法和步骤。 1. 研究目标媒体 在投稿之前&#xff0…

宠物空气净化器值得入手吗?选购宠物空气净化器关注哪些方面?

一开始养猫时&#xff0c;每天看着可爱的猫咪在家里快乐奔跑&#xff0c;让人心情愉悦。然而&#xff0c;作为铲屎官都知道&#xff0c;猫咪会掉毛&#xff0c;特别是在换毛期间&#xff0c;地板、沙发上都会有一大堆猫毛&#xff0c;甚至衣服也可能沾满猫毛。养猫家庭中&#…

安装邮件服务器postfix、mail客户端发送邮件

安装邮件服务器postfix、mail客户端发送邮件 1 安装postfix sudo apt-get update sudo apt-get install postfix -y安装过程中会让你选择一种Postfix配置类型&#xff0c;直接选择默认的第二种配置Internet Site就可以了。 选择ok之后会让你填入域名&#xff0c;一般会自动填…

鞋服品牌怎样合理把控订货深度和宽度

在鞋服品牌的运营管理中&#xff0c;订货深度和宽度是两个至关重要的概念。订货深度指的是某一款式或规格的产品数量&#xff0c;而订货宽度则代表品牌所涵盖的产品种类和款式。合理把控订货深度和宽度对于品牌的库存管理、销售情况以及顾客满意度都有着深远的影响。本文将探讨…

MindOpt优化器: 浅谈版本0.x和1.x之间API的差异

Mindopt 是一个优化求解器&#xff0c;如果它有两个主要版本——0.xx和1.x.x&#xff08;最新版本1.1.1&#xff09;&#xff0c;它们代表着软件开发的两个不同阶段。版本1.0.0表示软件的一个大的里程碑&#xff0c;代表着软件第一个正式的“成熟”发布版本&#xff0c;而0.25是…

【保姆级爬虫】微博关键词搜索并获取博文和评论内容(python+selenium+chorme)

微博爬虫记录 写这个主要是为了防止自己忘记以及之后的组内工作交接&#xff0c;至于代码美不美观&#xff0c;写的好不好&#xff0c;统统不考虑&#xff0c;我只能说&#xff0c;能跑就不错了&#xff0c;上学压根没学过python好吧&#xff0c;基本上是crtlc&ctrlv丝滑小…

说说flexbox(弹性盒布局模型)及适用场景?

文章目录 一、是什么二、属性flex-directionflex-wrapflex-flowjustify-contentalign-itemsalign-contentorderflex-growflex-basisflexalign-self 三、应用场景参考文献 一、是什么 Flexible Box 简称 flex&#xff0c;意为”弹性布局”&#xff0c;可以简便、完整、响应式地…

轻松关掉电脑用户账户控制弹窗!

对于新装的或者是电脑自带的系统来说,是不是会经常遇到的一个情况是,就是在你运行某些程序或者改动一些系统设置的时候,每次都会弹出个提示框,以提示你这个操作是安全的,某一个提示还行,但是每次运行程序都有提示框弹出,就会有点烦了,那么这个提示框是什么呐,如何关闭…

如何实现企业内部ERP、OA、CRM、MES系统的快速一体化集成

在企业数字化规划中&#xff0c;企业纷纷引入ERP&#xff08;企业资源规划&#xff09;、OA&#xff08;办公自动化&#xff09;、CRM&#xff08;客户关系管理&#xff09;、MES&#xff08;制造执行系统&#xff09;、电商ERP(电商订单系统)等多种信息化管理系统&#xff0c;…

你自降门槛 我就该回头吗?

作者&#xff1a;朱溪 琥珀酒研社快评&#xff1a; 曾经的你让我高攀不起 现在的我对你爱答不理 同事的哥哥 因为拿不出30万的彩礼和女友分了 两年后他开了公司也有了钱 女友跑来求复合 同事的哥哥想都没想就拒绝了 用金钱给爱情设门槛&#xff0c;爱情黄了 一个能力…

500强企业不会告诉你的真话,计算机专业如何更好地进大厂

“世界上所有的500强企业&#xff0c;都告诉你学历不重要&#xff0c;但他们绝对不会去一般学校招聘。” 听起来很残酷&#xff0c;可这就是事实。从一所普通的学校毕业&#xff0c;“混”了一个很普通的专业&#xff0c;最后只能入职一家低薪的小公司或者无法就业&#xff0c…

Codeforces Round 931(Div.2) A~D2

A. Too Min Too Max &#xff08;数学&#xff09; 题意&#xff1a; 给定长度为 n n n的数组 a a a&#xff0c;求下列表达式的最大值&#xff0c; ( i , j , k , l ) (i,j,k,l) (i,j,k,l)为不同的索引 ∣ a i − a j ∣ ∣ a j − a k ∣ ∣ a k − a l ∣ ∣ a l − a…

C/C++的内存管理与初阶模板

引言 我们在学习C的时候&#xff0c;会经常在堆上申请空间&#xff0c;所以这个时候就体现了内存管理遍历。 图下是我们常见的计算机的内存划分&#xff1a; 我也在图下对部分变量存在的位置&#xff0c;及时标注。(如果有任何问题可以联系博主修改&#xff0c;感谢大家。) 那…

OpenAI劲敌吹新风! Claude 3正式发布,Claude3使用指南

Claude 3是什么&#xff1f; 是Anthropic 实验室近期推出的 Claude 3 大规模语言模型&#xff08;Large Language Model&#xff0c;LLM&#xff09;系列&#xff0c;代表了人工智能技术的一个显著飞跃。 该系列包括三个不同定位的子模型&#xff1a;Claude 3 Haiku、Claude 3…

Compose UI 之 MediumLarge TopAppBar

Medium&Large TopAppBar 前面文章介绍了 Small 类型的 TopAppBar&#xff1a;TopAppBar CenterAlignedTopAppBar 。下来介绍 Medium 和 Large 类型的 TopAppBar&#xff1a;MediumTopAppBar LargeTopAppBar 。 MediumTopAppBar 上面介绍了Small 类型的 TopAppBar (TopAp…

Zynq—AD9238数据采集DDR3缓存千兆以太网发送实验(二)

Zynq—AD9238数据采集DDR3缓存千兆以太网发送实验&#xff08;前导&#xff09; Zynq—AD9238数据采集DDR3缓存千兆以太网发送实验&#xff08;一&#xff09; Zynq—AD9238数据采集DDR3缓存千兆以太网发送实验&#xff08;三&#xff09; 五、实验目的 本次实验使用电脑上的…

贪吃蛇c++

#include<bits/stdc.h> #include<conio.h> // 用于获取按键输入using namespace std;const int width 20; const int height 20; int x, y, fruitX, fruitY, score; int tailX[100], tailY[100]; // 蛇的身体位置数组 int nTail; // 蛇的长度 enum eDirecton { S…

C# 用Trace.WriteLine输出调试信息无法查看

写程序就会遇见BUG&#xff0c;这时候在代码不同部位输出一些标记的信息对查找错误非常有必要&#xff0c;一般情况下我们都是使用Console.WriteLine()方法来打印信息到控制台窗口&#xff0c;但有时候使用Console.WriteLine()方法会存在不方便的情况&#xff0c;比如鄙人遇到的…

国际光伏展览会

国际光伏展览会是一个专注于太阳能光伏领域的国际性展览会。该展览会汇集了来自全球光伏行业的专业人士和企业&#xff0c;展示和交流最新的太阳能光伏技术、产品和解决方案。 国际光伏展览会通常展示各种类型的光伏产品&#xff0c;包括太阳能电池、太阳能电池板、太阳能光伏发…

C#,最小代价多边形三角剖分MCPT(Minimum Cost Polygon Triangulation)算法与源代码

1 最小代价多边形三角剖分算法 凸多边形的三角剖分是通过在非相邻顶点&#xff08;角点&#xff09;之间绘制对角线来形成的&#xff0c;这样对角线就不会相交。问题是如何以最小的代价找到三角剖分的代价。三角剖分的代价是其组成三角形的权重之和。每个三角形的重量是其周长…
最新文章