不用手动创建,pdm 会自动管理 __pypackages__,但需项目根目录下有 pdm.toml 或 pyproject.toml 且启用 pep 582;手动创建易引发冲突。

PEP 582 的 __pypackages__ 目录到底要不要手动创建
不用,pdm 会自动管理 __pypackages__,但前提是项目根目录下有 pdm.toml 或 pyproject.toml(且已启用 PEP 582)。手动建目录、放包、改 PYTHONPATH 是旧思路,现在反而容易冲突。
常见错误现象:ModuleNotFoundError 即使包已安装;或 import 成功但 IDE 提示未解析 —— 很可能是没激活 PEP 582,或终端没加载 pdm 的 shell hook。
- 确认已运行
pdm --pep582 <shell></shell>(如pdm --pep582 bash),并把输出的export PYTHONPATH=...加入 shell 配置 -
pdm install后检查是否生成了__pypackages__/<cp3x>/lib</cp3x>(cp311等取决于你用的 Python 版本) - 不要在非项目目录下执行
python脚本——PEP 582 只在当前目录向上查找__pypackages__,跨目录不生效
为什么 python -m pip install 不走 PEP 582
因为 pip 本身不读取 __pypackages__,它只认 sys.path[0] 和传统 site-packages。用 pip 安装的包不会进 __pypackages__,也不会被 PEP 582 机制识别。
使用场景:想给当前项目装一个临时调试包,或需要指定 --find-links 源 —— 正确做法是用 pdm add --no-self 或直接 pdm add -e ./some-local-package。
立即学习“Python免费学习笔记(深入)”;
-
pdm add requests→ 走 PEP 582,进__pypackages__ -
python -m pip install requests→ 进全局或 venv site-packages,对当前项目无效 - IDE(如 VS Code)需配置 Python 解释器为项目根目录下的
.pdm-python,否则即使 shell 里能 import,编辑器仍报错
pdm run 和直接 python 的行为差异
pdm run 会自动注入 __pypackages__ 到 PYTHONPATH,并确保使用项目锁定的 Python 解释器;而裸 python 命令只依赖当前 shell 的 PYTHONPATH 和解释器版本,极易错配。
性能影响几乎为零,但兼容性风险明显:比如项目锁的是 python 3.11,你本地默认是 3.12,裸 python 就可能因字节码不兼容报 Bad magic number。
- 脚本执行统一用
pdm run python script.py,别图省事写python script.py -
pdm run会继承pdm的环境变量,包括PYTHONPATH注入逻辑,也支持--help查参数 - CI/CD 中若用
python -m pytest,应改为pdm run pytest,否则测试可能漏掉本地包依赖
Windows 下 PowerShell 的 PYTHONPATH 注入失败
PowerShell 默认禁止执行脚本,pdm --pep582 powershell 输出的是一个 .ps1 片段,直接粘贴执行会报错 ExecutionPolicy —— 这是最常被忽略的卡点。
不是 pdm 的 bug,是 PowerShell 安全策略限制。绕过方法简单但必须显式操作:
- 以管理员身份打开 PowerShell,运行
Set-ExecutionPolicy RemoteSigned -Scope CurrentUser - 然后执行
pdm --pep582 powershell | Out-String | Invoke-Expression - 验证:启动新 PowerShell,运行
echo $env:PYTHONPATH,应看到含__pypackages__的路径
复杂点在于,VS Code 的集成终端可能用的是旧会话,改完策略后要重启终端,否则 import 依然失败。










