Skip to content

语义化版本

目录

什么是语义化版本

语义化版本是一种描述软件的方式,使用一组规则描述版本的变化,采用 主版本号.次版本号.修订号 的格式

  • 主版本号 (Major):当软件进行不兼容的 API 变更 (breaking changes),主版本号递增次版本号和修订号重置为 0

  • 次版本号 (Minor):当软件添加了新功能,但保持向后兼容时,次版本号递增,修订号重置为 0

  • 修订号 (Patch):当软件进行向后兼容的 bug 修复或小更新,修订号递增

  • 先行版本号及版本编译信息可以加到 Major.Minor.Patch 之后作延申

举个例子

假设当前有一个版本号为 1.0.0 的软件包供给外部软件调用,当前软件包中有一个函数 example(a: string, b: number): string {}

  • example 函数体存在 bug,修复 bug 后未在软件中引入新的 API,该函数仍能实现预期的功能。这就是仅进行 bug 修复,未添加新功能,未发生不兼容的 API 修改,版本号变更为 1.0.1
  • 软件包中新增了 example 的函数重载,如:example(a: string, b: number, c?: boolean): string {},用户原有的调用依旧返回预期结果,当用户的 example 函数传入 c 参数时,返回值发生变化。新增了一个函数重载的功能,未发生不兼容的 API 修改,版本号变更为 1.1.0
  • example 函数新增了一个参数,如:example(a: string, b: number, c: boolean): string {},用户原有的调用会报错提示缺少参数,这时就发生了不兼容的 API 修改,版本号变更为 2.0.0

FAQ

  • 如何处理初始阶段的版本

    • 软件的主版本号为 0.y.z 是一种特殊状态,这意味着该软件处于开发初始阶段,一切都可能随时被改变
    • 最简单的做法是以 0.1.0 作为初始化开发版本,并在后续的每次发行时递增次版本号
  • 如何判断发布 1.0.0 的时机

    • 当软件被部署到生产环境中开始被正式使用,它应该已经达到了 1.0.0
    • 此时的软件已经有了一系列稳定的 API 在被使用者依赖,并开始需要考虑向后兼容的问题
  • v.1.2.3 是语义版本吗

    • 不是。v.1.2.3 是标签名称,1.2.3 是语义版本

      sh
      git tag v1.2.3 -m "Release version 1.2.3"
  • 如何决定版本的优先级:判断优先级时,必须把本依序拆分为主版本号次版本号修订号先行版本号后进行比较

    • 正式版本:依次比较主版本号次版本号修订号,数字较大的优先级较高 (如:2.0.0 > 1.0.0)
    • 相同版本正式版本的优先级高于先行版本 (如:1.0.0 > 1.0.0-alpha)
    • 先行版本:先行版本也相同时,其优先级通过从左到右的每个被句点分隔的标识符来比较,直到找到差异值
      • 数字标识符按照数值的高低比较 (如:1.0.0-alpha.5 > 1.0.0-alpha.1)
      • 字母按照 ASCII 的顺序比较 (如:1.0.0-alpha.rc > 1.0.0-alpha.beta)
      • 正式版本相同时,非数字标识符优先级更高 (如:1.0.0-alpha > 1.0.0-0)
      • 先行标识符相同时,栏位较多的优先级更高 (如:1.0.0-alpha.1.0 > 1.0.0-alpha.1)
  • 这会阻碍快速开发和快速迭代吗

    1. 如果每天修改大量 API,那么应该继续使用 0.y.z 作为版本

    2. 或者在单独的分支开发下一个主版本

  • 如果意外地将向后不兼容的更改发布为次要版本,怎么办

    • 一旦违反了语义化版本控制规范,请立即修复问题并发布新的次要版本,纠正问题并恢复向后兼容性
    • 修改已发布的版本是不可接受的,如果合适,记录违规版本并告知用户
  • 如果不改变公共 API,而是更新自身的依赖

    • 理论上它不影响公共 API,但仍需明确引入的依赖具有其自身的依赖项规范,确定更改是补丁级别、修复错误、还是引入新功能
  • 如果无意间以不符合的版本更改方式更改了公共 API (Breaking Changes)

    • 如果更改对预期造成巨大影响,那么需要进行一次主要版本发布 (即使这该被视为补丁分布)
  • 如何处理已弃用的功能 (弃用的公共 API)

    1. 更新文档,告知用户相关变更
    2. 发布包含弃用内容的新次要版本,在新的主要版本完全移除相关功能之前,应该至少发布一个包含启用内容的次要版本,方便用户过渡到新 API

References