You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
7.4 KiB
7.4 KiB
微信服务测试套件实现
日期: 2026-01-29
类型: 测试
影响范围: 微信登录服务测试
概述
完成微信登录服务的完整测试套件,包括单元测试和集成测试,覆盖所有核心功能。
测试文件
1. 单元测试
文件: server/tests/unit/test_wechat_service.py
测试覆盖
TestGenerateQrcode - 生成二维码测试
- ✅
test_generate_qrcode_mp_platform- 测试生成公众号二维码 - ✅
test_generate_qrcode_open_platform- 测试生成开放平台二维码 - ✅
test_generate_qrcode_invalid_platform- 测试无效平台类型
TestHandleCallback - 处理回调测试
- ✅
test_handle_callback_success- 测试成功处理回调 - ✅
test_handle_callback_invalid_platform- 测试无效平台
TestGetLoginResult - 获取登录结果测试
- ✅
test_get_login_result_pending- 测试等待中状态 - ✅
test_get_login_result_new_user- 测试新用户自动注册 - ✅
test_get_login_result_existing_user- 测试已存在用户登录
TestBindWechat - 绑定微信测试
- ✅
test_bind_wechat_success- 测试成功绑定 - ✅
test_bind_wechat_already_bound- 测试微信已被其他用户绑定
TestUnbindWechat - 解绑微信测试
- ✅
test_unbind_wechat_success- 测试成功解绑 - ✅
test_unbind_wechat_user_not_found- 测试用户不存在
2. 集成测试
文件: server/tests/integration/test_wechat_api.py
测试覆盖
TestWechatQrcodeAPI - 二维码 API 测试
test_get_qrcode_mp_platform- 测试获取公众号二维码test_get_qrcode_open_platform- 测试获取开放平台二维码test_get_qrcode_invalid_platform- 测试无效平台
TestWechatLoginResultAPI - 登录结果 API 测试
test_get_login_result_pending- 测试等待中状态test_get_login_result_success- 测试登录成功
TestWechatBindAPI - 绑定 API 测试
test_bind_wechat_success- 测试成功绑定test_bind_wechat_unauthorized- 测试未认证test_bind_wechat_invalid_platform- 测试无效平台
TestWechatUnbindAPI - 解绑 API 测试
test_unbind_wechat_success- 测试成功解绑test_unbind_wechat_unauthorized- 测试未认证
TestWechatCallbackAPI - 回调 API 测试
test_callback_success- 测试成功处理回调test_callback_error- 测试回调错误
测试执行结果
单元测试
$ docker exec jointo-server-app pytest tests/unit/test_wechat_service.py -v
============================= test session starts ==============================
platform linux -- Python 3.12.12, pytest-7.4.4, pluggy-1.6.0
cachedir: .pytest_cache
rootdir: /app
configfile: pytest.ini
plugins: cov-4.1.0, asyncio-0.23.3, anyio-4.12.1
asyncio: mode=Mode.AUTO
collecting ... collected 12 items
tests/unit/test_wechat_service.py::TestGenerateQrcode::test_generate_qrcode_mp_platform PASSED [ 8%]
tests/unit/test_wechat_service.py::TestGenerateQrcode::test_generate_qrcode_open_platform PASSED [ 16%]
tests/unit/test_wechat_service.py::TestGenerateQrcode::test_generate_qrcode_invalid_platform PASSED [ 25%]
tests/unit/test_wechat_service.py::TestHandleCallback::test_handle_callback_success PASSED [ 33%]
tests/unit/test_wechat_service.py::TestHandleCallback::test_handle_callback_invalid_platform PASSED [ 41%]
tests/unit/test_wechat_service.py::TestGetLoginResult::test_get_login_result_pending PASSED [ 50%]
tests/unit/test_wechat_service.py::TestGetLoginResult::test_get_login_result_new_user PASSED [ 58%]
tests/unit/test_wechat_service.py::TestGetLoginResult::test_get_login_result_existing_user PASSED [ 66%]
tests/unit/test_wechat_service.py::TestBindWechat::test_bind_wechat_success PASSED [ 75%]
tests/unit/test_wechat_service.py::TestBindWechat::test_bind_wechat_already_bound PASSED [ 83%]
tests/unit/test_wechat_service.py::TestUnbindWechat::test_unbind_wechat_success PASSED [ 91%]
tests/unit/test_wechat_service.py::TestUnbindWechat::test_unbind_wechat_user_not_found PASSED [100%]
============================== 12 passed in 0.22s ===============================
结果: ✅ 12/12 测试通过
测试技术要点
1. Mock 策略
数据库会话 Mock
@pytest.fixture
def mock_session():
session = AsyncMock()
session.begin = MagicMock()
session.begin.return_value.__aenter__ = AsyncMock()
session.begin.return_value.__aexit__ = AsyncMock()
return session
Redis Mock
@pytest.fixture
def mock_redis():
redis = AsyncMock()
return redis
ThreadPoolExecutor Mock
@pytest.fixture
def mock_executor():
from concurrent.futures import ThreadPoolExecutor, Future
executor = MagicMock(spec=ThreadPoolExecutor)
def mock_submit(fn, *args, **kwargs):
future = Future()
try:
result = fn(*args, **kwargs)
future.set_result(result)
except Exception as e:
future.set_exception(e)
return future
executor.submit = mock_submit
return executor
2. 异步测试
所有测试使用 @pytest.mark.asyncio 装饰器:
@pytest.mark.asyncio
async def test_generate_qrcode_mp_platform(self, wechat_service, mock_redis):
# 测试逻辑
pass
3. Patch 策略
使用 patch.object 模拟同步方法:
with patch.object(wechat_service, '_fetch_wechat_user_info', return_value=mock_user_info):
result = await wechat_service.bind_wechat(user_id, 'test_code', 'mp')
4. 异常测试
使用 pytest.raises 验证异常:
with pytest.raises(ValidationError, match="无效的平台类型"):
await wechat_service.generate_qrcode(platform='invalid')
修复的问题
1. DatabaseError 异常缺失
问题: app.core.exceptions 缺少 DatabaseError 异常类
修复: 添加 DatabaseError 异常类
class DatabaseError(Exception):
"""数据库操作异常"""
pass
文件: server/app/core/exceptions.py
2. ThreadPoolExecutor Mock
问题: 简单的 MagicMock() 无法正确模拟 ThreadPoolExecutor
修复: 使用 concurrent.futures.Future 正确模拟 executor
测试覆盖率
功能覆盖
- ✅ 生成二维码(公众号/开放平台)
- ✅ 处理微信回调
- ✅ 轮询登录结果
- ✅ 新用户自动注册
- ✅ 已存在用户登录
- ✅ 绑定微信账号
- ✅ 解绑微信账号
- ✅ 异常处理(无效平台、用户不存在、已绑定等)
边界情况
- ✅ 无效平台类型
- ✅ 微信已被其他用户绑定
- ✅ 用户不存在
- ✅ 等待中状态
后续任务
-
集成测试执行:
- 需要配置测试环境(Redis、数据库)
- 需要 mock 微信 API 调用
- 需要配置认证 fixture
-
测试覆盖率报告:
docker exec jointo-server-app pytest tests/unit/test_wechat_service.py --cov=app.services.wechat_service --cov-report=html -
端到端测试:
- 完整的微信登录流程测试
- 前端集成测试
参考文档
版本信息
- 测试框架: pytest 7.4.4
- 异步支持: pytest-asyncio 0.23.3
- 实现日期: 2026-01-29
- 测试状态: ✅ 12/12 通过