Angular 1 和 Angular 2 集成:無縫升級的方法

jopen 9年前發布 | 23K 次閱讀 Angular2

已經有了 Angular 1 應用程序,正在想著怎么把它升級到 Angular 2?看看我們是怎么樣支持遞增升級的。

摘要

好消息。

  • 我們計劃在同一應用程序上允許 Angular 1 和 Angular 2 混合使用

  • 你可以在同一個視圖中混用 Angular 1 和 Angular 2 組件

  • Angular 1 和 Angular 2可以跨框架注入服務

  • 數據綁定可以跨框架運行

為什么要升級?

Angular 2 相對于 Angular 1 有很多優勢,其中包括:性能有了極大提高,更強大的模板化,延遲加載,更簡單的 API。 調試更加簡單,測試前所未有地容易,等等。以下是幾個突出亮點:

更好的性能

我們通過關注大量的場景來讓你的應用變得輕快,初次渲染和再次渲染會快 3x 到 5x。

  • 通過單形態的 JS 調用進行更快的變化檢測

  • 模板預編譯和重用

  • 頁面緩存

  • 更低的內存使用 / VM 壓力

  • 線性可伸縮,可觀察或者不可變數據結構

  • 依賴注入支持增量加載

更多強大的模板

  • 不再需要大量的指令

  • 靜態分析 —— 未來工具和 IDEs 在開發的過程發現錯誤,而不是運行過程

  • 允許模板編寫工具來決定綁定的使用,而不是在指令定義硬連接

未來計劃

我們正在從 DOM 解耦 Angular 2 的渲染。我們正在積極支持下面的其他功能,從這個解耦我們可以:

  • 服務端渲染:允許超快的初次渲染和 web-crawler 支持。

  • Web Workers:把你的應用和大部分 Angular 轉移到一個 Web Worker 線程,保持任何時候的 UI 的流暢和響應式。

  • 原生移動 UI:我們熱衷于在移動應用中支持 Web 平臺。同時,一些團隊想要在他們的 iOS 和 Android 移動應用中展示完全原生的 UIs。

  • 編譯作為構建的步驟之一。Angular 應用解析和編譯他們的 HTML 模板。我們在把編譯步驟轉移到你的構建過程,以此來加快初次渲染速度。

Angular 1 和 2 共同運行

Angular 2 比 Angular 1 提供了更吸引人的優勢,表現在性能,簡易性和靈活性。我們正在努力令你容易地從現有 Angular 1應用中就能獲得這種優勢的好處,而這種 Angular 1 應用無縫混合了 Angular 2的組件和服務從而形成單獨的應用。通過這樣的混合,你能夠在多次小規模的提交中升級一個應用中的一個服務或組件。

例如,你可能有一個如下圖類似的應用。為了感受 Angular 2 的新特性,又決定升級組件 left nav 成為 Angular 2 組件。一旦你對 Angular 2 的應用更有把握,你決定為了你的主體區域中的滾動區使用 Angular 2 的渲染速度。

Angular 1 和 Angular 2 集成:無縫升級的方法

為了讓兩者集成工作,在 Anglar 1 和 Angular 2 之間有四樣要素需要相互協作:

  • 依賴注入

  • 組件嵌套

  • 內容嵌入

  • 變化檢測

為了實現以上功能,我們會建立一個名為 ng-upgrade 的庫。你能在已存在的 Angular 1 應用里包含 ng-upgrade 和 Angular 2,并能很好地與之混合并搭配使用。

你可以在原始的改進設計文檔中找到全部細節和偽代碼,并閱讀細節的概述以了解其工作原理。在未來的官方公告中,我們將會粗略介紹從 Angular 1 代碼升級到 Angular 2 的特例。

依賴注入

首先,我們需要解決應用程序中各部分的通信問題。在 Angular 中,用于與其他類或函數通信的的最普遍方式是依賴注入。Angular 1 具有單一的根注入器,而 Angular 2 則具有分層注入器。每次升級服務都暗示著這兩種注入需要互相提供實例。

ng-upgrade 庫會自動地把 Angular 1 中的所有可注入的元素在 Angular 2 中變得可用。這意味著 Angular 2 的組件或服務能夠在你的 Angular 1 應用服務中各處注入。

Angular 2 支持把 Angular 2 服務暴露在 Angular 1 注入器之下的行為,但你需要提供簡單的映射設置。

通過獨立的提交和混合環境中的通信,這種服務結果能夠簡便地一次一次地從 Angular 2  轉移到 Angular 1。

組件嵌套和嵌入

在所有版本的 Angular 中,我們將組件定義為擁有其模板的指令。為了進行增量遷移, 你需要能夠一次次遷移組件。這意味著 ng-upgrade 要允許來自每一個框架中的組件相互嵌套。

為 了解決這個問題,ng-upgrade 允許你在外觀設計模式中包含 Angular 1 的組件,這樣就能夠在 Angular 2 的組件中使用。相反地,你可以在 Angular 1 中包含 Angular 2 的組件來使用。伴隨著 Angular 1 的嵌入和 Angular 2 的內容保護的模擬,這能夠發揮全部作用。

在嵌套組件中,每個模板,包括其語法和語義,完全從屬與 Angular 1 或者 Angular 2 兩者之一。這不是一種仿真模式,而是每個框架中基于組件種類的實實在在的執行。這意味著升級到 Angular 2 的組件將會受益于 Angular 2 的所有特性,而不僅僅是更好的語法。

這也意味著Angular 1的組件通常會使用Angular 1的依賴注入。即使在使用Angular 2的模板時,Angular 2組件也會使用Angular 2的依賴注入,即使它是使用Angular 1的模板。


變化檢測

把Angular 1的組件和Angular 2的組件混合起來意味著Angular 1的作用范圍和Angular 2的組件是交錯的。因此,ng-upgrade會確認變化檢測(Angular 1的作用范圍摘要和Angular 2的變化檢測)在相同通道中是否交錯,以維持表達式的可預測性的評估命令。

ng-upgrade把這些特點納入賬戶,并通過創造一種單獨的結合性摘錄循環的方法來實現跨平臺,以便在Angular 1的作用范圍摘要和Angular 2的變化檢測建立聯系。

典型的應用升級過程

這里有一個Angular 1項目升級為 Angular 2 的例子:

1. 在現有的應用中包含 Angular 2 和 ng-upgrade 的庫。

2. 選擇你想遷移的組件。

a. 編輯 Angular 1 的指令控制器去順應 Angular 2 的語法。

b. 改變指令控制器/連接函數改變令其符合 Angular 2 的語法和語義。

c. 利用 ng-upgrade 去輸出指令(現在是組件)作為 Angular 1 的組件(如果需要你可以稱之為從Angular 1 模板衍生的 Angular 2 的組件)。

3. 選擇你想遷移的服務。

a. 大多數的服務要求最低限度的修改。

b. 在 Angular 2 環境下配置服務。

c.(可選的)不使用 ng-upgrade 再輸出服務到使用 ng-upgrade 的 Angular 1,如果它還繼續被其他 Angular 1 代碼使用。

4. 重復第2步驟和第3步驟以便于應用開發

5. 一旦沒有多余的服務/組件被用來變更,把高層次的 Angular 1 引導程序降下,更換為 Angular 2的引導程序。

注意每個獨立的變更會分別地被檢查。并且,應用會持續地工作,讓你隨心所欲地繼續發布升級。

我們不打算因為允許非組件的指令能夠在兩邊被使用而提供支持。因為我們想到,大多數的非組件的指令在 Angular 2 中是不必要的,但在新的模板語法中是被直接支持的。

Q&A

我聽說 Angular 2 不支持雙方法連接。我應當怎樣替換它?

事實上,Angular 2 是支持雙方發連接和 ng-model,雖然這需要一點不同的語法。

當我們打算建立起 Angular 時,我們就想修復好與 Angular 摘錄循環的發出。為了解決這個問題,我們選擇創建一個非直接的數據流用作于變化檢測。一開始,我們還不清楚怎樣用雙方法在 Angular 1 中來構建起 ng-model 的數據綁定。但我們總是認為我們必須令 Angular 2 中構建如同 Angular 1 的一樣簡單。

經過幾次循環后,我們設法修復多摘錄中壞掉的地方,同時保持 Angular 1 中 ng-model 的強力和簡易性。

雙方法數據綁定有了一個新語法:[(property-name)]="expression"來令表達式在各方位中的界限更加明確。由于能夠應用與大多數場景,這只不過是一個微小的語法更改,能夠輕易地進行遷移。

如下面的例子,在 Angular 1 中,你會有:
<input type="text" ng-model="model.name" />

在 Angular 2 中,你可以把上面的例子轉換為這樣:
<input type="text" [(ng-model)]="model.name" />

我能用什么語言搭配 Angular 2 使用?

Angular 2 的 API 完全支持現在的 JavaScript(ES5標準),下一個版本的 JavaScript(ES6標準或ES2015),TypeScript 和 Dart。

繼續使用現在的 JavaScript 是非常好的選擇,我們強烈建議你深入研究一下 ES6 和 TypeScript(ES6的一個超級集合),這些會為你的產品帶來強大的提升。

ES6 為常用庫,比如協議和模組,提供了很多提升性的語法和標準。TypeScript 能為你帶來更好的代碼導航,IDE 中的自動重構,文件,查找錯誤,等等。

ES6 和 TypeScript 作為現在 ES5 的超級集合,十分簡單易用。這意味著你現有的全部代碼是有效的,并且能為它們添加一些新特性。

我應該利用代碼庫中的$watch做什么?

為了得到運行速度和可預測性,在 Angular 2 中,通過在 HTML 模板中或者組件指令中的注釋中申明地指定要看的表達式。

在很多應用與性能不相適的場合下, 你可以從 ES7 標準的可見性中,比如 JavaScript 中的 Rx.js 或者Dart 中的 Streams,獲得可見性的好處。

現在我能為應用的版本遷移做什么準備

模仿最好的實例,并使用 Angular 1 的組件和服務來構建你的應用,就像 AngularJS 樣式指南中所描述的。

原生升級能否使用新的組件路由器?

我們在 ng-conf2015 告知的升級計劃是基于某時間段中全視圖的升級,和兩個版本的 Angular 中的組間路由器的控制通訊。

我們得到的反饋是“好的,這具有增量性,但增量性還不夠。我們又重新設計如上的計劃。

有更多的細節你能夠透露嗎?

當然是的!在升級 Angular 1 到 Angular 2 的策略設計文檔。

我們在編寫一系列即將發布的公告,相關主題包括如下:

  • 把你對于的 Angular 1 相關知識映射,類比到Angular 2中。

  • 一組圍繞 Angular 2 細節的問答。

  • 帶有代碼示例的版本遷移的細致指導。

再回!

 本文由用戶 jopen 自行上傳分享,僅供網友學習交流。所有權歸原作者,若您的權利被侵害,請聯系管理員。
 轉載本站原創文章,請注明出處,并保留原始鏈接、圖片水印。
 本站是一個以用戶分享為主的開源技術平臺,歡迎各類分享!