前端工程本質(zhì)上是軟件工程的一種。軟件工程化關(guān)注的是性能、穩(wěn)定性、可用性、可維護(hù)性等方面,注重基本的開(kāi)發(fā)效率、運(yùn)行效率的同時(shí),思考維護(hù)效率。一切以這些為目標(biāo)的工作都是'前端工程化'。工程化是一種思想而不是某種技術(shù)。舉例說(shuō)明: 要蓋一棟大樓,假如我們不進(jìn)行工程化的考量那就是一上來(lái)掂起瓦刀、磚塊就開(kāi)干,直到把大樓壘起來(lái),這樣做往往意味著中間會(huì)出現(xiàn)錯(cuò)誤,要推倒重來(lái)或是蓋好以后結(jié)構(gòu)有問(wèn)題但又不知道出現(xiàn)在哪誰(shuí)的責(zé)任甚至?xí)谀骋惶燹Z然倒塌,那我們?nèi)绻霉こ袒乃枷肴プ?,就?huì)先畫(huà)圖紙、確定結(jié)構(gòu)、確定用料和預(yù)算以及工期,另外需要用到什么工種多少人等等,我們會(huì)先打地基再建框架再填充墻體這樣最后建立起來(lái)的高樓才是穩(wěn)固的合規(guī)的,什么地方出了問(wèn)題我們也能找到源頭和負(fù)責(zé)人。 前端,是一種GUI軟件我們知道前端技術(shù)的主要應(yīng)用場(chǎng)景并非只是高大上的基礎(chǔ)庫(kù)/框架,拽炫酷的宣傳頁(yè)面,或者屌炸天的小游戲等這些一兩個(gè)文件的小項(xiàng)目,更具商業(yè)價(jià)值的則是復(fù)雜的Web應(yīng)用,它們功能完善,界面繁多,為用戶提供了完整的產(chǎn)品體驗(yàn)。(可能是新聞聚合網(wǎng)站,可能是在線購(gòu)物平臺(tái),可能是社交網(wǎng)絡(luò),可能是金融信貸應(yīng)用,可能是音樂(lè)互動(dòng)社區(qū),也可能是視頻上傳與分享平臺(tái)……) 從本質(zhì)上講,所有Web應(yīng)用,都是一種運(yùn)行在網(wǎng)頁(yè)瀏覽器中的軟件,這些軟件的圖形用戶界面(Graphical User Interface,簡(jiǎn)稱GUI)即為前端。 如此復(fù)雜的Web應(yīng)用,動(dòng)輒幾十上百人共同開(kāi)發(fā)維護(hù),其前端界面通常也頗具規(guī)模,工程量不亞于一般的傳統(tǒng)GUI軟件: ![]() GUI軟件 前端工程化需要考慮哪些因素?1. 模塊化簡(jiǎn)單來(lái)說(shuō),模塊化就是將一個(gè)大文件拆分成相互依賴的小文件,再進(jìn)行統(tǒng)一的拼裝和加載。(方便了多人協(xié)作)。 分而治之是軟件工程中的重要思想,是復(fù)雜系統(tǒng)開(kāi)發(fā)和維護(hù)的基石,這點(diǎn)放在前端開(kāi)發(fā)中同樣適用。模塊化是目前前端最流行的分治手段。
不管你將來(lái)是否要復(fù)用某段代碼,你都有充分的理由將其分治為一個(gè)模塊。
AMD/CommonJS/UMD/ES6 Module等等。 CommonJS的核心思想是把一個(gè)文件當(dāng)做一個(gè)模塊,要在哪里使用這個(gè)模塊,就在哪里require這個(gè)模塊,然后require方法開(kāi)始加載這個(gè)模塊并且執(zhí)行其中的代碼,最后會(huì)返回你指定的export對(duì)象。 module.export = function() { hello: function() { alert('你好'); }}var a = require('./xxx/a.js');a.hello(); // ==> 彈窗“你好” CommonJS 加載模塊是同步的,所以只有加載完成才能執(zhí)行后面的操作,不能非阻塞的并行加載多個(gè)模塊。 AMD(異步模塊定義,Asynchronous Module Definition),特點(diǎn)是可以實(shí)現(xiàn)異步加載模塊,等所有模塊都加載并且解釋執(zhí)行完成后,才會(huì)執(zhí)行接下來(lái)的代碼。
在一些同時(shí)需要AMD和CommonJS功能的項(xiàng)目中,你需要使用另一種規(guī)范:Universal Module Definition(通用模塊定義規(guī)范)。UMD創(chuàng)造了一種同時(shí)使用兩種規(guī)范的方法,并且也支持全局變量定義。所以UMD的模塊可以同時(shí)在客戶端和服務(wù)端使用。 幸運(yùn)的是在JS的最新規(guī)范ECMAScript 6 (ES6)中,引入了模塊功能。 // CommonJS代碼// lib/counter.jsvar counter = 1;function increment() { counter++;}function decrement() { counter--;}module.exports = { counter: counter, increment: increment, decrement: decrement};// src/main.jsvar counter = require('../../lib/counter');counter.increment();console.log(counter.counter); // 1
在less、sass、stylus等預(yù)處理器的import/mixin特性支持下實(shí)現(xiàn)、css modules。 雖然SASS、LESS、Stylus等預(yù)處理器實(shí)現(xiàn)了CSS的文件拆分,但沒(méi)有解決CSS模塊化的一個(gè)重要問(wèn)題:選擇器的全局污染問(wèn)題; CSS in JS是徹底拋棄CSS,使用JS或JSON來(lái)寫(xiě)樣式。這種方法很激進(jìn),不能利用現(xiàn)有的CSS技術(shù),而且處理偽類等問(wèn)題比較困難; CSS Modules 原理:使用JS 來(lái)管理樣式模塊,它能夠最大化地結(jié)合CSS生態(tài)和JS模塊化能力,通過(guò)在每個(gè) class 名后帶一個(gè)獨(dú)一無(wú)二 hash 值,這樣就不有存在全局命名沖突的問(wèn)題了。 webpack 自帶的 css-loader 組件,自帶了 CSS Modules,通過(guò)簡(jiǎn)單的配置即可使用。 { test: /\.css$/, loader: 'css?modules&localIdentName=[name]__[local]--[hash:base64:5]'} 2. 組件化前端作為一種GUI軟件,光有JS/CSS的模塊化還不夠,對(duì)于UI組件的分治也有著同樣迫切的需求。分治的確是非常重要的工程優(yōu)化手段。 ![]() 前端組件化開(kāi)發(fā)
由于系統(tǒng)功能被分治到獨(dú)立的模塊或組件中,粒度比較精細(xì),組織形式松散,開(kāi)發(fā)者之間不會(huì)產(chǎn)生開(kāi)發(fā)時(shí)序的依賴,大幅提升并行的開(kāi)發(fā)效率,理論上允許隨時(shí)加入新成員認(rèn)領(lǐng)組件開(kāi)發(fā)或維護(hù)工作,也更容易支持多個(gè)團(tuán)隊(duì)共同維護(hù)一個(gè)大型站點(diǎn)的開(kāi)發(fā)。 3. “智能”加載靜態(tài)資源(性能優(yōu)化)模塊化/組件化開(kāi)發(fā)之后,我們最終要解決的,就是模塊/組件加載的技術(shù)問(wèn)題。然而前端與客戶端GUI軟件有一個(gè)很大的不同:前端是一種遠(yuǎn)程部署,運(yùn)行時(shí)增量下載的GUI軟件。 如果用戶第一次訪問(wèn)頁(yè)面就強(qiáng)制其加載全站靜態(tài)資源再展示,相信會(huì)有很多用戶因?yàn)槭ツ托亩魇А8鶕?jù)“增量”的原則,我們應(yīng)該精心規(guī)劃每個(gè)頁(yè)面的資源加載策略,使得用戶無(wú)論訪問(wèn)哪個(gè)頁(yè)面都能按需加載頁(yè)面所需資源,沒(méi)訪問(wèn)過(guò)的無(wú)需加載,訪問(wèn)過(guò)的可以緩存復(fù)用,最終帶來(lái)流暢的應(yīng)用體驗(yàn)。 這正是Web應(yīng)用“免安裝”的魅力所在。 由“增量”原則引申出的前端優(yōu)化技巧幾乎成為了性能優(yōu)化的核心。
還有復(fù)雜的BigRender、BigPipe、Quickling、PageCache等技術(shù)。
資源表是一份數(shù)據(jù)文件(比如JSON),是項(xiàng)目中所有靜態(tài)資源(主要是JS和CSS)的構(gòu)建信息記錄,通過(guò)構(gòu)建工具掃描項(xiàng)目源碼生成,是一種k-v結(jié)構(gòu)的數(shù)據(jù),以每個(gè)資源的id為key,記錄了資源的類別、部署路徑、依賴關(guān)系、打包合并等內(nèi)容。
在查表的時(shí)候,如果一個(gè)靜態(tài)資源有pkg字段(用來(lái)記錄web應(yīng)用中一個(gè)頁(yè)面加載過(guò)的靜態(tài)資源,當(dāng)下個(gè)頁(yè)面用到這個(gè)資源就無(wú)需加載了,有效利用緩存),那么就去加載pkg字段所指向的打包文件,否則加載資源本身。 4. 規(guī)范化規(guī)范化其實(shí)是工程化中很重要的一個(gè)部分,項(xiàng)目初期規(guī)范制定的好壞會(huì)直接影響到后期的開(kāi)發(fā)質(zhì)量。
5. 自動(dòng)化任何簡(jiǎn)單機(jī)械的重復(fù)勞動(dòng)都應(yīng)該讓機(jī)器去完成。
|
|