结合unittest和pytest进行虚拟数据库测试

使用 pytestMagicMock 模拟数据库操作,并测试假设的 create_user 函数,将用户添加到数据库中。

代码实现

python 复制代码
from datetime import date
from typing import List, Optional
from unittest.mock import MagicMock
from pydantic import BaseModel, Field, EmailStr
from sqlalchemy.orm import Session

# 假设的枚举类
class GenderType:
    DEFAULT = "DEFAULT"
    MALE = "MALE"
    FEMALE = "FEMALE"

# 假设的 Employment 和 CustomerInfo 类
class Employment(BaseModel):
    company: str
    position: str

class CustomerInfo(BaseModel):
    merchant_id: int
    loyalty_points: int

# UserBase 类
class UserBase(BaseModel):
    nickname: str = Field(..., description="微信用户昵称")
    avatar_url: Optional[str] = Field(None, description="微信用户头像URL")

# User 类
class User(UserBase):
    id: int = Field(..., description="用户ID")
    union_id: Optional[str] = Field(None, description="微信用户唯一标识")
    name: Optional[str] = Field(None, description="用户真实姓名")
    gender: Optional[GenderType] = Field(
        GenderType.DEFAULT,
        description="用户性别,DEFAULT: 默认,MALE: 男,FEMALE: 女",
    )
    mobile: Optional[str] = Field(None, description="用户手机号")
    birthdate: Optional[date] = Field(None, description="用户生日")
    email: Optional[EmailStr] = Field(None, description="用户邮箱")
    address: Optional[str] = Field(None, description="用户地址")
    employments: Optional[List[Employment]] = Field(
        None, description="在不同商户中,用户作为员工所拥有的员工组信息"
    )
    customers: Optional[List[CustomerInfo]] = Field(
        None, description="在不同商户中,用户作为顾客所拥有的信息"
    )

    class Config:
        orm_mode = True

# 假设的 create_user 函数
def create_user(db: Session, user_data: UserBase) -> User:
    # 模拟创建用户
    user = User(
        id=1,  # 假设生成的用户ID
        nickname=user_data.nickname,
        avatar_url=user_data.avatar_url,
        union_id="mock_union_id",
        name="Mock User",
        gender=GenderType.DEFAULT,
        mobile="1234567890",
        birthdate=date(1990, 1, 1),
        email="mock@example.com",
        address="Mock Address",
        employments=[Employment(company="Mock Company", position="Mock Position")],
        customers=[CustomerInfo(merchant_id=1, loyalty_points=100)],
    )
    db.add(user)
    db.commit()
    return user

# 测试代码
def test_create_user():
    # 创建一个模拟的数据库会话
    db = MagicMock(spec=Session)

    # 创建测试数据
    user_data = UserBase(nickname="test_user", avatar_url="https://example.com/avatar.jpg")

    # 调用 create_user 函数
    user = create_user(db, user_data)

    # 断言 db.add 被调用了一次,并且传入的参数是模拟的 user 对象
    db.add.assert_called_once_with(user)

    # 断言 db.commit 被调用了一次
    db.commit.assert_called_once()

    # 断言返回的 user 对象有正确的属性
    assert user.id == 1
    assert user.nickname == "test_user"
    assert user.avatar_url == "https://example.com/avatar.jpg"
    assert user.union_id == "mock_union_id"
    assert user.name == "Mock User"
    assert user.gender == GenderType.DEFAULT
    assert user.mobile == "1234567890"
    assert user.birthdate == date(1990, 1, 1)
    assert user.email == "mock@example.com"
    assert user.address == "Mock Address"
    assert len(user.employments) == 1
    assert user.employments[0].company == "Mock Company"
    assert user.employments[0].position == "Mock Position"
    assert len(user.customers) == 1
    assert user.customers[0].merchant_id == 1
    assert user.customers[0].loyalty_points == 100

解释

  1. UserBaseUser: 这些类是基于你提供的代码实现的,包含用户的字段和配置。

  2. create_user 函数 : 这是一个假设的函数,它接受一个数据库会话 (db) 和用户数据 (UserBase),并创建一个 User 对象,将其添加到数据库中。

  3. test_create_user 函数 : 这是测试函数,我们在这里测试 create_user 函数的行为。

    • 首先创建一个模拟的数据库会话 db

    • 然后创建测试数据 user_data

    • 调用 create_user 函数,并传入模拟的 db 和测试数据。

    • 使用 assert_called_once_with 来验证 db.adddb.commit 是否被正确调用。

    • 使用 assert 来验证返回的 user 对象具有正确的属性。

运行测试

  1. 将上述代码保存为一个 Python 文件(例如 test_user.py)。

  2. 确保已安装 pytest。如果未安装,可以使用以下命令安装:

    bash 复制代码
    pip install pytest
  3. 在终端中运行以下命令来执行测试:

    bash 复制代码
    pytest test_user.py

预期输出

如果测试通过,会看到类似以下的输出:

============================= test session starts =============================
platform darwin -- Python 3.x.x, pytest-7.x.x, pluggy-1.x.x
rootdir: /path/to/your/project
collected 1 item

test_user.py .                                                      [100%]

============================== 1 passed in 0.01s ==============================
相关推荐
椰椰椰耶14 分钟前
【redis】全局命令set、get、keys
数据库·redis·缓存
月落星还在22 分钟前
Redis 内存淘汰策略深度解析
数据库·redis·缓存
左灯右行的爱情26 分钟前
Redis- 切片集群
数据库·redis·缓存
LKAI.26 分钟前
MongoDB用户管理和复制组
linux·数据库·mongodb
计算机学姐31 分钟前
基于Asp.net的教学管理系统
vue.js·windows·后端·sqlserver·c#·asp.net·visual studio
T风呤41 分钟前
ffmpeg windows 基本命令
windows·ffmpeg
firstime_tzjz41 分钟前
windows下使用msys2编译ffmpeg
windows·ffmpeg
PinkandWhite1 小时前
MySQL复习笔记
数据库·笔记·mysql
熬夜苦读学习1 小时前
库制作与原理
linux·数据库·后端
cmgdxrz2 小时前
Mysql中的常用函数
数据库·mysql