用 python -m compileall 先扫一遍语法错误

34 次浏览5 条回复

改了一堆 Python 文件,但还没准备完整跑测试时,可以先用内置的 compileall 快速扫一下语法问题。

环境:Python 3.8+,在项目根目录执行:

python -m compileall .

它会递归编译 .py 文件,遇到缩进、括号没闭合这类语法错误会直接报出来。只想安静一点、不打印每个文件,可以加:

python -m compileall -q .

这个不会替代测试,只是提交前多一道很轻的检查。仓库里如果不想留下 __pycache__,可以跑完后按项目习惯清掉,或者本来就把它放进 .gitignore。

补充一点:compileall 主要是编译检查语法,不会替你发现运行时的导入错误、类型问题或测试逻辑问题。目录比较大时也可以只扫改动过的路径,避免每次都递归整个仓库。

阿线Lv1#1

补充一点:compileall 主要是编译检查语法,不会替你发现运行时的导入错误、类型问题或测试逻辑问题。目录比较大时也可以只扫改动过的路径,避免每次都递归整个仓库。

放进 CI 里也挺合适:用 python -m compileall -q src,编译失败时命令会返回非零状态,流水线可以直接拦住。项目如果把源码放在多个目录,最好显式列路径,别把虚拟环境或生成目录也扫进去。

大项目里还可以加 -j 0 让它按 CPU 核心并行编译,速度会好一些:

python -m compileall -q -j 0 src tests

我一般也倾向于显式写 src tests 这种路径,少扫一堆虚拟环境和构建产物,报错也更聚焦。

雾很大Lv1#3

大项目里还可以加 -j 0 让它按 CPU 核心并行编译,速度会好一些:

python -m compileall -q -j 0 src tests

我一般也倾向于显式写 src tests 这种路径,少扫一堆虚拟环境和构建产物,报错也更聚焦。

如果构建缓存或文件时间戳不太可信,可以再加 -f 强制重新编译:

python -m compileall -q -f src tests

平时增量检查不用加,CI 里需要确认所有源码都重新过一遍时再用,避免无谓地增加耗时。

还有个不太常用但挺干净的选项:如果只是想做语法检查,不想在源码目录旁边留下 __pycache__,可以把 pyc 写到临时目录:

PYTHONPYCACHEPREFIX=/tmp/pycache python -m compileall -q src tests

本地临时扫一遍时比较省心。CI 里一般也可以直接用临时工作区,跑完就没了。