如何在Python 3的Pytest运行测试时暂停并等待用户输入?
在Pytest测试中暂停并获取用户输入的解决方案
嘿,我懂你这个需求——虽然交互式测试确实不符合自动化测试的“无人工干预”标准流程,但在调试OAuth这种需要手动授权的场景时,确实是个实用的临时方案。下面给你几个可行的实现方法:
方法1:用Python内置input()直接实现(最简便)
这是最直接的方式,在需要暂停的位置调用input(),让用户在终端输入从浏览器拿到的授权码。修改你的测试代码如下:
def test_oauth_flow(): client_id = "你的客户端ID" scope = "所需权限范围" url_jwt = auth(id=client_id, scope=scope) # 打开浏览器引导用户完成授权操作 webbrowser.open_new(url_jwt) # 暂停测试,等待用户输入授权码 id_code = input("请粘贴浏览器中获取到的授权码:") # 使用授权码完成后续认证流程 auth_result = auth(code=id_code) assert auth_result == 1
小提示:
- 运行测试时一定要在交互式终端中执行,如果用无交互的CI/CD环境,测试会直接卡住。
- 记得加上
pytest -s参数运行,这个参数会禁用Pytest的输出捕获,确保input()的提示信息能正常显示给你,不然可能看不到输入提示哦。
方法2:用Pytest Fixture封装输入逻辑(更优雅)
如果多个测试都需要这种交互式输入,可以把输入逻辑封装成fixture,提升代码复用性:
import pytest @pytest.fixture def user_auth_code(): def _get_code(prompt="请输入授权码:"): return input(prompt) return _get_code def test_oauth_flow(user_auth_code): client_id = "你的客户端ID" scope = "所需权限范围" url_jwt = auth(id=client_id, scope=scope) webbrowser.open_new(url_jwt) # 调用fixture获取用户输入的授权码 id_code = user_auth_code("请粘贴浏览器中的授权码:") auth_result = auth(code=id_code) assert auth_result == 1
方法3:预留自动化切换入口(可选)
如果之后想回归完全自动化的测试,可以加个环境变量的判断,方便在本地调试(交互)和CI/CD(自动化)之间切换:
import os import pytest def test_oauth_flow(): client_id = "你的客户端ID" scope = "所需权限范围" url_jwt = auth(id=client_id, scope=scope) webbrowser.open_new(url_jwt) # 优先从环境变量取授权码,没有则提示用户输入 id_code = os.getenv("TEST_AUTH_CODE") or input("请输入授权码:") if not id_code: pytest.fail("未提供授权码,测试终止") auth_result = auth(code=id_code) assert auth_result == 1
这样,在CI环境中可以提前设置TEST_AUTH_CODE环境变量,测试就能自动运行;本地调试时则会自动触发输入提示。
最后再提醒一句:这种交互式测试只适合本地调试或临时验证,千万别长期放在自动化测试套件里。如果要长期自动化OAuth测试,建议用测试账号的预生成令牌,或者mock授权服务的响应来模拟整个流程。
内容的提问来源于stack exchange,提问作者MarkK




