You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

pytest两种启动方式的差异及ModuleNotFoundError报错原因与底层原理解析

Why python -m pytest Works But pytest Doesn't (ModuleNotFoundError for 'server')

Let’s break down exactly why these two commands behave so differently, and what’s going on under the hood to cause that ModuleNotFoundError.

The Core Issue: Python’s Module Search Path (sys.path)

The root of the problem lies in how Python builds its module search list (sys.path) when you run these two commands. This list determines where Python looks for modules to import.

When you run python -m pytest

Using python -m pytest tells Python to load the pytest module as an executable script. This does two critical things for your project:

  1. It adds your current working directory (the src/ folder you’re in when running the command) to the very start of sys.path.
  2. It then launches the pytest runner from this context.

Since src/ is in sys.path, Python can immediately find the server module when conftest.py tries to import it—because server/ is a subdirectory of src/ (and has an __init__.py, so it’s recognized as a valid Python package).

When you run pytest directly

Running pytest as a standalone command works from a different context:

  1. It executes the pytest executable located in your virtual environment’s bin/ folder.
  2. By default, pytest adds the directory containing your test files (your src/tests/ folder) to sys.path—but it doesn’t automatically include the parent src/ folder.

So when conftest.py tries to import server, Python looks for it in src/tests/ (and other standard system paths) and comes up empty, hence the ModuleNotFoundError.

Underlying Mechanism Deep Dive

To get a bit more technical:

  • python -m <module>: This invokes Python’s built-in module loader, which sets sys.path[0] to your current working directory (os.getcwd()). This is the same behavior you get when running a script with python my_script.py—it prioritizes the folder you’re in when you run the command.
  • Standalone pytest command: The pytest executable sets up its own runtime environment. By default, it focuses on the test directory, not the parent application directory. Unless you explicitly configure it to look elsewhere, it won’t scan src/ for your application modules.

Quick Fixes to Make pytest Work Directly

If you want to run pytest without relying on python -m pytest, here are two simple solutions:

  1. Add src/ to sys.path in conftest.py:
    import sys
    from pathlib import Path
    
    # Add the parent directory (src/) to Python's module search path
    sys.path.append(str(Path(__file__).parent.parent))
    
  2. Configure pytest via pyproject.toml:
    Create a pyproject.toml file in your src/ folder with this content:
    [tool.pytest.ini_options]
    pythonpath = ["."]
    
    This tells pytest to add the current src/ directory to sys.path, matching the behavior of python -m pytest.

内容的提问来源于stack exchange,提问作者Alexey Orlov

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.04.29 18:17:32