對微前端的11個錯誤認識

本文最初發佈於Bits and Pieces博客,經原作者授權由InfoQ中文站翻譯並分享。

微前端是一個可以追溯到多年前的新趨勢。隨着新方法的出現以及各種挑戰被克服,它們正在慢慢地進入主流。但遺憾的是,許多非常明顯的認識誤區,讓許多人很難理解微前端到底是什麼。

簡而言之,微前端就是將微服務的一些好處引入前端。除此之外,我們不應該忘記,微服務也不是什麼“銀彈”。

提示:要在微前端或任何其他項目之間共享React/Angular/Vue組件,可以使用像Bit這樣的工具。它允許你從任何代碼庫中“harvest”組件,並將它們共享到bit.dev的一個集合中。它讓團隊可以在任何存儲庫中使用你的組件。使用它可以優化協作、加速開發和保持UI一致性。

示例:在bit.dev中查找共享React組件

認識誤區

我想列一下在過去幾個月中,我最常聽到的關於微前端的誤解。先從從一個明顯的例子開始。

微前端需要JavaScript

目前,許多微前端解決方案都是JavaScript框架。這怎麼可能錯呢?JavaScript不再是可選的。每個人都想要高度交互的體驗,而JS在提供這些體驗中發揮着至關重要的作用。

除了加載速度快、可訪問Web應用的優點外,還有其他因素應該考慮。因此,許多JavaScript框架都提供了isomorphic渲染能力。最終,這讓它們不僅能夠在客戶端進行拼接(stitch),還能在服務器上準備好一切。如果有性能要求(如第一次有意義渲染的初始時間),這個選項聽起來很不錯。

請記住,isomorphic渲染有其自身的挑戰。

然而,即使一個JavaScript解決方案沒有提供isomorphic呈現,這也沒什麼問題。如果不想在構建微前端時使用JavaScript,我們當然可以這樣做。有許多模式,其中很多根本不需要JavaScript。

考慮一種“比較舊的”模式:使用<frameset>。我聽見你笑了?好吧,有一些現如今人們試圖做的分割,它以前就支持了(下文有更詳細的討論)。一個頁面(可能由另一個服務渲染)負責菜單,而另一個頁面負責標題。

<frameset cols="25%,*,25%">
  <frame src="menu.html">
  <frame src="content.html">
  <frame src="sidebar.html">
</frameset>

如今,我們使用更靈活(且仍然受到活躍支持)的<iframe>元素。它們提供了一些很好的特性——最重要的是使得不同的微前端相互隔離,但仍然可以通過postMessage進行通信。

微前端只在客戶端有效

在JavaScript認識誤區之後,這是下一個層次。當然,在客戶端有多種技術可以實現微前端,實際上,我們甚至不需要<iframe>或任何類似的技術。

微前端可以像服務器端“includes”一樣簡單。有了諸如Edge Side Includes之類的高級技術,這將變得更加強大。如果我們排除了在微前端功能中實現的微前端場景,那麼即使是簡單的鏈接也可以很好的工作。最終,微前端解決方案也能像小而獨立的服務器端渲染器一樣簡單。每個渲染器可能只有一個頁面那麼小。

下圖展示了在反向代理中發生的更高級的拼接:

通過反向代理實現服務器端拼接

當然,可能JavaScript有許多優點,但它仍然高度依賴於你試圖通過微前端解決的問題。根據你的需要,服務器端解決方案可能仍然是最好的(或者至少是更好的)選擇。

你應該使用多個框架

在幾乎每一個關於微前端的教程中,不同的部分不僅由不同的團隊開發,而且使用了不同的技術。這是假的。

適當的微前端方法可能使用不同的技術,但是,這不應該是目標。我們做微服務也不只是爲了在後端拼湊技術。如果我們使用多種技術,那只是因爲我們獲得了一個特定的好處。

我們的目標應該始終是某種統一性。最好的方法是考慮一個新項目:我們會怎麼做?如果答案是“使用單一框架”,那麼我們就走上正軌了。

長遠來看,有很多原因可以解釋爲什麼應用程序中會出現多個框架。可能是遺留的,可能爲了方便,也可能是一個概念驗證。無論是什麼原因:能夠處理這種場景還是不錯的,但它絕不應該是開始就希望達到的狀態。

不管你的微前端框架多高效——使用多個框架總是要付出不可忽視的代價。不僅初始渲染會花費更長的時間,而且內存消耗也會朝着錯誤的方向發展。不能使用方便模型(例如,針對某個框架的模式庫)。需要更多的重複。最終,程序的Bug數量、不一致行爲和可感知的響應性都會受到影響。

按技術組件劃分

一般來說,這沒有多大意義。我還沒見過微服務後端的數據處理在一個服務中而API在另一個服務中。通常,服務由多個層組成。雖然某些技術內容(如日誌記錄)肯定會引入到公共服務中,但有時也會使用諸如Sidecar之類的技術。此外,還需要通用服務編程技術。

對於微前端,情況也是如此。爲什麼一個微前端只能做菜單?每個微前端都有相應的菜單嗎?拆分應該根據業務需求來做,而不是技術決策。如果你讀過一些關於領域驅動設計的書,你就會知道它是關於定義這些領域的——而這個定義與任何技術要求無關。

考慮以下劃分:

按佈局分解成微前端

這些都是技術組件,和微前端無關。在一個真實的微前端應用程序中,屏幕可能看起來是這樣的。

按領域分解成微前端

的確,這裏的拼接要複雜得多,但這是一個可靠的微前端應用程序應該爲你提供的!

不應該共享任何東西

不。你應該共享那些值得共享的東西。你絕對不應該共享所有東西(見下一條)。但要做到始終如一,你至少需要共享一套原則。至於是通過共享庫、共享URL,或者只是在構建或設計應用程序時使用的文檔,那就不重要了。

對於微服務,“無共享”架構如下圖所示:

微服務的“無共享”架構

在瀏覽器中,這將導致使用<iframe>,因爲目前沒有其他方法可以防止資源泄漏。使用影子DOM,則CSS可能會被隔離,但腳本層面仍然能訪問所有內容。

即使想遵循無共享的架構,我們也會遇到麻煩。

當然,共享的程度越深(例如,使用一個通過應用shell追加到DOM的共享庫),就越會出問題。另一方面,共享程度越淺(例如,只是一個指定基本設計元素的文檔),就會出現更多的不一致性。

應該共享一切

絕對不是。如果這樣想,那麼單體更有意義。就性能而言,這可能已經是一個問題了。什麼可以延遲加載?我們能去掉一些東西嗎?但真正的問題是依賴管理。什麼都不能更新,因爲它可能會破壞某個東西。

共享部件的好處是一致性保證。

現在,如果我們共享所有的東西,我們就是用複雜性來換一致性。這種一致性是不可維護的,因爲複雜性會在每個角落引入Bug。

問題的根源在於“依賴地獄”。下圖很好地說明了這一點。

簡而言之,如果一切都相互依賴,那麼我們就會有依賴問題。僅僅更新一個方框就會影響整個系統。一致嗎?確實。簡單的?絕不。

微前端只是Web端的

爲什麼只是Web?誠然,到目前爲止,我們接觸到的主要是Web,但其概念和想法可以應用於任何類型的應用程序(移動應用、客戶端應用……甚至是CLI工具)。在我看來,微前端只是“插件架構”的一個花哨叫法。不過,插件接口如何設計,以及運行使用插件的應用程序需要具備什麼條件,這就是另外一回事了。

下圖顯示了一個非常通用的插件架構,來自Omar Elgabry

通用插件架構

該架構並沒有在哪裏運行的概念。它既可以在手機上運行,也能在Windows上運行,甚至還能在服務器上運行。

微前端需要大型團隊

爲什麼?如果解決方案超級複雜,那麼我肯定會找一個簡單的。有些問題需要複雜的解決方案,但好的解決方案通常是簡單的。

根據場景的不同,它甚至可能不需要一個分佈式團隊。擁有分佈式團隊是採用微前端的首要原因之一,但這不是唯一原因。另一個很好的理由是特性的粒度。

如果從業務的角度來看微前端,那麼你就會發現,擁有啓用和關閉特定特性的能力是很有意義的。針對不同的市場,使用不同的微前端。回到一個簡單的權限模式,這是有意義的。不需要編寫代碼來根據特定條件打開或關閉某些東西。所有這些都留給公共層,可以根據(可能是動態的)條件激活或停用。

這樣,不能(或不應該)使用的代碼也不會被交付。雖然這不應該是一個保護層,但它肯定是一個便捷(和性能)層。用戶不會感到困惑,因爲他們看到的是他們能做的。他們看不到沒有交付的功能,所以沒有字節浪費在不可用的代碼上。

微前端無法調試

對於任何類型的實現(或供討論的底層架構),開發經驗都可能遭到削弱。應對這種情況的唯一方法是開發人員優先。實現中的第一原則應該是:使調試和開發成爲可能。採用標準的工具。

有些微前端框架根本不接受這一點。有些需要在線連接、專用環境、多重服務……這不應該是標準,也絕不是常態。

微服務需要微前端(或反過來)

解耦的模塊化後端可能爲解耦前端打下了一個很好的基礎,但通常情況下,情況並非如此。後端單體,前端模塊化,也是完全可行的,例如,爲簡化個性化可能就要結合授權、權限和市場。

實際上,同樣,微服務後端並不能證明適合將類似的模式應用於前端。許多微服務後端都是由單用途的應用程序操作的,它們的功能沒有增加,只是外觀發生了改變。

微前端需要單存儲庫

我已經讀到過好幾次,要創建一個微前端解決方案,就需要利用單存儲庫,最好使用像Lerna這樣的工具。我不認可這一點。當然,單存儲庫有一些優點,但也有明顯的缺點。

雖然有一些微前端框架需要聯合CI/CD構建,但大多數都不需要。聯合CI/CD構建通常會導致單存儲庫,因爲其設置要簡單得多。但對我來說,這是單體重新打包。如果你在單存儲庫上進行聯合構建,那麼你就失去了讓微前端富有吸引力的兩個非常重要的優點:

  1. 獨立部署
  2. 獨立開發

不管怎樣,如果你看到微前端解決方案需要單存儲庫:那樣做就行。一個精心設計的單體系統可能會更好,它不會有分佈式系統的所有問題。

結論

微前端技術並不適合所有人。我不認爲微前端是未來的發展趨勢,但我也相信它們在未來會發揮重要作用。

原文鏈接:

https://blog.bitsrc.io/11-popular-misconceptions-about-micro-frontends-d5daecc92efb

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章