繼Edge棄用后,微軟工程師再發(fā)萬字警示:React已過時(shí),也該換了!
當(dāng)前位置:點(diǎn)晴教程→知識(shí)管理交流
→『 技術(shù)文檔交流 』
以下為譯文: 在過去的十年里,我的工作重點(diǎn)是與團(tuán)隊(duì)合作,共同開發(fā)面向桌面和移動(dòng)端的 Web 產(chǎn)品。這讓我有機(jī)會(huì)近距離接觸了各種各樣的團(tuán)隊(duì)、產(chǎn)品和技術(shù)棧,回顧過往,我參與了超過 100 個(gè)項(xiàng)目。 雖然我個(gè)人更希望將大部分時(shí)間專注于改進(jìn) Web API,但往往事與愿違,與合作伙伴們的合作大多數(shù)時(shí)間都用于解決由“現(xiàn)代”前端框架(如 React、Angular 等)及其周圍文化所帶來的性能和可訪問性問題。這些問題在基于 React 的技術(shù)棧中尤為突出。 這令人不安,因?yàn)?React 已經(jīng)被很多人視為是一門過時(shí)的技術(shù),但它依然出現(xiàn)在新建的應(yīng)用程序中。 不過,也有一些人仍然堅(jiān)持認(rèn)為 React 是“現(xiàn)代”的技術(shù)框架。也許在今天這篇文章里,我們可以通過理解“現(xiàn)代”一詞來解釋這種情況,就像它在藝術(shù)中應(yīng)用一樣。React 和藝術(shù)作品一樣,并沒有展示當(dāng)代的設(shè)計(jì)或構(gòu)建技術(shù)。它們并非為了滿足當(dāng)前的需求或性能標(biāo)準(zhǔn)而構(gòu)建,而是基于過去的過時(shí)方法,并且在那個(gè)時(shí)代這些方法曾經(jīng)是最先進(jìn)的、最昂貴的。 為了讓更多的團(tuán)隊(duì)遠(yuǎn)離使用 React 帶來的后續(xù)困境,我基于最新的研究,分析當(dāng)前的局勢(shì),同時(shí)通過講座提醒管理者和開發(fā)人員注意當(dāng)前前端正統(tǒng)觀念的危害。 簡(jiǎn)而言之,在 2020 年代,不應(yīng)該再有人基于 React 開始新的項(xiàng)目。這一點(diǎn)無須質(zhì)疑。
客戶端復(fù)雜性最小化原則 在服務(wù)器上運(yùn)行的代碼完全計(jì)算出成本。服務(wù)器端系統(tǒng)的性能和可用性由提供服務(wù)的組織控制,延遲性則可以由開發(fā)人員和運(yùn)維工程師主動(dòng)管理。 相比之下,運(yùn)行在客戶端的代碼則是在“魔鬼的計(jì)算機(jī)”上運(yùn)行。用戶所體驗(yàn)到的延遲、客戶端資源,甚至可用的 API,都不在開發(fā)人員的控制范圍之內(nèi)。 客戶端 Web 開發(fā)或許最好可以將其理解為一種面向影響力的編程方式。一旦代碼離開數(shù)據(jù)中心,Web 開發(fā)人員能做的只是祈禱和希望。 因此,一個(gè)出奇有效的策略是減少代碼量。實(shí)際上,這意味著開發(fā)者可以優(yōu)先使用 HTML 和 CSS 而不是 JavaScript,因?yàn)?HTML 和 CSS 更加簡(jiǎn)潔,并且在壓縮時(shí)能有效減小文件大小,同時(shí)也能優(yōu)雅地在不同條件下降級(jí)工作。聲明式編程的方式能夠讓開發(fā)者通過發(fā)送較少的字節(jié)來實(shí)現(xiàn)更多的功能性界面(UI)。這些優(yōu)化不僅能提高網(wǎng)站的穩(wěn)定性(韌性),還能降低開發(fā)和維護(hù)成本,而這種效果隨著網(wǎng)站使用時(shí)間的增長(zhǎng)會(huì)成倍放大。 基于 React、Angular 和其他一些遺留的、面向桌面的 JavaScript 框架的技術(shù)棧,通常采取的做法與上述的減少代碼量的策略相反。雖然這些生態(tài)系統(tǒng)口頭上承諾要防止不必要的客戶端代碼過多,但實(shí)際上,它們往往會(huì)通過 NPM 包的合并,導(dǎo)致代碼中包含了大量冗余的庫(kù)和代碼,比如 core-js、lodash、underscore、為已不存在的瀏覽器提供的 polyfill、用戶空間的 ECC 庫(kù)、moment.js以及其他一百個(gè)類似的復(fù)雜庫(kù)。這些冗余的代碼和庫(kù)不僅增加了文件的體積,還可能帶來不必要的性能負(fù)擔(dān)。 如今這種情況已經(jīng)進(jìn)入失控狀態(tài),似乎 2024 年的 React 開發(fā)者在構(gòu)建聊天機(jī)器人時(shí),根本無法不包括那些 2010 年代的遺留庫(kù),甚至還要再加上至少一個(gè)非常笨重的 MathML 或 TeX 格式化庫(kù)來顯示公式,事實(shí)上,這種需求只會(huì)在極少數(shù)會(huì)話中才會(huì)出現(xiàn)。 當(dāng)前,公司的技術(shù)主管和經(jīng)理們需要打破這種魔咒,深入了解自己所做的決策對(duì)客戶端性能、效率和用戶體驗(yàn)的實(shí)際影響,承擔(dān)起更多關(guān)于客戶端技術(shù)決策的責(zé)任。實(shí)際上,這意味著在所有新的工作中禁止使用 React。 好吧,那又該怎么辦呢? 禁止使用 React 這個(gè)問題有兩種解讀觀點(diǎn),值得仔細(xì)區(qū)分:
那些做出正確產(chǎn)品決策的團(tuán)隊(duì),可以通過客觀的實(shí)驗(yàn)對(duì)比,解決上述狹義上的問題。具體來說,團(tuán)隊(duì)可以通過構(gòu)建多個(gè)小規(guī)模的概念驗(yàn)證(PoC)來測(cè)試不同方法的可擴(kuò)展性和局限性。這種做法不僅有效,而且很有趣,因?yàn)樗试S團(tuán)隊(duì)在明確的約束條件下嘗試新技術(shù)或方法,從而改善最終的用戶體驗(yàn)和結(jié)果。 注意:構(gòu)建 SPA(單頁應(yīng)用程序)或客戶端交互性模塊的開發(fā)者有很多選擇。這篇博客不會(huì)推薦具體的工具,但 Svelte、Lit、FAST、Solid、Qwik、Marko、HTMX、Vue、Stencil 等以及其他數(shù)十種當(dāng)代框架都值得關(guān)注。 盡管它們的初始成本較低,任何投資這些框架的團(tuán)隊(duì)仍然需要對(duì)客戶端負(fù)載和復(fù)雜度進(jìn)行嚴(yán)格控制,因?yàn)?JavaScript 的成本至少比同等 HTML 和 CSS 高出 3 倍(按每字節(jié)計(jì)算)。 毋庸置疑,技術(shù)棧的決策標(biāo)準(zhǔn)會(huì)隨著時(shí)間的推移而發(fā)生變化。可能是因?yàn)樯洗螌徱暭夹g(shù)棧時(shí)的條件發(fā)生了顯著的變化,或者是網(wǎng)站的用戶群體和產(chǎn)品經(jīng)理、技術(shù)主管預(yù)期的用戶群體之間差距很大。因此,收集相關(guān)數(shù)據(jù)來了解這些變化,可以幫助團(tuán)隊(duì)在做第一次決策時(shí)更快速地縮小選擇范圍,為后續(xù)的比較實(shí)驗(yàn)提供更有針對(duì)性的依據(jù)。 但我們花最多時(shí)間接觸的團(tuán)隊(duì)并不處于這種位置,也不會(huì)做上述這些事情。 很多人在問“如果不使用 React,那用什么?”時(shí),認(rèn)為自己是在問狹義的問題,但實(shí)際上他們正面臨廣義問題。令人震驚的是,很多(有能力、出于善意的)產(chǎn)品經(jīng)理和工程師沒有深入思考架構(gòu)的原因和背景,而是選擇跟隨潮流。 對(duì)于一些人來說,放棄 React 這種流行的技術(shù)框架,會(huì)讓他們感到迷茫,甚至懷疑自己是否還能理解這個(gè)世界。處于這種狀態(tài)的團(tuán)隊(duì),面臨的是關(guān)于技術(shù)選擇和價(jià)值觀的認(rèn)知危機(jī)。他們不確認(rèn)如何判斷自己的技術(shù)選擇是否優(yōu)于其他選擇,也不知道為什么會(huì)選擇這個(gè)技術(shù)棧而不是另一個(gè)? 很多人需要幫助去找到更合適的方法來解決前端問題。如今,框架主義(即依賴使用框架來解決問題的思想)已成為前端開發(fā)的主流理念。持有框架主義的人認(rèn)為,只要團(tuán)隊(duì)足夠努力地使用某個(gè)框架,所有的用戶問題都會(huì)得到解決。然而,這是邏輯錯(cuò)誤,甚至可以說是完全錯(cuò)誤的。事實(shí)上,唯一能使 Web 體驗(yàn)變得好的是關(guān)心用戶體驗(yàn)——特別是邊緣用戶的體驗(yàn)。技術(shù)來來去去,但始終能帶來差異的,是關(guān)心用戶。 通俗地說,這場(chǎng)斗爭(zhēng)最具挑戰(zhàn)性的地方在于說服經(jīng)理和技術(shù)主管,讓他們從用戶需求出發(fā)。正如全球知名咨詢公司 Public Digital 所言,“為用戶需求設(shè)計(jì),而非為組織便利設(shè)計(jì)。” 要做到這一點(diǎn),需要改變思維方式——從單純依賴承諾和想象,轉(zhuǎn)向基于實(shí)際的研究和證據(jù)來做決策。這與所謂的“無所不用其極的工程”相吻合,因?yàn)楣こ痰谋举|(zhì)是利用已知條件和限制,為用戶和社會(huì)創(chuàng)造切實(shí)可行的解決方案。 與之相對(duì)的是一種不切實(shí)際的幻想——認(rèn)為沒有約束條件,或者認(rèn)為那些限制根本不適用于你的產(chǎn)品。這種想法用一個(gè)詞總結(jié)就是“胡扯”。 現(xiàn)實(shí)中,要拒絕根深蒂固的“胡扯”做法并非易事。所謂的“框架主義”宣揚(yáng),改善用戶體驗(yàn)的方式是采用更多(或不同)的框架生態(tài)工具。乍一看,這讓信奉者有事可做,看起來像是在進(jìn)行工程實(shí)踐,實(shí)際上并非如此。這種做法甚至讓人深信不疑,只關(guān)注框架生態(tài)內(nèi)部的解決方案,而忽視框架之外更實(shí)際、更有效的選項(xiàng)。如果有一種非主流的方式對(duì)用戶更有幫助,“框架主義者”可能還會(huì)把它當(dāng)成錯(cuò)誤去排斥。更糟的是,如果沒人拿出數(shù)據(jù)和證據(jù)來反駁這些錯(cuò)誤做法,就很難證明它們的問題。結(jié)果,忽視用戶需求的做法會(huì)越來越荒謬,而質(zhì)疑這種做法的人反而可能被視為“異端”,甚至被打壓。 說白了,這一切都是“胡扯”。 現(xiàn)實(shí)主義的做法和框架主義正好相反。現(xiàn)實(shí)主義者不會(huì)沉迷于那些看似高深的概念,而是用數(shù)據(jù)和事實(shí)來評(píng)估用戶體驗(yàn)。他們關(guān)心的是真實(shí)情況,而不是理想化的假象。 要打破框架主義的迷思,最有效的工具就是為管理層提供真實(shí)的、以用戶為中心的系統(tǒng)表現(xiàn)數(shù)據(jù)。比如,可以使用 RUM(真實(shí)用戶監(jiān)測(cè))工具,像 Core Web Vitals 來分析網(wǎng)頁性能;或者通過實(shí)驗(yàn)室工具(比如 WPT)獲取具體的測(cè)試結(jié)果。同時(shí),監(jiān)測(cè)用戶的關(guān)鍵行為路徑,把這些數(shù)據(jù)和業(yè)務(wù)目標(biāo)結(jié)合討論,也能更快推動(dòng)改變。 像 RUM 和其他基準(zhǔn)數(shù)據(jù),能幫助團(tuán)隊(duì)擺脫盲目追逐框架的陷阱。因?yàn)閿?shù)據(jù)能清楚顯示:引入這些框架到底花了多少成本,實(shí)際能帶來多大的回報(bào)。只有用數(shù)據(jù)說話,才能讓團(tuán)隊(duì)做出真正理性的決策,而不是盲目“信仰”某些框架。
沒有什么有價(jià)值的東西丟失 通過政策禁止 React(或其他類似框架)的使用,既是一個(gè)有效減少成本的策略,也可以幫助團(tuán)隊(duì)把注意力轉(zhuǎn)向?yàn)橛脩籼峁└袃r(jià)值的產(chǎn)品。然而,要真正獲得更好的結(jié)果,僅僅限制某些框架是不夠的。必須徹底擺脫“框架主義”的影響,也就是避免盲目地依賴框架來做決策。如果只是避免了一種錯(cuò)誤(比如過度依賴 React),卻把省下的資源浪費(fèi)在其他類似的錯(cuò)誤上(比如換用另一個(gè)框架但仍然不關(guān)注用戶需求),最終不會(huì)有任何真正的進(jìn)步或收益。 針對(duì)上述廣義形式的問題,可以從以下幾個(gè)維度來做解答:
不同類型網(wǎng)站的最優(yōu)選擇 為了說明現(xiàn)實(shí)主義(注重實(shí)際效果)和框架主義(迷信框架工具)在實(shí)際應(yīng)用中的區(qū)別,以下提供了一些例子作為說明。回顧過去,我們通常選擇技術(shù)時(shí),會(huì)根據(jù)應(yīng)用程序處理的關(guān)鍵需求來決定,比如對(duì)數(shù)據(jù)的操作次數(shù)和用戶會(huì)話的持續(xù)時(shí)間。有些應(yīng)用程序的特點(diǎn)是用戶需要長(zhǎng)時(shí)間使用(會(huì)話時(shí)間長(zhǎng)),同時(shí)需要在界面中頻繁地、逐步地更新信息。在這種情況下,本地化的數(shù)據(jù)模型(例如,將數(shù)據(jù)存儲(chǔ)在用戶設(shè)備中以便快速處理)有助于更高效地應(yīng)用更新。然而,這種需求并不普遍,是一種特殊情況。 只有在這些特殊情況下,SPA 架構(gòu)才應(yīng)當(dāng)考慮。 并且,只有在確實(shí)需要單頁應(yīng)用程序(SPA)架構(gòu)時(shí),才應(yīng)該將那些專門用來支持本地?cái)?shù)據(jù)模型樂觀更新的工具(如前端框架和狀態(tài)管理工具)納入網(wǎng)站的架構(gòu)設(shè)計(jì)中。 選擇的關(guān)鍵不在于是否選擇 JavaScript 框架,而是是否應(yīng)該考慮支持 SPA 的工具。 對(duì)于大多數(shù)網(wǎng)站,答案顯然是“否”。 以下是一些示例情況: 信息性網(wǎng)站 旨在提供信息的網(wǎng)站幾乎總是應(yīng)該使用語義化的 HTML 構(gòu)建,并根據(jù)需要加入漸進(jìn)增強(qiáng)功能。 像 Hugo、Astro、11ty 和 Jekyll 這樣的靜態(tài)網(wǎng)站生成工具在許多情況下都能很好地工作。內(nèi)容變化較頻繁的網(wǎng)站應(yīng)該考慮使用“經(jīng)典”的 CMS 工具或像 WordPress 這樣的工具來生成 HTML 和 CSS。 對(duì)于博客、營(yíng)銷網(wǎng)站、公司主頁、公共信息網(wǎng)站這樣的應(yīng)用,它們的核心需求通常是展示內(nèi)容而非復(fù)雜的交互。因此,應(yīng)盡量減少在客戶端運(yùn)行的 JavaScript 代碼的數(shù)量和復(fù)雜性。這類網(wǎng)站不需要采用為支持 SPA(單頁應(yīng)用程序)設(shè)計(jì)的框架,因?yàn)檫@些框架是為更復(fù)雜的交互場(chǎng)景準(zhǔn)備的,而不是簡(jiǎn)單的內(nèi)容展示。 為什么語義化標(biāo)記和可選的漸進(jìn)增強(qiáng)是正確選擇? 信息性網(wǎng)站通常具有較短的會(huì)話時(shí)間,并且擁有由服務(wù)器管理的應(yīng)用數(shù)據(jù)模型;也就是說,頁面上顯示的內(nèi)容的真實(shí)來源總是由服務(wù)器管理和擁有。這意味著不需要客戶端的數(shù)據(jù)模型抽象或客戶端組件定義,這些可能需要從數(shù)據(jù)模型中進(jìn)行更新。 注:許多信息性網(wǎng)站包含作為獨(dú)立子應(yīng)用的生產(chǎn)力組件。像 WordPress 這樣的 CMS 由兩個(gè)不同的部分組成;一個(gè)低流量、高互動(dòng)性的編輯器界面供文章作者使用,一個(gè)高流量、低互動(dòng)性的閱讀者界面供讀者使用。漸進(jìn)增強(qiáng)應(yīng)考慮應(yīng)用于兩者,但對(duì)于沒有長(zhǎng)時(shí)間會(huì)話的讀者視圖來說,漸進(jìn)增強(qiáng)是絕對(duì)必要的。 電子商務(wù)網(wǎng)站 電子商務(wù)網(wǎng)站應(yīng)該使用服務(wù)器生成的語義化 HTML 和漸進(jìn)增強(qiáng)來構(gòu)建。 有許多工具可用于支持這種架構(gòu)。構(gòu)建電子商務(wù)體驗(yàn)的團(tuán)隊(duì)?wèi)?yīng)優(yōu)先選擇默認(rèn)不加載 JavaScript 的技術(shù)棧,并通過控制客戶端腳本來防止在關(guān)鍵業(yè)務(wù)指標(biāo)上出現(xiàn)回退。 為什么漸進(jìn)增強(qiáng)是正確的選擇? 電子商務(wù)網(wǎng)站的整體形式在過去 20 多年中一直保持穩(wěn)定:
在所有這些頁面類型中,將顯示一個(gè)普遍存在的登錄和購(gòu)物車狀態(tài)小部件。這個(gè)小部件以及網(wǎng)站的標(biāo)志,有時(shí)是唯一一致的元素。 從多年的經(jīng)驗(yàn)來看,電子商務(wù)網(wǎng)站的 UI 差異性較大,用戶停留時(shí)間也會(huì)因?yàn)橘?gòu)物行為的多樣性而變化。此外,像商品價(jià)格這樣的內(nèi)容需要實(shí)時(shí)更新,因此將應(yīng)用的狀態(tài)(比如購(gòu)物車信息或庫(kù)存)存儲(chǔ)在服務(wù)器端更為合理。為了讓電子商務(wù)網(wǎng)站加載得更快,最好的方法是優(yōu)化頁面的大小和加載速度。這包括積極使用緩存、優(yōu)化圖像和減小頁面體積,確保頁面盡量輕量化。 媒體網(wǎng)站 媒體消費(fèi)網(wǎng)站在用戶停留時(shí)間和內(nèi)容更新頻率方面差異很大。對(duì)于大多數(shù)此類網(wǎng)站,推薦采用“漸進(jìn)增強(qiáng)”的設(shè)計(jì)理念。也就是說,網(wǎng)站的基礎(chǔ)版本應(yīng)該是簡(jiǎn)單且易加載的,以確保核心內(nèi)容對(duì)所有用戶都可用。隨后,可以根據(jù)功能需求,逐步增加復(fù)雜性,比如添加動(dòng)態(tài)交互功能。 為什么漸進(jìn)增強(qiáng)和島嶼模式可能是正確的選擇? 許多媒體消費(fèi)網(wǎng)站的互動(dòng)功能(如評(píng)論區(qū)、點(diǎn)贊按鈕、推薦列表等)可以被視為相對(duì)獨(dú)立的小功能模塊。這些模塊像“互動(dòng)島嶼”一樣獨(dú)立運(yùn)行,擁有自己的數(shù)據(jù)模型,可以使用 Web 組件技術(shù)開發(fā),將其嵌入在一個(gè)更大的靜態(tài)頁面中。 何時(shí) SPA 可能是合適的選擇? 當(dāng)用戶瀏覽媒體內(nèi)容且需要持續(xù)進(jìn)行媒體播放(例如“迷你播放器”的 UI)時(shí),上述的設(shè)計(jì)方法就不再適用。原因在于當(dāng)前的 Web 平臺(tái)存在一個(gè)基本限制:當(dāng)用戶切換頁面時(shí),頁面內(nèi)容(例如正在播放的媒體)無法保留。因此,如果網(wǎng)站需要支持這樣的功能(如播放不中斷),應(yīng)該考慮使用 SPA 技術(shù),但要注意限制客戶端 JavaScript 的大小,避免性能下降。 另一個(gè)考慮使用 SPA 的情況是離線播放。因?yàn)樗枰?Service Worker 來管理本地緩存的媒體文件,以及需要有與服務(wù)器同步數(shù)據(jù)的方法(例如更新緩存或驗(yàn)證用戶權(quán)限)。 在這種情況下,輕量級(jí)的 SPA 框架可能是合適的,同時(shí)還可以使用像 Zero 或 Y.js 這樣的連接狀態(tài)彈性數(shù)據(jù)系統(tǒng)。 社交網(wǎng)站 社交媒體應(yīng)用的特點(diǎn)是,用戶使用時(shí)間長(zhǎng)短不一,而且通常涉及多媒體內(nèi)容。很多社交平臺(tái)會(huì)用“無限滾動(dòng)”的界面,讓用戶不斷加載新內(nèi)容,同時(shí)還支持復(fù)雜的功能,比如編輯帖子。這些功能設(shè)計(jì)上有明顯的分界點(diǎn),通常與用戶瀏覽的深度以及客戶端和服務(wù)器之間的數(shù)據(jù)處理方式有關(guān)。 為什么漸進(jìn)增強(qiáng)可能是正確的選擇? 大多數(shù)社交媒體的使用場(chǎng)景就是用戶在服務(wù)器上的數(shù)據(jù)模型基礎(chǔ)上,進(jìn)行一些簡(jiǎn)單的操作,比如“點(diǎn)贊”帖子等。另外,用戶會(huì)間隔性地看到新的內(nèi)容更新。這種模式很適合用一種“混合方法”來實(shí)現(xiàn),比如類似于 Hotwire 或 HTMX 那樣的技術(shù),把服務(wù)器和客戶端的功能結(jié)合起來。 SPA 何時(shí)可能是合適的選擇? 在社交媒體應(yīng)用中,有些功能可能需要更復(fù)雜的交互方式,比如“深度互動(dòng)區(qū)域”(或稱“島嶼”)、用于草稿帖子緩存的功能。這些部分與主頁面展示的內(nèi)容不同,需求更復(fù)雜,可以看成應(yīng)用的一部分。 如果需要支持離線功能,就需要把數(shù)據(jù)模型和用戶狀態(tài)的快照下載到客戶端。這需要結(jié)合構(gòu)建主應(yīng)用的可靠性來設(shè)計(jì)。團(tuán)隊(duì)可以考慮基于 Service Worker 的多頁面應(yīng)用(MPA),配合“流拼接”架構(gòu)。這種架構(gòu)主要通過 HTML 提供頁面,同時(shí)啟用離線優(yōu)先的邏輯和同步功能。但要注意,離線支持會(huì)對(duì)架構(gòu)產(chǎn)生很大影響,因此這個(gè)需求必須在項(xiàng)目開始時(shí)就明確。 注意:有些人認(rèn)為必須用 SPA 工具和框架才能構(gòu)建支持離線功能的漸進(jìn)式 Web 應(yīng)用(PWA),但實(shí)際上并非如此。PWA 也可以用“流拼接”架構(gòu)來構(gòu)建,通過 Service Worker 在客戶端實(shí)現(xiàn)類似服務(wù)器端模板化的效果。 隨著多頁面視圖無縫過渡技術(shù)的發(fā)展,MPA 架構(gòu)的 PWA 已經(jīng)可以在不依賴大型 JavaScript 包的情況下,實(shí)現(xiàn)不同用戶狀態(tài)之間的流暢切換。盡管框架社區(qū)可能需要幾年時(shí)間才能完全適應(yīng)這些技術(shù),但它們已經(jīng)可以被應(yīng)用,并且在基礎(chǔ)架構(gòu)和漸進(jìn)增強(qiáng)的場(chǎng)景中表現(xiàn)優(yōu)秀。 生產(chǎn)力應(yīng)用 面向文檔的生產(chǎn)力應(yīng)用可能是最難以理清的類別,因?yàn)閰f(xié)作編輯、離線支持和輕量級(jí)(快速)“查看”模式,且需保持文檔完整性,都是通用的產(chǎn)品需求。 以優(yōu)先級(jí)排序的數(shù)據(jù)存儲(chǔ)(例如電子郵件客戶端)可能非常適合使用 SPA 技術(shù)。但是否能帶來更好的用戶體驗(yàn),取決于用戶在會(huì)話中的操作深度以及初次加載的性能成本。如果處理不好,很容易失敗,正如之前的討論所提到的那樣。 類似地,各種編輯器應(yīng)用由于需要頻繁修改數(shù)據(jù),天然適合使用本地?cái)?shù)據(jù)模型和 SPA 架構(gòu)。然而,這類系統(tǒng)的復(fù)雜性往往會(huì)導(dǎo)致性能問題,成為長(zhǎng)期挑戰(zhàn)。因此,開發(fā)這些應(yīng)用的團(tuán)隊(duì)需要提前制定性能保障措施,比如明確關(guān)鍵用戶操作路徑,并部署適當(dāng)?shù)谋O(jiān)控工具。這有助于及時(shí)發(fā)現(xiàn)問題,避免出現(xiàn)嚴(yán)重的性能問題,讓用戶體驗(yàn)受損。 為什么 SPA 可能是正確的選擇? 編輯器類應(yīng)用通常會(huì)頻繁更新數(shù)據(jù),比如每次按鍵或鼠標(biāo)拖動(dòng)時(shí)都會(huì)更新內(nèi)容。通過采用“樂觀更新”的方式,可以讓用戶在編輯時(shí)享受到流暢的體驗(yàn):編輯的內(nèi)容立即顯示,同時(shí)后臺(tái)異步通知服務(wù)器進(jìn)行保存。 不過,團(tuán)隊(duì)需要注意,編輯器應(yīng)用有時(shí)也會(huì)被用作查看工具。如果前期加載的代碼包太大,無論是用來看內(nèi)容還是用來編輯,都可能導(dǎo)致加載時(shí)間過長(zhǎng),用戶體驗(yàn)變差。更麻煩的是,系統(tǒng)在加載頁面時(shí)往往無法區(qū)分用戶是只想查看內(nèi)容,還是準(zhǔn)備開始編輯。 要想在這種情況下取得成功,團(tuán)隊(duì)需要非常嚴(yán)格地控制代碼包的模塊化、分階段加載和延遲加載策略。例如,僅在用戶確實(shí)需要編輯功能時(shí)才加載相關(guān)組件。反之,如果團(tuán)隊(duì)缺乏對(duì)關(guān)鍵路徑資源變更的審批和管理,性能問題就會(huì)頻發(fā),導(dǎo)致用戶體驗(yàn)不佳。 其他應(yīng)用類別 有些應(yīng)用天生需要很強(qiáng)的互動(dòng)性,或者需要訪問本地設(shè)備的硬件,或者處理一些 HTML 本身無法直接處理的媒體類型,比如 3D CAD 軟件、編程編輯器、游戲流媒體、網(wǎng)頁游戲、媒體編輯軟件和音樂創(chuàng)作工具等。這些應(yīng)用的需求往往需要復(fù)雜的客戶端 JavaScript 界面,但即使是這些應(yīng)用,也應(yīng)該像做生產(chǎn)力工具一樣,經(jīng)過嚴(yán)格的評(píng)估,考慮以下問題:
這些類型的應(yīng)用在 Web 上是可以成功實(shí)現(xiàn)的,但需要非常小心謹(jǐn)慎。 ? “但是……” 許多管理者和技術(shù)負(fù)責(zé)人,一旦他們對(duì)框架主義(frameworkism)產(chǎn)生依賴,就不得不應(yīng)對(duì)一系列由其他過度反應(yīng)者(Over Reactors)所提出的看似合理、實(shí)則很容易被推翻的理由。仔細(xì)查看這些反對(duì)理由,你會(huì)發(fā)現(xiàn):其中沒有一個(gè)是真正將用戶的實(shí)際體驗(yàn)放在首位的。通過這種現(xiàn)象,往往就可以判斷出這些對(duì)話的本質(zhì)是什么。 “……我們需要快速行動(dòng)” 每當(dāng)聽到這樣的說辭時(shí),最好的回應(yīng)就是一個(gè)反問:“要多快?” 因?yàn)槟欠N“隨便用 NPM 把代碼東拼西湊”的開發(fā)模式,就算在價(jià)值 3000 美元的高端筆記本電腦上看似運(yùn)行良好,也很快就會(huì)讓團(tuán)隊(duì)陷入困境。這種思維模式的后果,從重大的可訪問性問題到足以損害品牌形象的低劣性能問題,這十年來幾乎每周都會(huì)出現(xiàn)在我的辦公桌上。 我可以明確告訴你,所有這些團(tuán)隊(duì)和產(chǎn)品都有一個(gè)共同點(diǎn):它們并沒有因此變得更快。一些你聽說過的或者你本周使用過的網(wǎng)站都曾向我們求助,我們也盡職盡責(zé)地提供了幫助。通常的解決方案是,花費(fèi)數(shù)周甚至數(shù)月的時(shí)間來解開這些由 JavaScript 造成的棘手難題。這種補(bǔ)救工作確實(shí)能修復(fù)由 JavaScript 濫用導(dǎo)致的收入和可訪問性問題,但在此期間團(tuán)隊(duì)的進(jìn)展將完全停滯——他們只能亡羊補(bǔ)牢,匆忙添加代碼質(zhì)量關(guān)卡、包大小控制及相關(guān)流程,以防止進(jìn)一步的倒退。 這種必要、痛苦且昂貴的補(bǔ)救措施,通常發(fā)生在最糟糕的時(shí)候,且?guī)缀醯貌坏街С郑@主要?dú)w因于 JavaScript 生態(tài)系統(tǒng)內(nèi)的緘默文化(omerta)。被困于這種體系中的管理者逐漸意識(shí)到,他們倉(cāng)促做出的決定并不容易調(diào)整。原本為了加速進(jìn)度而引入的復(fù)雜且難以理解的工具,現(xiàn)在反而成為了團(tuán)隊(duì)必須花大量時(shí)間去學(xué)習(xí)、深入了解并熟練操作的負(fù)擔(dān)。與此同時(shí),新功能發(fā)布的速度也會(huì)顯著放緩。 顯然,這并不是管理者當(dāng)初接受“我們需要快速行動(dòng)”這個(gè)理由時(shí)所期望的結(jié)果。 如果我們按照字面意思理解這一主張,即假設(shè)某個(gè)團(tuán)隊(duì)不會(huì)因此陷入困境,那么這句話隱含的想法大致是:現(xiàn)在沒有充足的時(shí)間把事情做到最好(所以用 React?),但以后會(huì)有時(shí)間返工。 然而,這種邏輯與“尋找產(chǎn)品市場(chǎng)契合點(diǎn)”的基本原則直接相悖。 與硅谷常見的觀念相反,找到產(chǎn)品需求的最佳方法是讓它盡可能廣泛地可用,然后再逐步優(yōu)化用戶體驗(yàn)。我曾合作過的團(tuán)隊(duì)經(jīng)常驚訝地發(fā)現(xiàn),消除使用障礙不僅能開拓新的市場(chǎng),還能在他們之前低估的其他地區(qū)提高利潤(rùn)率和業(yè)務(wù)成果。 當(dāng)然,如果你銷售的是奢侈品類型(即炫耀價(jià)值遠(yuǎn)高于實(shí)用價(jià)值的商品),那么優(yōu)先考慮其他因素而非可訪問性也無可厚非。但在幾乎所有其他類別中,產(chǎn)品質(zhì)量的回報(bào)可以理解為產(chǎn)品定位的清晰度。當(dāng)使用 React 作為權(quán)宜之計(jì)時(shí),實(shí)際上就是暗示了一種低質(zhì)量的體驗(yàn),而這種體驗(yàn)會(huì)直接弱化你服務(wù)的核心增長(zhǎng)邏輯。如果你的目標(biāo)是規(guī)模化而非排他性,那么為微軟早已停止銷售的老式桌面瀏覽器構(gòu)建功能,就絕對(duì)是一個(gè)戰(zhàn)略性錯(cuò)誤。 “……但 Facebook 用它就有效” 可以肯定的是,你的產(chǎn)品不是 Facebook,你遇到的問題與 Facebook 在 2010 年代初遇到的問題可能也截然不同;即使相似,效仿 Facebook 的做法也可能是一個(gè)糟糕的選擇。 而且實(shí)際上,這些工具對(duì) Facebook 本身都沒有起到多大作用。Facebook 只不過恰好在某些社交領(lǐng)域處于壟斷地位,因此可以“燒錢”。如果你的公司情況并非如此,那么最好不要過度依賴那些基于 Facebook 成功故事的決策邏輯。 “……可我們的團(tuán)隊(duì)已經(jīng)很熟悉 React 了” React 開發(fā)者本質(zhì)上就是 Web 開發(fā)者的一部分,他們需要在 CSS、HTML、JavaScript 和 DOM 這個(gè)生態(tài)系統(tǒng)中工作,這是不可避免的,但這也意味著 React 是技術(shù)棧中最容易被替換的一環(huán)。切換模板系統(tǒng)(JSX 本質(zhì)上就是模板語言)是 Web 開發(fā)者三十多年來一直熟練掌握的事情,即便是那些精通 Rails 和 ERB 等特定框架的人,也能輕松適應(yīng) Django、Laravel、WordPress 或 11ty 等其他項(xiàng)目。當(dāng)然,各個(gè)框架間確實(shí)存在差異,但所有 Web 開發(fā)者都是多面手,能夠在不同環(huán)境中游刃有余。 更重要的是,React的專業(yè)知識(shí)本身也并不具備特別高的價(jià)值。任何熟悉 React 那些復(fù)雜慣例的團(tuán)隊(duì),都能快速掌握 Preact、Stencil、Svelte、Lit、FAST、Qwik 等眾多更快、更小、更高效的客戶端響應(yīng)式系統(tǒng),且這些系統(tǒng)對(duì)開發(fā)者的認(rèn)知負(fù)擔(dān)要求更低。 “……這樣也方便招聘” 最近,科技行業(yè)發(fā)生了大規(guī)模裁員,我所認(rèn)識(shí)的許多才華橫溢、富有同理心、以用戶為中心的工程師都無緣無故地被解雇了,僅僅因?yàn)樗麄兊墓芾韺游茨茴A(yù)見疫情后市場(chǎng)的回歸正常波動(dòng)。也就是說,現(xiàn)在人才市場(chǎng)上正在進(jìn)行一場(chǎng)“大甩賣”,你可以根據(jù)需要提出任何技能要求,并且仍能找到非常合適的人選。 如果你招聘不到那些了解 Web 標(biāo)準(zhǔn)和基本原理的人才,請(qǐng)聯(lián)系我,我可以親自幫你制定招聘建議、職位描述、錄用標(biāo)準(zhǔn)及晉升指南,以便你能正確地重視這些人才:將他們視為被低估的英雄,他們將以極低的成本下為你的產(chǎn)品創(chuàng)造巨大價(jià)值,而無需花費(fèi)巨資去解決 React 社區(qū)終于承認(rèn)由框架主義(frameworkism)本身所導(dǎo)致的下一個(gè)問題。 簡(jiǎn)歷不是生死契約 即使你決定在面試過程中篩選具備 React 經(jīng)驗(yàn)的候選人,這也并不意味著你應(yīng)該使用 React。任何能夠駕馭復(fù)雜構(gòu)建工具、TypeScript 特性和 JSX 語法變體帶來的各種細(xì)微問題的人,都完全有能力適應(yīng)其他技術(shù)體系。 事實(shí)上,他們已經(jīng)在不斷變化的流行技術(shù)漩渦中工作了。技術(shù)的快速迭代是真實(shí)存在的,這意味著問題不在于“這些人能否迅速上手?”(答案必然是否定的,無論如何他們都需要花幾周時(shí)間來熟悉你的特定環(huán)境),而在于“在我們的團(tuán)隊(duì)生命周期中,哪種技術(shù)能提供最高的投資回報(bào)率?” 鑒于 React 及其他框架主義方案的高昂成本,在項(xiàng)目生命周期中,選擇當(dāng)下流行的框架并不會(huì)比選擇成熟穩(wěn)定的技術(shù)棧更有利。因此在長(zhǎng)期來看,選擇那些穩(wěn)定、可靠且易于維護(hù)的技術(shù)通常會(huì)帶來更高的回報(bào)。 關(guān)于“編程訓(xùn)練營(yíng)” 聽到管理者貶低那些從編程訓(xùn)練營(yíng)畢業(yè)的工程師,我就感到惡心,而這種現(xiàn)象似乎越來越常見。他們覺得:那些從編程培訓(xùn)營(yíng)出來的人——只是花錢學(xué)習(xí)課程大綱上內(nèi)容的人——沒有能力或不愿意學(xué)習(xí)其他技術(shù)棧,這簡(jiǎn)直是無稽之談。 編程訓(xùn)練營(yíng)的畢業(yè)生可能是初級(jí)開發(fā)者,他們對(duì)框架主義有著不同程度的理解和應(yīng)用,但這并不代表他們不具備學(xué)習(xí)能力或意愿。他們渴望做出好的成績(jī),而管理層應(yīng)該負(fù)責(zé)明確什么才是“做好工作”。許多新手開發(fā)者可能了解 React,但他們?cè)诼殬I(yè)生涯中會(huì)接觸和掌握十幾種其他工具,而 React 無疑是其中最復(fù)雜(且不必要)的一個(gè)。 認(rèn)為那些已經(jīng)掌握了 React 及其相關(guān)技術(shù)的恐怖之處的人,無法接受 DOM 生命周期方法、事件循環(huán)或現(xiàn)代 CSS,這簡(jiǎn)直是一種侮辱且毫無根據(jù)。這種不公平的刻板印象不僅限制了團(tuán)隊(duì)潛力,也凸顯了管理的失敗。 換句話說,這就是管理層的極大失敗。 “……現(xiàn)在每個(gè)人都有快速的手機(jī)了” 十多年來,框架主義一直堅(jiān)持一個(gè)核心觀點(diǎn):客戶端資源成本低廉,因此為了開發(fā)者的便利,犧牲一些用戶端性能是合理的。這一觀點(diǎn)已被證實(shí)是一場(chǎng)徹底的失敗。至少?gòu)?2012 年開始,移動(dòng)設(shè)備的興起就駁斥了這一論點(diǎn),而我們剛剛開始意識(shí)到問題的嚴(yán)重性。 所謂“現(xiàn)在每個(gè)人都有快速的手機(jī)”的論調(diào),首先暴露了提出者自身的無知,同時(shí)也寄希望于聽眾也不了解實(shí)際情況。任何試圖在網(wǎng)絡(luò)上立足的企業(yè)都無法承受這種錯(cuò)誤理念帶來的后果,你也沒有理由為了迎合這種錯(cuò)誤的信念而犧牲產(chǎn)品的質(zhì)量。 “……React 是行業(yè)標(biāo)準(zhǔn)” 這種說法,最多不過是一種令人感到安慰的謊言。 更糟糕的是,它可能是一種故意為之的虛假陳述,旨在掩蓋基于 React 的不同技術(shù)棧間的顯著差異。事實(shí)上,React 不是一個(gè)固定的技術(shù),而更像是一個(gè)包含多種選擇的生活方式:你需要決定使用函數(shù)組件還是類組件;是否采用 TypeScript;選擇哪個(gè)包管理器(如 npm、yarn 或 pnpm);以及使用哪種打包工具(如 webpack、esbuild、SWC 或 rollup)。此外,還有元工具(如 Vite、Turbopack 或 Nx)和狀態(tài)管理工具(如 Redux、MobX 或 Apollo)等選擇。甚至在 CSS 處理方面,也有不同的插件和方法可以選擇。例如,“CSS-in-JS”就是一個(gè)特別不合理的選項(xiàng)。 在超過 100 次的咨詢項(xiàng)目中,我從未見過兩個(gè)完全相同的 React 配置,除非是那些尚未更改 Create React App 默認(rèn)設(shè)置的小型項(xiàng)目。而這個(gè)工具本身也隨著 React 的發(fā)展經(jīng)歷了多次重大變更,最終從官方文檔中消失,不再是推薦的入門方式。 這一切都說明,所謂的“標(biāo)準(zhǔn)”并不存在。所有的技術(shù)和工具都在持續(xù)演變,任何告訴你“React 是行業(yè)標(biāo)準(zhǔn)”的人都不值得信任。 毫無意義的斷言 希望你能原諒我稍微偏離主題,探討一下“React 是行業(yè)標(biāo)準(zhǔn)”這一誤導(dǎo)性觀念為何會(huì)如此深入人心。 盡管有大量證據(jù)表明,這些技術(shù)甚至連那些被視為 React 成功案例的網(wǎng)站都無法有效運(yùn)作,為什么 React 仍然廣泛存在于現(xiàn)代前端開發(fā)的各個(gè)角落呢? 原因在于,那些自認(rèn)為無所不知的人們通過強(qiáng)力推廣實(shí)現(xiàn)了這一點(diǎn)。框架主義者往往用簡(jiǎn)單的斷言如“虛擬 DOM 意味著更快的速度”來主導(dǎo)每一項(xiàng)討論,但實(shí)際上他們對(duì)瀏覽器的工作機(jī)制一無所知,更不用說理解其替代方案帶來的高昂垃圾回收(GC)成本了。這種無知使他們能自信地宣稱 React 是“沒問題的”——即使在各個(gè)維度上都存在更經(jīng)濟(jì)高效的替代方案。 這些人并不值得認(rèn)真對(duì)待。你不需要把他們的話當(dāng)真,但你必須要反對(duì)他們,并建立以數(shù)據(jù)為驅(qū)動(dòng)、以用戶為核心的架構(gòu)。這些錯(cuò)誤決策的長(zhǎng)期成本是巨大的,正如我們所見,許多團(tuán)隊(duì)不得不尋求幫助,以修復(fù)那些號(hào)稱“高性能”的技術(shù)棧所帶來的性能問題。 “……生態(tài)系統(tǒng)……” 具體是指哪個(gè)部分呢?請(qǐng)極其明確地指出。哪些包對(duì) React 綁定得如此緊密,以至于團(tuán)隊(duì)不應(yīng)該考慮其他替代方案?這些包真的不能與 Preact 一起使用嗎?為了使用這些庫(kù),究竟需要付出多少成本才是合理的?因?yàn)檫@才是討論的核心。 即使你在開始時(shí)確實(shí)享受到了“生態(tài)系統(tǒng)”的好處,為什么你認(rèn)為這種優(yōu)勢(shì)會(huì)持續(xù)下去? 每個(gè)庫(kù)都存在被遺棄的隨機(jī)風(fēng)險(xiǎn)。即使是最常用的系統(tǒng),也會(huì)因 JS 工業(yè)圈的風(fēng)云變幻而失寵,最終讓你處于和一開始就選擇更自主構(gòu)建棧但經(jīng)驗(yàn)較少、掌控力較弱的情況下相同的位置。這真是個(gè)明智的交易嗎?你的老板會(huì)同意嗎? 順便問一句,那個(gè)“CSS-in-JS”的冒險(xiǎn)進(jìn)行得如何?你們還在寫類組件,還是已經(jīng)經(jīng)歷了一次大規(guī)模且不完全的遷移,而現(xiàn)在仍然在處理由此帶來的各種問題? 事實(shí)上,每一個(gè)作為 devDependencies 依賴項(xiàng)的包,現(xiàn)在或?qū)矶紝⒂上M(fèi)者全權(quán)負(fù)責(zé)。避免意外驚喜的唯一防線是,將 NPM 依賴視為一種高利貸,而抵押的資本是未來的工程能力。 防止這些成本失控的最佳方法是對(duì)每個(gè) UI 工具和構(gòu)建系統(tǒng)的依賴進(jìn)行全面審查和批準(zhǔn)。如果你的團(tuán)隊(duì)不愿意承擔(dān)所有這些系統(tǒng)的所有權(quán)、修復(fù)和改進(jìn)責(zé)任,那它們就不應(yīng)該成為你技術(shù)棧的一部分。 “……Next.js 可以很快” 你覺得自己幸運(yùn)嗎?真的覺得幸運(yùn)嗎?——因?yàn)橐獙?shí)現(xiàn)這一概率,你需要相當(dāng)?shù)男疫\(yùn)。 用 Next.js 構(gòu)建的網(wǎng)站性能明顯不如那些 HTML 優(yōu)先的系統(tǒng),如 11ty、Astro 等。 Next.js 不僅難以擴(kuò)展,而且它捆綁 React 的做法就像帶著沉重的枷鎖,這是雙重不利因素。任何 Next.js 站點(diǎn)默認(rèn)延遲加載的龐大 JavaScript 負(fù)載會(huì)與其他業(yè)務(wù)關(guān)鍵的延遲內(nèi)容爭(zhēng)奪帶寬,這還不算添加任何自定義組件或路由時(shí)的負(fù)擔(dān)。即使使用了 React 服務(wù)器組件情況也是如此。換句話說,Next.js 是一個(gè)快速燒錢的選擇,同時(shí)會(huì)將你鎖定在一個(gè)由風(fēng)險(xiǎn)投資支持的初創(chuàng)公司專有的 API 中。 Next.js 從一開始就不是最優(yōu)選,并且隨著項(xiàng)目的推進(jìn),其劣勢(shì)愈發(fā)明顯。難怪只有那些用戶基礎(chǔ)極富有的 Next.js 站點(diǎn),或者得到了 Vercel 精心調(diào)優(yōu)支持的站點(diǎn),才會(huì)表現(xiàn)出較好的性能。 所以,你覺得自己足夠幸運(yùn)嗎? “……React Native!” React Native 是一種制作緩慢應(yīng)用的好方法,且需要不斷調(diào)試;同時(shí),它也是制作糟糕網(wǎng)站的極佳選擇,甚至曾經(jīng)作為其成功案例的一些公司也已經(jīng)逐漸放棄了它。 那些希望通過與網(wǎng)站共用代碼庫(kù)向應(yīng)用商店交付引人注目的移動(dòng)體驗(yàn)的公司,應(yīng)該更傾向于研究 Trusted Web Activities 和 PWABuilder。如果這些方案不可行,Capacitor 和 Cordova 也能提供類似的好處。這些方法可以讓大多數(shù)原生功能可用,但將 UI 投資集中在 Web 端,通過單一路徑提供可見性和控制力,從而減少重復(fù)優(yōu)化和可訪問性問題帶來的困擾。 該文章在 2024/12/11 11:02:45 編輯過 |
關(guān)鍵字查詢
相關(guān)文章
正在查詢... |