不推荐使用 pytest-env 插件。该插件已三年未更新,不兼容 pytest 8+ 和 Python 3.12,且非官方推荐;应改用 pytest-dotenv 的 --envfile 参数或 conftest.py 中的 pytest_configure 钩子来管理环境变量。
不推荐。pytest-env 已经三年没更新,最后一次发布是 2021 年(v0.6.2),不兼容 pytest 8+,且在 Python 3.12 下会因 pkg_resources 被弃用而直接报错:ModuleNotFoundError: No module named 'pkg_resources'。它也不是 pytest 官方推荐方案,现在更可靠的方式是用原生机制替代。
pytest 本身从 v7.0 开始内置了 --envfile 支持(需配合 pytest-dotenv 插件),这是目前最轻量、兼容性最好的做法。它不会侵入测试逻辑,变量只在测试运行时注入 os.environ,且支持多文件叠加。
pip install pytest-dotenv
.env.test,内容如:API_BASE_URL=https://staging.example.com<br>DB_NAME=test_db<br>DEBUG=true
pytest --envfile=.env.test tests/
os.getenv("API_BASE_URL"),无需额外 import 或 setup.env 和 .env.test,后者优先级更高;但不要依赖隐式加载,始终用 --envfile 明确指定适用于需要动态生成或条件化设置变量的场景(比如根据 pytest 参数切换环境),比 .env 文件更灵活,但要小心污染全局 os.environ。
conftest.py 中使用 pytest_configure 钩子:import os<br><br>def pytest_configure(config):<br> os.environ.setdefault("API_BASE_URL", "https://local.dev")<br> os.environ.setdefault("LOG_LEVEL", "DEBUG")
setdefault 而非直接赋值,否则会干扰本地调试或 CI 环境已设的变量pytest_unconfigure 删除临时变量(但通常没必要,进程退出后自动释放)setup_method 或 fixture 中反复 set,会导致不可预测的覆盖顺序在单个测试里用 monkeypatch.setenv() 是安全的,但它只作用于当前测试函数,无法统一管理跨测试的“固定环境”。如果你的目标是“所有测试都跑在 staging 环境下”,那就不是 patch 的适用场景——那是配置问题,不是模拟问题。
立即学习“Python免费学习笔记(深入)”;
@pytest.mark.parametrize 给每个测试传环境参数,导致配置分散、难维护monkeypatch 测试“当 ENV=prod 时函数行为不同”,而不是用来设置整套测试环境@pytest.fixture(autouse=True))容易引发执行顺序问题,且无法被 --envfile 或 CI 变量覆盖,灵活性反而下降真正关键的是分清“固定环境”和“测试隔离”:前者属于运行配置,走 --envfile 或 pytest_configure;后者才是 monkeypatch 和 fixture 的地盘。混用会导致配置漂移,尤其在 CI 中表现不一致。