Gopls v0.17.0 版本釋出

go install golang.org/x/tools/gopls@v0.17.0-pre.4

新的支援策略

在此版本中,我們將官方支援視窗縮窄,以與Go 支援策略保持一致。這將大大降低我們針對舊版本 Go 進行測試的成本,使我們能夠花費更多時間來修復錯誤並新增對執行近期版本 Go 的大多數 gopls 使用者有益的功能。

此次縮窄在兩個維度上進行:構建相容性是指可用於構建 gopls 的 Go 工具鏈版本,而go 命令相容性是指 gopls 可用於列出工作區中包和模組資訊的 go 命令版本。

構建相容性:最新的主 Go 版本

正如v0.16.0 版本說明中所述,構建最新版本的 gopls 現在需要最新的主 Go 工具鏈版本。因此,此版本(gopls@v0.17.0)必須使用 Go 1.23.0 或更高版本進行構建。得益於自動工具鏈升級,如果您的系統 Go 版本至少為 Go 1.21.0 並且設定了 GOTOOLCHAIN=auto(預設設定),go 命令將自動按需下載新的 Go 工具鏈,類似於升級模組依賴。

Go 命令相容性:最近的 2 個主 Go 版本

gopls@v0.17.x 版本將是 gopls 最後一個名義上支援整合超過最近 2 個 Go 版本以內的版本。過去,我們暗示支援最多 4 個版本,但實際上我們沒有資源來修復僅存在於舊 Go 版本中的錯誤。在 gopls@v0.17.0 中,我們將此盡力支援的範圍縮窄到 3 個版本,這主要是因為使用者至少需要 Go 1.21 才能從自動工具鏈升級中受益(見上文)。

從 gopls@v0.18.0 開始,我們將僅正式支援與最近 2 個主 Go 命令版本整合。這與 Go 支援策略一致。有關詳細資訊,請參閱 golang/go#69321(或此評論)。

我們不會阻止 gopls 與舊版 Go 版本一起使用(就像我們不禁止與任意go/packages驅動程式整合一樣),但我們不會針對舊版 Go 版本執行整合測試,也不會修復僅在與舊版 Go 版本一起使用時才存在的錯誤。

配置更改

  • fieldalignment 分析器(以前預設停用)已被移除:它與 v0.16.0 顯示的懸停大小/偏移量資訊重複,並且其診斷資訊令人困惑。
  • undeclaredname 分析器已被替換為常規程式碼操作。
  • gopls 所有程式碼操作的型別(識別符號)已更改為使用更具體的層級名稱。例如,“Inline call”已從 refactor.inline 更改為 refactor.inline.call。這允許客戶端更精確地請求特定的程式碼操作。使用者手冊現在包含每個程式碼操作文件中的識別符號。
  • 實驗性的 allowImplicitNetworkAccess 設定已根據 gopls@v0.16.0 中的棄用而被移除。有關詳細資訊,請參閱 golang/go#66861。

新功能

重構

此版本包含多項與重構相關的新功能。此外,它還修復了現有重構操作中許多錯誤,主要涉及提取內聯

這些改進使我們朝著提供更強大、更完整的重構工具集的長期目標邁進。我們還有很多工作要做,這項工作將持續到 2025 年。

移動引數重構

Gopls 現在提供程式碼操作,可以將函式和方法引數在函式簽名中向左或向右移動,並更新所有呼叫者。

不幸的是,沒有原生的 LSP 操作可以為任意“更改簽名”重構提供良好的使用者介面。我們計劃在 VS Code 中構建這樣一個介面。短期內,我們透過呼叫 func 關鍵字的“重新命名”操作,使得表達更復雜的引數轉換成為可能。此使用者介面是臨時的權宜之計,直到有更好的機制可用於啟用客戶端對話方塊的 LSP 命令。

將宣告提取到新檔案

Gopls 現在提供另一項程式碼操作“Extract declarations to new file”(refactor.extract.toNewFile),該操作將選定的程式碼段移動到同一包中新建立的檔案。建立的檔名選擇為遇到的第一個 {function, type, const, var} 名稱。此外,還會根據需要新增或刪除匯入宣告。

使用者可以透過選擇函式名、關鍵字 funcconstvartype,或將游標放在它們上面而不選擇,或選擇整個宣告或多個宣告來呼叫此程式碼操作。

為了避免歧義和意外,某些型別的宣告的部分選擇無法呼叫此程式碼操作。

提取常量

當選中的是常量表達式時,gopls 現在提供“Extract constant”而不是“Extract variable”,並生成 const 宣告而不是區域性變數。

此外,提取常量或變數現在可以在頂層工作,不在任何函式內部。

根據函式呼叫生成缺失的方法

當您嘗試呼叫一個型別上不存在該方法的型別時,編譯器會報告錯誤,例如“type T has no field or method f”。Gopls 現在提供一項新的程式碼操作“Declare missing method of T.f”,其中 T 是具體型別,f 是未定義的函式。存根方法的簽名會根據呼叫的上下文進行推斷。

為函式或方法生成測試

如果選中的程式碼塊是函式或方法宣告 F 的一部分,gopls 將提供“Add test for F”程式碼操作,該操作會在相應的 _test.go 檔案中為選中的函式新增一個新的測試。生成的測試會考慮其簽名,包括輸入引數和返回值。

由於此功能由伺服器(gopls)實現,因此與所有支援 LSP 的編輯器相容。VS Code 使用者可以繼續使用客戶端命令 Go: Generate Unit Tests For file/function/package,該命令會執行gotests工具。

初步支援拉取診斷

當使用選項 "pullDiagnostics": true 初始化時,gopls 將宣告支援 textDocument.diagnostic 客戶端能力,允許編輯器使用 textDocument/diagnostic 請求直接從 gopls 請求診斷,而不是等待 textDocument/publishDiagnostics 通知。此功能預設關閉,直到拉取診斷的功能集與推送診斷的功能集相當。

懸停改進

textDocument/hover 響應已略微調整了 markdown 渲染,幷包含以下附加資訊:

  • 懸停在標準庫符號上現在會顯示該符號首次出現的 Go 版本資訊。例如,懸停在 errors.As 上會顯示“Added in go1.13”。
  • 懸停在包宣告的包名稱上會包含額外的包元資料。

型別頂級建構函式的語義令牌修飾符

語義令牌響應現在包含每個符號型別的頂級建構函式的附加修飾符:interfacestructsignaturepointerarraymapslicechanstringnumberboolinvalid。編輯器可以使用此資訊進行語法著色。

identvalues 的 SignatureHelp。

現在,函式簽名幫助可以在任何具有函式簽名的識別符號上使用,而不僅僅是在正在呼叫的函式的括號內。

跳轉到彙編定義

對函式引用的 Definition 查詢會跳轉到函式的 Go func 宣告。如果函式是用 C 或彙編實現的,則函式沒有函式體。執行第二個 Definition 查詢(當已經在 Go 宣告處時)將導航到彙編實現。

yield 分析器

新的 yield 分析器可檢測 Go 1.23 迭代器中使用 yield 函式的錯誤,例如未能檢查其布林結果並跳出迴圈。

waitgroup 分析器

新的 waitgroup 分析器可檢測對 sync.WaitGroupAdd 方法的呼叫,這些呼叫(錯誤地)在新 goroutine 中進行,導致 AddWait 發生競爭。(此檢查等同於staticcheck 的 SA2000,但預設啟用。)


本文件的原始碼可以在 golang.org/x/tools/gopls/doc 下找到。