Go 改版本號(hào)規(guī)則,主版本號(hào)終于支持第三位數(shù)字 0 了...
大家好,我是煎魚。
平時(shí)我們經(jīng)常會(huì)跟蹤 Go 的版本發(fā)布,看看是不是有 BUG,新特性等值得關(guān)注的東西,好吸取新的知識(shí)和技術(shù)跟進(jìn),用到自己的日常工作和系統(tǒng)中。
在新的特性、新的資料記錄的映射上,我們也會(huì)用版本號(hào)來與之關(guān)聯(lián),這很常見。
背景
但看 Go 版本號(hào)時(shí),會(huì)出現(xiàn)一個(gè)和其他軟件版本不一樣的神奇現(xiàn)象。那就是 Go 的主要版本號(hào),居然是兩位數(shù):
圖片
說是兩位數(shù),也可以理解。結(jié)果你認(rèn)真一看,會(huì)發(fā)現(xiàn)是主要版本和次要版本,在兩位數(shù)和三位數(shù)之間橫跳:
圖片
這時(shí)候就會(huì)有一個(gè)容易引起誤解(理解)的事情。像是開發(fā)同學(xué)或運(yùn)維同學(xué)部署開發(fā)、私有化環(huán)境時(shí),問你用的什么版本?
可能大部分同學(xué)會(huì)直接說用 Go1.20。有了解 Go 版本號(hào)規(guī)則的人,不知道你到底說的是 Go1.20(第一個(gè)版本),還是說要求 Go1.20.x(該大版本的當(dāng)前最新版本),就會(huì)造成明確混淆。
懶得糾結(jié)的,一配置,Docker 一拉取。就直接應(yīng)用到 Go1.20 的第一個(gè)版本去了。會(huì)錯(cuò)過許多 Go BUG 本身的修復(fù)。
對(duì)于許多應(yīng)用場(chǎng)景來講,這可能影響不是特別大。但對(duì)于 Go 是一門對(duì)外開源社區(qū)運(yùn)作的編程語(yǔ)言來講,顯然是不合適的。
要不要用 semver 做版本控制
在業(yè)內(nèi)有一個(gè)管理版本號(hào)的標(biāo)準(zhǔn):semver。版本格式:“主版本號(hào).次版本號(hào).修訂號(hào)”,版本號(hào)遞增規(guī)則如下:
- 主版本號(hào):當(dāng)你做了不兼容的 API 修改,將是主版本號(hào)的破壞性變更。
- 次版本號(hào):當(dāng)你做了向下兼容的功能性新增,將是次版本的特性變更。
- 修訂號(hào):當(dāng)你做了向下兼容的問題修正,將是修復(fù)的版本變更。
先行版本號(hào)及版本編譯信息可以加到“主版本號(hào).次版本號(hào).修訂號(hào)”的后面,作為延伸。并且標(biāo)準(zhǔn)的版本號(hào)必須(MUST)采用 X.Y.Z 的格式。
以往在 Go 社區(qū)很多人提了很多次,希望 Go 掰過來。用 semver 來管理社區(qū)的版本號(hào)發(fā)布,這樣子最為標(biāo)準(zhǔn)化。
圖片
顯然 Go 是不符合的,為什么呢?因?yàn)?Go 并沒有采納這個(gè)版本思路,版本號(hào)也是用 go 開頭的,例如 runtime.Version()
輸出的結(jié)果是:go1.20,或是 go1.20.6。
最重要的是 Go 創(chuàng)始人認(rèn)為 semver 是理想化的,在互聯(lián)網(wǎng)社區(qū)的路子上是行不通的,直接就拒絕了。
解決方案
經(jīng)過多年的折騰,大家也認(rèn)清了現(xiàn)實(shí)。提出了一個(gè)有意縮小變更范圍的新提案《build: use a zero for third digit for major release, such as 'go1.21.0'[1]》,爭(zhēng)取解決背景中提到的問題。
圖片
本次僅限只做一個(gè)變動(dòng),那就是:把 “.0” 加到主版本中。例如以前是 go1.23?,F(xiàn)在要變成 go.1.23.0。
在 Go 工具鏈上。例如配套的 go.mod 的 go 行,我后續(xù)也是會(huì)跟著改變的,主版本時(shí)也會(huì)多 “.0”,確保兩者保持一致。
這樣的妥協(xié)方案,至少可以解決解決大家對(duì) go1.20(以該版本舉例)的理解誤差。明確到底是 1.20.0,還是 1.20.x 的版本。
我們也可以緩解另一派以為 go1.20.0 才是第一個(gè) BUG 修復(fù)版本,結(jié)果沒想到居然是 go1.20.1?,F(xiàn)在會(huì)更明確和清晰些。
當(dāng)然,為此會(huì)帶來一些成本。例如:解析 Go 版本號(hào)的工具鏈和腳本的改造、文檔、博客、書籍等的更新。但綜合成本來看,改變的成本并不是很大。
總結(jié)
目前該提案已經(jīng)完成審查和 CL,可以說很明確將會(huì)進(jìn)入到 Go 后續(xù)版本的使用中。以后主版本將會(huì)是 go1.21.0 起,并補(bǔ)充 “.0”,而不再是以前的 go1.21,能夠規(guī)避相當(dāng)一部分的版本混淆問題。
這個(gè)問題,說大不大,是比較細(xì)微的變更。但在我們的日常工程構(gòu)建中,是經(jīng)常會(huì)遇到的。為了省事(沒具體看),有的同學(xué)會(huì)在 Dockerfile 中寫 go1.18,更新版本號(hào)也是寫 go1.19、go1.20 等,很少會(huì)關(guān)注到后面的 BUG 修復(fù)版本,這是比較可惜的。
當(dāng)然,Go 版本號(hào)的命名規(guī)則不完全統(tǒng)一,本身也是一個(gè)比較無奈的事。與此相類似的還有 RC 版本。
Go RC 版本目前的命名規(guī)則是:go1.20rc3。社區(qū)會(huì)建議 go1.20-rc3 的格式規(guī)范。但顯然,Go 核心團(tuán)隊(duì)暫時(shí)沒打算改。