返回专题首页

Python 专题

让代码更可靠:格式化、Lint、类型检查与提交前校验

代码质量这件事,不能只靠“我下次注意一下”。越是多人协作、越是长期维护的项目,越需要把格式统一、静态检查和类型校验前置成工具流程。

Python 专题第 23 篇 / 39 篇4 分钟

代码质量这件事,不能只靠“我下次注意一下”。越是多人协作、越是长期维护的项目,越需要把格式统一、静态检查和类型校验前置成工具流程。

这一节我们会把 Python 工程里最常见的质量保障工具串起来,看看格式化、Lint、类型检查和提交前校验分别扮演什么角色,以及怎样用尽可能小的成本搭起一套可靠的基本盘。

代码规范为什么不能只靠自觉?

如果一个项目完全靠人工约定维持质量,很快就会出现这些问题:

  • 每个人格式不一样;
  • 低级错误在评审阶段反复出现;
  • 某些问题要到运行后才暴露;
  • 提交风格时松时紧,团队体验不稳定。

所以工程化的关键,不是“要求大家更自觉”,而是让工具尽量提前帮你兜底。

格式化工具:Black 与 Ruff Format

格式化工具的作用,是把“代码长什么样”这件事从主观讨论变成自动执行。

Black 代表的是一种非常鲜明的取舍:规则相对固定,讨论空间较少,目的是让团队尽量别把精力花在格式争论上。

Ruff Format 则是 Ruff 工具链里与格式化相关的能力,和它自己的检查能力配合更紧。

不管你最终选哪一个,真正重要的是:格式统一应该自动完成,而不是靠人工维持。

Lint 检查:Ruff 的基本能力

Lint 工具负责发现那些“代码能跑,但写法存在风险或不规范”的问题。

例如:

  • 未使用的导入;
  • 变量定义了却没用;
  • 某些明显可疑的写法;
  • 风格和复杂度相关问题。

Ruff 近年来很受欢迎,一个重要原因就是它把很多常见检查能力统一到了一个高速工具里,落地成本相对低。

所以从实践角度看,Ruff 很适合作为 Python 项目最小质量基线的一部分。

类型检查:mypy / pyright 的职责

格式化解决的是“长相一致”,Lint 解决的是“静态坏味道”,而类型检查解决的是“数据流是否自洽”。

这三者职责不同,不能互相替代。

例如一个函数签名和调用方参数类型不匹配,代码格式再整齐、Lint 再干净,也照样可能埋 bug。类型检查工具能在这类问题进入运行时之前,先拦下一部分。

这也是为什么类型标注和类型检查应该一起看,而不是只写标注却不真正执行校验。

pre-commit:把质量检查前置到提交前

如果格式化、Lint、类型检查全靠人手动记得执行,那它们迟早会漏。

pre-commit 的价值就在于,把这些动作前置到提交动作之前,让工具自动帮你跑一遍。

它最有价值的地方,不是“更严格”,而是让质量检查变成稳定流程,而不是看心情执行。

一旦这层机制搭起来,很多本来会流进仓库、流进评审、流进 CI 的低级问题,就能更早被拦住。

团队里如何落地一套最小规范?

最容易失败的方式,就是一上来堆很多规则、很多工具、很多例外,把团队搞得人人头大。

更稳的落地方式通常是:

  • 先统一格式化;
  • 再补最核心的 Lint 规则;
  • 然后在关键模块逐步引入类型检查;
  • 最后把这些动作接入提交前校验和 CI。

也就是说,质量体系是可以渐进增强的,不一定非要第一天就达到极限配置。

真正重要的是先建立一个稳定、能执行、不会被团队反感的最小闭环。

总结与预告

这一节我们把代码质量从“个人习惯”变成了“可执行流程”。一旦格式化、静态检查和提交前校验进入日常开发,很多本来会在评审或联调阶段暴露的问题,都能被更早拦下来。

下一节我们会继续补上另一块关键基础设施,也就是 Python 项目中的测试体系,从 pytest 一路讲到 fixturemock