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

使用 pytest 和 MagicMock 模拟数据库操作,并测试假设的 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. UserBase 和 User 类: 这些类是基于你提供的代码实现的,包含用户的字段和配置。

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

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

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

    • 然后创建测试数据 user_data。

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

    • 使用 assert_called_once_with 来验证 db.add 和 db.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 分钟前
第 5 章:Codex 从可运行程序到可交付工具
java·前端·数据库
杨云龙UP15 分钟前
MySQL 主从复制管理:暂停、恢复、清理主从关系及命令执行位置
运维·数据库·mysql·主从配置·主从命令·reset replica·清除复制
2501_9160074730 分钟前
Windows OpenSSL 生成 iOS 证书,制作 p12 与描述文件,KXBuild 签名实操
windows·vscode·ios·objective-c·个人开发·swift·敏捷流程
yzs8733 分钟前
openGauss branch diff能力解析
数据库·oracle
郭小李43 分钟前
spring中@Transactional注解对事务的支持
数据库·spring·oracle
运维行者_44 分钟前
供应链安全成最大风险源,企业如何构建可控的运维体系?
运维·开发语言·网络·数据库·安全·云计算·流量监控
高铭杰1 小时前
Postgresql源码(160)新的共享内存注册机制,为动态调整shared_buffers打基础
数据库·postgresql
数据库小学妹1 小时前
AI Agent连数据库怎么控权限?只读账号的4个缺口
数据库·人工智能·安全·数据库权限·审计·ai数据库·只读账号
瑞克-桑切斯1 小时前
6、MySQL 总结
数据库
凤凰院凶涛QAQ1 小时前
《MySQL内核拆解:从SQL到InnoDB》(三) : 数据库设计 & 聚合查询 & 分组查询
数据库·sql·mysql