使用 TypeScript 7 加快疊代速度
2026年6月26日 由 VS Code 團隊發布,@code
VS Code 與 TypeScript 幾乎可說是一同成長的。我們早期就大膽決定用 TypeScript 來編寫 VS Code,並且一直與 TypeScript 團隊緊密合作,為 VS Code 提供優秀的內建 TypeScript 與 JavaScript 語言支援。這篇文章探討這趟旅程的下一步:TypeScript 7,以及我們如何透過合作採用 TypeScript 7 加快了建置速度、改善了開發者與代理程式(agents)的日常編輯迴圈,並協助 TypeScript 團隊推出經過更充分測試的版本。
TypeScript 7 是使用 Go 語言對 TypeScript 編譯器及語言工具進行的完整移植(complete port)。這意味著它的速度極快,在許多情況下甚至快上 10 倍以上。VS Code 從這些速度提升中獲益良多,因此我們自然迫不及待地想盡快採用 TypeScript 7。
然而,我們也很清楚這需要時間。當我們在 2025 年夏天開始這個過程時,以一個完全重寫的專案來說,TypeScript 7 的進度其實已經快得令人震驚,但它仍然存在型別檢查不一致的問題,且缺少了許多我們需要的功能。即便如此,我們仍希望立即開始測試並提供回饋。在 TypeScript 7 還在建構中的同時就著手採用,聽起來可能有點瘋狂,但事實證明,這對 VS Code 和 TypeScript 來說都是個絕佳的決定。
漸進式移轉
VS Code 團隊從不畏懼承擔大型的工程挑戰,無論是在我們的程式碼基底中啟用嚴格空值檢查(strict null checking)、加入遠端開發支援,還是在數千個檔案中處理並預防危險的程式碼模式。這些努力的一個共同主題是,我們嘗試採取漸進式的方法。這意味著將龐大、複雜的問題拆解成微小的步驟。這些步驟都在主程式碼基底中進行(沒有分出分支或長期存在的旁支),每當一個步驟落地,通常都會帶來小小的改善。只要跨出足夠多的小步,最終當你回頭看時,就會發現自己已經悄悄征服了那個曾經看似難以跨越的挑戰。
我們希望對採用 TypeScript 7 採取相同的方法。對我們而言,這意味著將 TypeScript 7 逐步引入我們工作流程和程式碼基底的不同部分,從影響較小、風險較低的區域開始,最後再推進到 VS Code 的主要核心區域。採取漸進式作法有許多好處,其中有兩點對這項工作特別重要:
-
降低風險。每一步的採用都相對較小,因此如果出錯,很容易就能找出原因並進行復原。
-
及早回饋。我們希望在 TS 7 開發的早期階段就開始進行測試,並向 TS 團隊提供高品質的回饋。這意味著要盡可能多地使用 TypeScript 7,但又不能對 VS Code 團隊開發人員的生產力造成負面影響。
這些測試幫助我們發現了諸多錯誤與限制,讓他們能夠優先進行修復。隨著我們在程式碼基底的更多地方採用 TS 7,這些區域也成為了每次 TypeScript 7 每日建置版本(nightly release)的非正式迴歸測試(regression tests)。
在實務上,這種漸進式理念在大約六個月的時間裡,以一系列階段的形式展開。每個階段都稍微增加了我們對 TypeScript 7 的使用與測試,與 TypeScript 7 本身的進展同步推進,並在過程中協助塑造它的樣貌。以下是整個過程的發展經過:
探索期(2025 年夏季與初秋)
TypeScript 7 於 2025 年 3 月公開宣布。到了夏天,它已經準備好進行初步測試,儘管此時它仍然存在已知的錯誤與限制。
型別檢查的進度比 emit(產生 JavaScript 輸出檔案的過程)更超前,因此我們早期的測試大多集中在某些較小的擴充功能上,手動執行 @typescript/native-preview npm 套件並帶入 --noEmit 參數。我們在發現問題時隨即回報,且由於 native-preview 套件每日更新,因此我們能夠快速測試新的變更與修復。
作為 TypeScript 7 的一部分,TypeScript 團隊同時也在建構新的語言伺服器(language server),該伺服器將支援 VS Code 的編輯器內 TypeScript 與 JavaScript 支援。這透過 TypeScript native preview VS Code 擴充功能發布,它用全新的 TypeScript 7 語言伺服器取代了 VS Code 內建的 JavaScript 與 TypeScript IntelliSense。我們與 TypeScript 團隊合作,讓在兩個 TypeScript 版本之間輕鬆切換變得輕而易舉。這種靈活性至關重要,因為當時 TypeScript 7 仍然缺少許多基本的語言功能。我們希望讓開發人員覺得,他們可以盡可能以最少的心力與風險來嘗試這項新技術。
我們也讓直接從 VS Code 回報 TypeScript 7 問題變得輕而易舉。讓回報變得容易,意味著開發人員就算遇到再小的困擾,也會毫不猶豫地提交回報。這些回報為 TypeScript 團隊源源不絕地提供真實世界的意見回饋。
在這個階段,大多數測試都是由少數積極主動的 VS Code 團隊成員進行的,他們對 Alpha 測試感興趣,並且不介意繞過一些令人煩惱的小問題。
TS 6 橋接版本(2025 年秋季)
同時,TypeScript 團隊也在思考如何平順過渡到 TypeScript 7,而不是讓使用者一步跨一大步。既然現在是 2025 年,這種思考過程莫名其妙地伴隨著一個令人困惑的手勢,其產物就是這個命名貼切的 TypeScript 6.0
TypeScript 6.0 充當了 TypeScript 5.9 與 7 之間的橋樑。因此,TypeScript 6.0 中的大多數變更都是為了協助對齊並為採用 TypeScript 7 做準備
— https://devblogs.microsoft.com/typescript/announcing-typescript-6-0/
這樣的一個橋樑是必要的,因為 TypeScript 7 給了團隊一個機會去修復並現代化 TypeScript 工具中某些存在已久的痛點。例如,較舊的 TypeScript 版本預設以 ES5 為目標。這在 2014 年 ES6(又稱 ECMAScript 2015)尚未定案時合情合理,但在 2025 年看起來卻極度過時。對於新手開發人員來說,這也是個隱藏陷阱(footgun),他們往往只是因為忘記設定 target,就不小心產生了更大、效率較差的 JavaScript 檔案。同樣地,TypeScript 5 預設並未啟用嚴格空值檢查,因此許多使用者僅僅是因為不知道需要啟用它,而錯失了這個真正具備顛覆性的功能。
對我們 VS Code 團隊而言,與直接採用完全重寫的 TypeScript 7 相比,切換到 TypeScript 6 是一個風險很低的小步驟。它只需要修改少數幾處程式碼。儘管如此,這個小步驟讓我們更有信心,確信我們的程式碼基底狀態良好,而且一旦 TypeScript 7 準備就緒,我們就能順利切換過去而不會遇到太多問題。
TS 6 與 7 並行(2025 年秋季)
接下來,是時候認真開始使用 TypeScript 7 了。我們從風險最低的區域開始:使用 TypeScript 7 來對我們的內建擴充功能進行型別檢查。在此階段,我們繼續執行 TypeScript 6 以進行完整的型別檢查與 JavaScript 產生(emit)。我們設定了持續整合,確保 TypeScript 6 與 7 的建置都必須通過。一般來說,TypeScript 6 與 7 之間的型別檢查結果是一致的,但同時執行兩者確實有助於捕捉到一些我們回報的差異。
到這個時候,多虧了 TypeScript 團隊穩健的努力,TypeScript 7 中的語言伺服器進展也更加超前,因此我們將 TypeScript 7 擴充功能作為相依性加入到 VS Code 儲存庫中,以便我們的開發人員能輕鬆切換至該版本。我們的目標是逐步改善編輯器支援,讓開發人員能花越來越多時間使用 TypeScript 7。我們將任何導致開發人員切換回 TypeScript 6 的原因(無論是錯誤還是缺少功能)都列為最高優先級來處理。
起初開發人員切換回 TypeScript 6 最常見getQuery的原因之一可能會讓人有點意外:程式碼格式化。你通常可以接受建議不夠完美,甚至可以接受「前往定義」(Go to Definition)的行為不一致,但 TypeScript 6 與 7 之間的格式化差異會導致我們的 PR 提交前檢查(pre-commit checks)以及持續整合格式化檢查失敗。這使得甚至是微小的格式化不一致(例如多餘的空白)都獲得了不成比例的高優先級。隨著時間過去,這些格式化問題逐漸被修復,開發人員需要切換回 TypeScript 6 的頻率也越來越低。
在大多數擴充功能中採用 TypeScript 7(2026 年 1 月與 2 月)
到了 2026 年初,TypeScript 7 已經具備了我們全面使用所需的一切功能。TypeScript 團隊做了真正了不起的工作,讓型別檢查變得值得信賴、完成了 emit,並改善了編輯器中的語言工具。是時候開始全面切換到 TypeScript 7 了。
一如往常,我們希望謹慎且漸進地推進,因此我們開始逐一移轉我們的內建擴充功能。這些內建擴充功能在根本上與您可以使用 yo code 建立的 VS Code 擴充功能相當類似。在切換之前,這些擴充功能使用以下建置工具
- 用於型別檢查與開發建置的
tsc(TypeScript 6)。 - 用於正式環境與網路版打包(web bundles)的
webpack。 - 用於快速 emit 的
esbuild。
作為 TypeScript 7 移轉的一部分,我們決定將打包工具從 webpack 改為 esbuild,以簡化建置流程。這簡化了我們的建置工具鏈,並大幅縮短了產生打包檔案所需的時間。
我們全新的建置設定變得更簡單了
- 用於型別檢查與開發建置的
tsgo(TypeScript 7)。 - 用於正式環境與網路版打包的
esbuild。
我們以小群組為單位進行擴充功能移轉,以將任何迴歸問題的影響降至最低。這也讓我們能從最簡單的擴充功能開始,在進一步處理較複雜的擴充功能之前,累積相關知識與信心。這個過程大致上相當順利,考慮到我們先前已經在用 TypeScript 7 建構這些程式碼,這其實不應該令人太意外。
將 TypeScript 7 設為預設值(2026 年 2 月)
最後一步是在日常開發中切換到 TypeScript 7。到了那個時候,TypeScript 團隊的修復已經消除了我們一直在繞過的阻礙,而且由於漸進式的步驟已經完成了大部分的工作,因此這次的程式碼變更其實非常小。例如,這項變更將我們的日常監控(watch)工作切換為使用 TypeScript 7。
我們也讓 TypeScript 7 成為 VS Code 儲存庫在編輯器中使用的預設版本。我們仍然支援切換回舊版的 TypeScript 作為安全逃生口(escape hatch),但在實務上很少需要用到。大多數開發人員都很樂意停留在 TypeScript 7 上,因為它的效能表現顯著更好。
數據表現
那麼,這一切都值得嗎?答案是肯定的,而且毫無疑問。
以下是對 VS Code 主要原始碼進行型別檢查的前後對比
# TS 6.0
tsc --noEmit -p src/tsconfig.json
36 seconds
# TS 7
tsgo --noEmit -p src/tsconfig.json
5 seconds
TypeScript 7 快了七倍以上!當你考量到這兩項任務正在做完全相同的工作時,這點特別令人驚豔:它們以相同的徹底程度對相同的檔案進行型別檢查,並回報相同的錯誤。僅僅是從 TypeScript 6 切換到 TypeScript 7,我們就將型別檢查的速度提升了 7 倍。
有了 TypeScript 7,我們現在幾乎可以在不到一秒的時間內完成所有內建擴充功能的型別檢查。唯一的例外是較大的 Copilot 擴充功能,但也只需要 2.5 秒。
當我們檢視 VS Code 整體的編譯與型別檢查(亦即我們的主要原始碼以及大約五十個內建擴充功能的 tsconfig 專案)時,結果更是令人印象深刻。這正是 npm run watch 指令所做的事,也是 VS Code 開發人員通常會執行的指令。
在 TypeScript 6 下,npm run watch 需要大約 80 秒才能完成。移轉到 TypeScript 7 之後,我們將這個時間縮短到略多於 20 秒:大約快了四倍。這意味著每次需要重新啟動建置時(在初始監控完成後的重新檢查最多只需大約一秒),在日常開發與代理輔助迭代(agent-assisted iteration)中整整節省了一分鐘。
這些改進也轉化為編輯器中更好的語言工具效能。對於編輯器中的 TypeScript 語言功能,我們需要載入整個 tsconfig 專案,才能提供適當的錯誤提示以及自動匯入(auto imports)等複雜功能。對於主要的 VS Code 專案而言,過去這大約需要一分鐘。現在大約只需 10 秒。這大約節省了 50 秒。由於 VS Code 開發人員經常在一天內多次重新載入編輯器視窗,這些省下的時間真的相當可觀。再也不用趁著編輯器工具載入時去匆匆買杯咖啡了。
看到這些數字,真的能讓人體會到改進的規模有多大。我們很容易忽略整體的影響,因為我們的漸進式作法意味著許多改進是逐步到來的,而不是透過單一個巨大的 PR 一次到位。早期的步驟可能只在這裡省下一秒,或在那裡省下幾百毫秒。然而到最後,這些小小的勝利累積成了巨大的成果。看到 TypeScript 團隊如何兌現他們最初的承諾,也令人驚嘆:它依然是完整的 TypeScript,只是速度快得多。
透過協作變得更好
採用 TypeScript 7 對於從事 VS Code 開發的人員來說是一大勝利,而這項工作還有另一個成果比較不那麼具體,但也許影響更為深遠。事實證明,VS Code 龐大而複雜的程式碼基底,是找出 TypeScript 7 中真實世界錯誤並打磨其編輯器工具的絕佳途徑。
VS Code 團隊的開發人員也毫不畏懼地針對缺少的功能或任何感覺不對勁的地方提供回饋。每當開發人員遇到棘手的狀況並切換回 TypeScript 6 時,這對 TypeScript 團隊來說就是一個訊號,決定接下來要修復什麼。其結果就是一個經過更充分測試與打磨的 TypeScript 7 版本,我們知道它在 VS Code 程式碼基底之外也能運作良好。
雖然我們這篇文章的焦點放在 VS Code 這邊的故事,但 TypeScript 團隊真的值得獲得幾乎所有的功勞。畢竟,是他們打造了 TypeScript 7,同時還要回應來自這群難搞的 VS Code 開發人員的所有回饋。在此代表我本人以及全體 VS Code 團隊,向你們致謝!
對這個語言來說,TypeScript 7 是令人振奮的前進步伐。無論您是在 VS Code 中編輯程式碼、在命令列上觸發編譯,還是要求代理程式在專案上進行迭代,效能的提升都是顯著且有感的。多虧了 TypeScript 團隊的努力,以及此處概述的測試與回饋流程,切換到 TypeScript 7 應該是一個相對平順的過程,對許多程式碼基底而言也是個輕而易舉的勝利。
不過,最重要的是,我希望這篇文章能展現出漸進式工作、及早且頻繁測試,以及建立緊密回饋迴圈以進行密切協作的價值。這些一直是 VS Code 所秉持的價值觀,而在這次的努力中,它們再次發揮了很好的作用。我希望這個故事能啟發您,讓您對如何在自己的專案中應對大型工程挑戰、並最終交付更好的程式碼有不同的思考。
祝開發愉快! 💙