開發(fā)經(jīng)驗總結(jié):從項目搭建到性能優(yōu)化的全套思路)
做了幾年Vue網(wǎng)站開發(fā)從最初拿官方文檔當(dāng)小說啃到后來在真實項目里被各種邊界情況毒打積累了不少心得。這篇文章不是官方文檔的復(fù)述而是我在實際項目中總結(jié)出的整套Vue開發(fā)思路從為什么選Vue、項目怎么搭才順手、組件到底怎么拆到響應(yīng)式原理和性能排查最后再把新手最容易踩的坑一次性列出來。適合剛?cè)腴T想建立整體認知的人也適合已經(jīng)寫了一陣子Vue但總覺得差點意思的開發(fā)者。很多人學(xué)Vue是直接從組件寫起跟著教程復(fù)制一個to-do list跑通了就覺得自己會了。但等接手真實項目遇到數(shù)據(jù)改了視圖不變、組件瘋狂重渲染、路由權(quán)限繞來繞去才發(fā)現(xiàn)自己只是知道語法不懂框架的脾氣。我希望這篇文章能幫你在動手之前先建立一套相對清晰的心智模型再帶著模型去寫代碼會順手很多。1. 為什么選Vue框架選型背后的實際考量1.1 漸進式設(shè)計從“一個頁面”到“一套系統(tǒng)”的平滑過渡Vue最打動我的地方不是某個炫技特性而是它的漸進式思路。你可以只在頁面里引入一個全局腳本把某個表單交互做掉也可以配上路由、狀態(tài)管理、服務(wù)端渲染做成一個完整的中后臺系統(tǒng)。這個“按需取用”的特性在實際項目中非常實用。很多團隊不是從零開始選型而是接手一個老項目想在保留現(xiàn)有架構(gòu)的前提下逐步引入新框架。Vue的這種設(shè)計讓遷移成本低很多先在一個角落用起來驗證效果后再逐步擴大范圍。比如我在一個舊項目中引入Vue最初只是用它渲染一個動態(tài)表格后來才慢慢把篩選、彈窗、表單校驗都遷進來。整個過程沒有“推倒重來”的陣痛業(yè)務(wù)連續(xù)性保住了技術(shù)債也還得起。對比一下React它的函數(shù)式理念更純粹但初始學(xué)習(xí)曲線會陡一些JSX、不可變數(shù)據(jù)、Hooks規(guī)則剛接觸時很容易寫出“看起來能跑但思路混亂”的代碼。Angular則更像一套全家桶約束多、概念多、依賴注入、RxJS適合大團隊統(tǒng)一規(guī)范但對小團隊和個人項目來說光是想清楚模塊劃分就要折騰很久。Vue的好處是它不強求你一次性接受所有概念你可以先寫模板再接觸選項式API最后才上組合式API和TypeScript每一步都有一個自然的“剛好夠用”的層次。1.2 響應(yīng)式數(shù)據(jù)模型上手快、心智負擔(dān)低的根本原因Vue的響應(yīng)式系統(tǒng)讓人感覺“數(shù)據(jù)改了視圖就自動更新”這個體驗在小項目里特別爽。你不需要像用原生DOM那樣手動操作節(jié)點也不用像早年的jQuery那樣對一堆DOM事件來回綁定。模板和數(shù)據(jù)之間的關(guān)聯(lián)是聲明式的代碼量直接少了一大截。舉個例子做一個篩選聯(lián)動選完省份城市下拉框要跟著刷新。用原生寫法你需要監(jiān)聽change事件然后查DOM、清空選項、構(gòu)造新選項、再綁定事件。用Vue你只需要維護一個cities數(shù)組省份一變計算屬性或偵聽器就會重新計算模板自動重新渲染??雌饋硎切∈碌麄€項目里到處都是這種“小事”積累起來就是把開發(fā)周期砍半的效力。當(dāng)然響應(yīng)式不是魔法。Vue 2用的是Object.defineProperty只能攔截對象屬性的讀取和賦值所以新增屬性、數(shù)組下標(biāo)修改這些操作會失效。Vue 3改用Proxy可以代理整個對象所以動態(tài)增刪屬性、監(jiān)聽數(shù)組變化都比Vue 2更徹底。這個區(qū)別在你調(diào)試“數(shù)據(jù)明明改了視圖卻沒反應(yīng)”這種問題時特別關(guān)鍵。很多時候不是框架bug而是你還在用Vue 2時代的寫法操作Vue 3的數(shù)據(jù)自然會踩坑。1.3 什么時候不要選Vue雖然我對Vue有偏好但必須承認它不適用于所有場景。如果你的項目是一個超大型、需要高度類型推導(dǎo)和嚴(yán)格架構(gòu)約束的團隊項目并且團隊里已經(jīng)有React或Angular的資深專家那沒必要強行換Vue。Vue的靈活是一把雙刃劍靈活意味著可選方案多團隊如果沒有統(tǒng)一規(guī)范不同人寫出來的代碼風(fēng)格可能差異很大。另外如果你的核心業(yè)務(wù)高度依賴原生WebGL、復(fù)雜動畫編排或者需要直接嵌入一些非Vue生態(tài)的庫Vue提供的那層抽象反而可能成為阻力。這時候不如直接用原生或更底層的框架。選型這事兒沒有“最好的框架”只有“最適合當(dāng)前團隊和業(yè)務(wù)的框架”。我的經(jīng)驗是中小型團隊、業(yè)務(wù)迭代快、需要快速出活Vue幾乎是性價比很高的選擇。2. 項目搭建與工程化實踐從零到一的關(guān)鍵選擇2.1 腳手架我用Vite替代了Vue CLI之后回不去了新項目啟動過去官方推薦vue-cli底層是webpack配起來繁瑣啟動慢改個配置要翻半天文檔?,F(xiàn)在我用Vite啟動速度真的是秒開。Vite開發(fā)環(huán)境用原生ES Module加載不用像webpack那樣把所有模塊預(yù)先打包成bundle所以冷啟動快熱更新也快改動代碼后刷新幾乎是即時的。我第一次用Vite搭項目時還有點不放心擔(dān)心插件生態(tài)跟不上。實際用了才發(fā)現(xiàn)主流工具基本都有Vite插件版本Vue、Router、Pinia、ESLint、Prettier、UnoCSS全都能在Vite里跑得很順暢。而且Vite內(nèi)置開發(fā)服務(wù)器和構(gòu)建優(yōu)化生產(chǎn)環(huán)境用Rollup打包產(chǎn)物體積控制和Tree Shaking做得也不錯。但Vite也不是完全沒有坑。它要求Node版本比較新舊項目如果鎖定在老版本Node上升級成本需要考慮。另外有些依賴包只提供CommonJS版本在Vite里需要配置optimizeDeps之類的參數(shù)才能正常工作。新手遇到這類問題容易懵其實就是專門處理一下依賴預(yù)構(gòu)建的兼容性就好。提示如果你現(xiàn)在要開新項目直接用Vite Vue 3不要再走Vue CLI的老路了。老項目用什么維持什么新項目就別給自己添堵。2.2 目錄結(jié)構(gòu)照著這個分層維護半年也不亂項目搭起來了目錄結(jié)構(gòu)決定了后面代碼能清晰多久。我踩過“把所有組件都塞到components里頁面與頁面之間邏輯互相糾纏”的坑后來慢慢總結(jié)出一套適合中后臺項目的分層方式src/api所有后端接口請求按業(yè)務(wù)模塊拆文件src/assets靜態(tài)資源圖片、字體、全局樣式src/components通用組件和具體業(yè)務(wù)無關(guān)src/composables組合式函數(shù)封裝可復(fù)用的邏輯src/layouts頁面布局組件比如側(cè)邊欄頂欄的框架src/router路由配置與守衛(wèi)src/storesPinia狀態(tài)管理按模塊拆分src/views頁面級組件一個路由對應(yīng)一個src/utils工具函數(shù)純邏輯不依賴Vuesrc/typesTypeScript類型定義這樣分層最大的好處是“看路徑就知道這個文件是干什么的”。你不需要翻遍代碼才能找到接口封裝也不需要在一個巨型組件里找業(yè)務(wù)邏輯。尤其是在團隊協(xié)作的時候新人接手項目能快速定位問題域。我見過有人把Api請求直接寫在組件里當(dāng)時覺得省事后來接口字段變了要全局搜索好幾個組件逐一修改非常痛苦。統(tǒng)一放到api目錄后改動一個文件就好組件的職責(zé)也純粹了。2.3 狀態(tài)管理選型Pinia好在哪里Vue 3時代狀態(tài)管理我直接選Pinia基本不用猶豫。Pinia的設(shè)計比Vuex簡潔太多去掉了mutations的概念直接改state配合Composition Api的寫法代碼體量小很多而且天然支持TypeScript。舉個例子一個用戶登錄狀態(tài)的管理Vuex需要定義state、mutations、actions、getters四件套還要考慮模塊命名空間寫起來很儀式感。Pinia直接定義一個useUserStore內(nèi)部放state和action組件里調(diào)用store的方法就直接改數(shù)據(jù)清爽得很。Pinia還解決了Vuex的一個長期痛點模塊嵌套太深時mapState和mapActions寫起來繞。Pinia里每個store都是獨立的通過storeToRefs之類的輔助函數(shù)可以很方便地解構(gòu)使用心智負擔(dān)低多了。不過狀態(tài)管理也不是用得越多越好。我的原則是只在多個不相關(guān)的組件需要共享同一份數(shù)據(jù)時才用store比如用戶信息、權(quán)限、購物車、全局配置。如果只是父子組件傳值那就用props和emit不要把所有東西都塞到store里否則store變成一個大垃圾箱調(diào)試起來很痛苦。2.4 環(huán)境變量與接口封裝最容易翻車的基礎(chǔ)建設(shè)環(huán)境變量這塊Vite默認只有import.meta.env你需要把自定義變量放到.env.development和.env.production里變量名前綴必須是VITE_才暴露給前端。比如VITE_API_BASE_URL/api代碼里用import.meta.env.VITE_API_BASE_URL訪問。接口封裝我用axios作為基礎(chǔ)網(wǎng)絡(luò)庫然后在api目錄里做一個統(tǒng)一實例配置好請求頭、超時時間、攔截器。攔截器里做兩件最重要的事請求攔截器統(tǒng)一攜帶token響應(yīng)攔截器統(tǒng)一處理HTTP錯誤碼和業(yè)務(wù)錯誤碼比如401跳登錄、500提示服務(wù)器異常。這樣每個業(yè)務(wù)模塊的接口函數(shù)只需要負責(zé)拼接地址和傳參不需要重復(fù)寫錯誤處理邏輯。這里有一個容易踩的坑后端返回的錯誤信息結(jié)構(gòu)不統(tǒng)一。有的接口返回{ success: false, msg: xx }有的返回{ code: 1, message: xx }如果你在攔截器里硬編碼了某一種結(jié)構(gòu)遇到另一個接口就掛了。最好是和后端提前約定好統(tǒng)一的返回格式或者在攔截器里做兼容處理。這個看似基礎(chǔ)但實際項目中幾乎每個團隊都要在這上面消耗不少時間。3. 組件化開發(fā)組件不是“越長越好”而是“越清晰越好”3.1 組件設(shè)計的三條邊界責(zé)任、可復(fù)用性、通信成本寫組件最容易出現(xiàn)的錯誤就是“一個組件負責(zé)太多事情”。我今天還看到過有人把表格、表單、彈窗、分頁全部塞進一個BigThing.vue四千多行代碼看著就跑不動。組件拆分的邊界我認為可以從三個維度考慮第一是責(zé)任邊界一個組件只做一件事。表格組件就負責(zé)渲染和操作行數(shù)據(jù)彈窗組件只負責(zé)顯示和關(guān)閉業(yè)務(wù)邏輯放到外層頁面或?qū)iT的composable里。第二是可復(fù)用性邊界你可以問自己“這個組件在另一個頁面能不能用”如果答案是不能可能它不應(yīng)該叫通用組件而應(yīng)該放在業(yè)務(wù)模塊里。第三是通信成本邊界組件嵌套層級太深props和emit反復(fù)中轉(zhuǎn)至少超過三層就考慮用插槽或者放到store里別為了“完全解耦”把組件之間的通信搞得比直接改store還費勁。3.2 組合式API我更推薦組件的邏輯以“功能”聚合Vue 2時代寫選項式API把一個功能的邏輯拆成data、computed、methods、watch幾部分一個稍微復(fù)雜的組件里代碼就像在幾個區(qū)域之間來回蹦跶。組合式API最大的改變是允許你按“功能”去組織代碼而不是按“選項類型”去組織。我后來寫組件的基本習(xí)慣是把邏輯先用script setup里的一組相關(guān)變量、函數(shù)、computed、watch放一起形成一個一個的“邏輯塊”。比如一個訂單列表組件里面有加載訂單、篩選訂單、排序、分頁我就會把跟訂單加載相關(guān)的邏輯放在一起跟篩選相關(guān)的放在一起跟分頁相關(guān)的放在一起。這樣看代碼的時候一個功能的所有相關(guān)代碼都在一個區(qū)域里維護起來非常順。組合式函數(shù)可以繼續(xù)抽離重復(fù)邏輯。比如“表格加載數(shù)據(jù)”這個動作很多頁面都有那我就可以寫一個useTable組合式函數(shù)把loading、data列表、分頁參數(shù)、刷新方法都封裝進去組件里直接調(diào)用就行。這個路子我實踐下來確實能顯著減少重復(fù)代碼也讓組件看起來特別干凈。3.3 Props、事件、插槽組件之間的溝通語言Props和事件是父子組件通信的基本方式。Props要寫得克制只傳你需要的不要傳一個整對象進去然后又用一堆watch去拆它這樣容易讓Vue追蹤不到依賴。事件命名建議統(tǒng)一風(fēng)格我習(xí)慣用on開頭比如on-search、on-close這樣語義清楚別人接手時一看就知道這個組件能做什么。插槽是Vue一個很容易被低估的特性。當(dāng)組件內(nèi)部布局有變化時props和事件很難滿足。比如一個通用卡片組件頭部、內(nèi)容、底部在業(yè)務(wù)里都有自定義需求如果你用props去傳一堆HTML模板字符串又齷齪又難維護。正確的做法是用具名插槽template div classcard header v-if$slots.header slot nameheader / /header main slot / /main footer v-if$slots.footer slot namefooter / /footer /div /template這樣卡片的框架是固定的內(nèi)容區(qū)域完全交給使用方自己填充。插槽讓組件的擴展能力上了一個臺階。3.4 組件通信的“潛規(guī)則”什么時候不要用props組件通信方式包括props、事件、v-model、provide/inject、Pinia。很多人喜歡一股腦用props傳遞所有數(shù)據(jù)結(jié)果組件層級一深中間層全都是無意義的轉(zhuǎn)發(fā)。我的經(jīng)驗是對于深層嵌套的跨層級傳遞用provide/inject要省事很多它可以隔代傳數(shù)據(jù)但有一點需要留意——它會讓組件之間的依賴關(guān)系變得“隱形”不利于代碼追蹤。所以provide/inject適合傳遞類似主題配置、用戶信息、權(quán)限標(biāo)識這樣相對穩(wěn)定的全局?jǐn)?shù)據(jù)業(yè)務(wù)狀態(tài)盡量還是放Pinia。另外v-model不只是表單控件可以用自定義組件也可以。比如一個自定義的日期范圍選擇組件你想要讓父組件能通過v-model綁定一個區(qū)間數(shù)組就在組件里設(shè)置modelValue和update:modelValue事件。這個模式很適合做“受控組件”父組件負責(zé)保存數(shù)據(jù)子組件負責(zé)交互數(shù)據(jù)流清晰調(diào)試也方便。4. 響應(yīng)式原理與性能優(yōu)化知其所以然才能寫得快4.1 響應(yīng)式系統(tǒng)如何工作從getter到依賴收集Vue 3的響應(yīng)式底層是reactive和effect。簡單說當(dāng)你讀取一個響應(yīng)式對象的屬性時當(dāng)前正在執(zhí)行的副作用函數(shù)會被記為“依賴”當(dāng)你修改這個屬性時Vue會觸發(fā)它收集到的依賴函數(shù)重新執(zhí)行。這個機制叫“依賴收集”。我當(dāng)初學(xué)這塊的時候總感覺抽象后來我自己畫了個比喻把響應(yīng)式系統(tǒng)想象成一個社交圈子。數(shù)據(jù)是明星頁面是粉絲。數(shù)據(jù)在讀取的時候粉絲就開始關(guān)注數(shù)據(jù)依賴收集。數(shù)據(jù)一變明星發(fā)條動態(tài)所有關(guān)注它的粉絲都會刷到消息觸發(fā)更新。這個刷動態(tài)的過程就是組件重新渲染。知道原理后很多問題就迎刃而解。比如為什么在Vue 3里reactive包裹的對象解構(gòu)之后會失去響應(yīng)性因為解構(gòu)出來的普通變量只是讀取了一次值并沒有在副作用函數(shù)里持續(xù)追蹤它。明白了這個點你就知道應(yīng)該使用toRefs或ref來保持響應(yīng)性。4.2 別急著優(yōu)化先找到“真瓶頸”很多剛接觸性能調(diào)優(yōu)的新手一上來就想著用memo、shallowRef、v-memo這些花哨手段其實大多數(shù)項目根本不需要。Vue的響應(yīng)式更新已經(jīng)足夠快真正的瓶頸往往出在三種地方一是渲染了超大列表比如幾千行的表格二是頻繁觸發(fā)高耗時計算比如復(fù)雜的篩選、排序三是組件更新范圍太大比如修改一個全局狀態(tài)導(dǎo)致所有組件重新渲染。性能優(yōu)化首先要量化。打開瀏覽器開發(fā)者工具看Performance面板記錄用戶交互前后的長任務(wù)和渲染時間。如果一個交互導(dǎo)致主線程忙了300毫秒以上那才是需要優(yōu)化的情況。我見過有人為了一個只需要渲染50條數(shù)據(jù)的列表搞了一堆virtual-list優(yōu)化結(jié)果復(fù)雜度上來了收益卻幾乎沒有。過度優(yōu)化是現(xiàn)代前端的一種病得克制。4.3 值得用的性能優(yōu)化手段computed、v-for key、事件委托真正值得默認使用的優(yōu)化手段其實很簡單computed能緩存的盡量用computed避免模板里寫復(fù)雜表達式。計算屬性只有相關(guān)依賴變化時才重新計算這點和method不同。我經(jīng)常在模板里看到有人寫list.filter().map()每次渲染都全量執(zhí)行一遍改成computed之后好很多。v-for一定要給key而且key最好是業(yè)務(wù)里的唯一ID不要用index。用index作key在列表插入、刪除、排序時會出各種詭異問題輕則性能浪費重則狀態(tài)錯亂。大量同類事件的監(jiān)聽用事件委托。比如一個表格里每一行都有刪除按鈕如果給每個按鈕都綁一個監(jiān)聽列表大了會有不必要的內(nèi)存開銷。我把監(jiān)聽綁在表格容器上通過事件參數(shù)判斷來源性能提升明顯。4.4 異步更新與nextTickVue不是“實時渲染”Vue的數(shù)據(jù)更新和DOM渲染是異步的。你修改一個響應(yīng)式數(shù)據(jù)后DOM不會立刻變化而是要等到Vue的更新隊列flush。這是為了合并同一事件循環(huán)里的多次修改避免重復(fù)渲染。所以當(dāng)你需要在數(shù)據(jù)修改之后立刻讀取DOM位置或尺寸時就必須用nextTickconst count ref(0) function handleClick() { count.value // 這里DOM還沒有更新 nextTick(() { // 這里DOM已經(jīng)更新了 }) }我踩過類似坑修改列表數(shù)據(jù)后馬上要把滾動條滾到底部直接用scrollTop scrollHeight結(jié)果還是舊列表高度。用nextTick包一下就好了。5. 實戰(zhàn)中的常見問題與排查技巧5.1 生命周期與異步請求為什么數(shù)據(jù)在頁面里是空的新手經(jīng)常遇到一個問題進入詳情頁接口數(shù)據(jù)還沒返回組件已經(jīng)開始渲染了結(jié)果頁面上先是空數(shù)據(jù)一閃而過或者直接報錯“讀取不到undefined的某個屬性”。解決辦法其實不是推遲請求而是正確處理異步落地。我通常會在請求結(jié)果返回之后把loading置為false模板里用v-if或v-loading控制渲染時機template div v-ifloading加載中.../div div v-else-iferror{{ error }}/div div v-else !-- 正常內(nèi)容 -- /div /template另外注意在組件卸載時取消未完成的請求避免已經(jīng)離開頁面了還在setStateVue里是直接改響應(yīng)式變量這叫“內(nèi)存泄漏”。用axios的話可以通過AbortController或axios的CancelToken來取消。5.2 路由守衛(wèi)與權(quán)限控制別把所有邏輯都堆在全局路由里中后臺系統(tǒng)的權(quán)限控制是必考題。正常的流程是用戶在登錄頁輸入賬號密碼拿到token然后路由跳轉(zhuǎn)時通過全局守衛(wèi)校驗token是否存在同時拉取用戶信息和權(quán)限列表動態(tài)生成可訪問的路由表。很多新手把權(quán)限校驗直接寫在全局beforeEach里代碼越來越長各種特殊情況用if-else嵌套最終沒法維護。我的經(jīng)驗是拆開路由先分成“公開路由”和“權(quán)限路由”兩類權(quán)限路由用一個常量數(shù)組定義在登錄后根據(jù)用戶權(quán)限過濾一遍再動態(tài)注冊全局守衛(wèi)只負責(zé)三件事有沒有token、token是否過期、當(dāng)前訪問的路由是否在白名單內(nèi)動態(tài)路由注冊用router.addRoute每次登錄后重新構(gòu)建。注銷時別忘了重置路由表否則重新登錄時權(quán)限變了路由還留著之前的就出嚴(yán)重bug。5.3 表格和列表渲染的性能問題監(jiān)控、虛擬滾動、分頁后臺項目里最吃性能的就是大數(shù)據(jù)表格。幾千條數(shù)據(jù)渲染成表格如果不做任何處理每次輸入篩選都卡體驗極差。我的經(jīng)驗是分級處理如果數(shù)據(jù)量在幾百條以內(nèi)普通渲染加computed篩選就夠了不要上復(fù)雜方案如果數(shù)據(jù)量超過一千條考慮服務(wù)端分頁一次只返回當(dāng)前頁數(shù)據(jù)如果必須一次性渲染大量數(shù)據(jù)那就用虛擬滾動只渲染可視區(qū)內(nèi)的行比如virtual-list相關(guān)組件。但虛擬滾動有一些細節(jié)要注意比如行高必須確定、滾動容器和滾動條要處理好否則會出現(xiàn)滾動跳位的問題另外篩選條件變化時盡量用防抖函數(shù)控制接口請求頻率免得每敲一個字符就發(fā)一次請求把后端打爆。這個點我經(jīng)常用就是用lodash-es的debounce或者自己寫一個簡單的定時器。5.4 常見報錯與解決速查報錯信息常見原因解決辦法Maximum recursive updates exceeded遞歸更新比如在模板里無限修改響應(yīng)式數(shù)據(jù)檢查computed是否有副作用避免修改依賴項本身Cannot read properties of undefined異步數(shù)據(jù)還沒到就訪問深層屬性用可選鏈?.或提前判斷[Vue warn] Property xx was accessed during render but is not defined模板里引用了未定義的變量或ref未解包檢查ref是否.value或檢查import導(dǎo)入Hydration node mismatchSSR或靜態(tài)托管時客戶端和服務(wù)端渲染結(jié)果不一致檢查日期、隨機數(shù)等動態(tài)內(nèi)容渲染Failed to resolve component: xx組件沒有正確注冊或拼寫錯誤檢查導(dǎo)入路徑和組件名5.5 調(diào)試技巧把console.log換成更聰明的寫法調(diào)試Vue組件時與其到處打console.log看數(shù)據(jù)不如用Vue官方的Devtools瀏覽器擴展。它能直觀顯示組件樹、props、事件、Pinia狀態(tài)、路由歷史還可以時間旅行調(diào)試。我建議把第三方調(diào)試工具和瀏覽器內(nèi)置調(diào)試器結(jié)合使用。如果是要臨時查看某個響應(yīng)式變量的變化可以寫一個watch把變化輸出到控制臺watch(count, (newVal, oldVal) { console.log(count changed:, oldVal, -, newVal) })這樣調(diào)試信息帶上了前后值比在事件處理函數(shù)里打日志要直觀得多。6. 給新手的建議我的Vue學(xué)習(xí)路徑和避坑經(jīng)驗6.1 不要一上來就全盤學(xué)挑最常用的部分先上手我見過很多新人從“環(huán)境搭建”開始學(xué)然后卡在webpack配置文件里出不來最后連一個組件都沒寫就放棄了。正確的姿勢應(yīng)該是先不用腳手架直接在script標(biāo)簽里引入Vue的CDN寫一個簡單頁面體驗一下模板語法、事件、數(shù)據(jù)綁定。等有感覺了再上Vite和完整工程。學(xué)習(xí)順序我從自己的經(jīng)歷出發(fā)建議是模板語法插值、指令、事件綁定響應(yīng)式數(shù)據(jù)ref和reactive、computed、watch組件基礎(chǔ)props、emit、插槽路由基礎(chǔ)創(chuàng)建路由、跳轉(zhuǎn)、傳參、守衛(wèi)狀態(tài)管理Pinia的基本用法工程化Vite配置、環(huán)境變量、構(gòu)建部署深入響應(yīng)式原理和性能優(yōu)化這個順序基本符合“會用 - 懂原理 - 能調(diào)優(yōu)”的節(jié)奏。不要跳級尤其不要一上來就研究響應(yīng)式源碼那會勸退。6.2 實戰(zhàn)項目比視頻教程更重要看視頻和讀文檔是“輸入”自己寫項目才是“輸出”。我學(xué)Vue進步最快的一段時間是因為要給團隊搭一個模擬業(yè)務(wù)的管理后臺。雖然一開始磕磕絆絆但那個項目逼著我去處理路由鑒權(quán)、表格復(fù)雜交互、權(quán)限控制、遠程部署這些問題這些全是視頻里不會演示的細節(jié)。找項目練手也講究策略。最好是找一個你自己真正用得上的小工具比如個人記賬本、團隊會議預(yù)約系統(tǒng)、簡單的CMS。照著別人的demo敲代碼效果有限因為clone一個倉庫改兩個按鈕不等于會開發(fā)。你必須從一張白紙開始決定組件怎么拆、數(shù)據(jù)放哪里、路由怎么設(shè)計這個過程才是真正的能力積累。6.3 最后分享一個我個人的習(xí)慣開發(fā)Vue項目時我習(xí)慣在寫每個功能之前先在紙上或者空白編輯器里列出這個功能涉及的“數(shù)據(jù)、動作、依賴”三張清單。數(shù)據(jù)是頁面要展示什么動作是用戶操作會觸發(fā)哪些函數(shù)依賴是這個數(shù)據(jù)需要從哪里來、影響到哪些其他數(shù)據(jù)。列完清單再開始寫代碼。這個方法幫我減少了很多次“寫到一半發(fā)現(xiàn)設(shè)計錯了要重來”的情況。Vue本身是一個包容性很強的框架上限和下限差距極大。寫一個小頁面誰都會但是把幾千行代碼的復(fù)雜系統(tǒng)整理得井井有條才是真正考驗水平的地方。希望這篇文章里那些從實戰(zhàn)里沉淀下來的思路能讓你在寫Vue時少走一些彎路。