【前端福利】用grunt搭建自動化的web前端開發環境-完整教程

王福朋發表於2015-06-09

   

  jQuery在使用grunt,bootstrap在使用grunt,百度UEditor在使用grunt,你沒有理由不學、不用!

1. 前言

  各位web前端開發人員,如果你現在還不知道grunt或者聽說過、但是不會熟練使用grunt,那你就真的真的真的out了(三個“真的”重複,表示重點)。至於grunt的作用,這裡不詳細說了,總之你如果做web前端開發,你一定要用grunt。還有一點,它完全免費,沒有盜版。既強大又免費的東西,為何不用?

  當然了,你如果你能找到更好的替代grunt的其他工具也是可以的,例如gulp。Gulp未來有可能替代grunt,但是現在來說市場佔有率還是不如grunt。而這種工具我們們是現在就需要用的,所有不要再猶豫了,拿來主義,先用grunt,即學即用。

  本文章旨在講解grunt入門,以及講解grunt最常用的幾個外掛的使用。篇幅可能會比較長,大家耐心看。本文例證詳細、清晰的講解每一個知識點。但是——如果你看完本文還是不會,我還有最後一個大招。不過你可能需要付出一頓飯錢 + 一包煙錢的代價——去看看我錄製的視訊教程《用grunt搭建自動化的web前端開發環境》(教程中有原始碼下載) ,保證你看完就會用。

  (PS:碰巧,本文基於windows環境寫的,而視訊教程是基於mac os錄製的,兩者兼備了)

  廢話不多少,視訊教程你也先別看,錢彆著急花。先挑戰一下自己的理解能力,看下文講述是否清晰、是否能看懂。

2. 安裝nodejs

  Grunt和所有grunt外掛都是基於nodejs來執行的,如果你的電腦上沒有nodejs,就去安裝吧。安裝nodejs非常簡單,完全傻瓜式、下一步下一步下一步、的安裝方式,這裡不再贅述。去 https://nodejs.org/ 上,點選頁面中那個綠色、大大的“install”按鈕即可。

  安裝了nodejs之後,可以在你的控制檯中輸入“node -v”來檢視nodejs的版本,也順便試驗nodejs是否安裝成功。

  

  注意兩點。第一,grunt依賴於nodejs的v0.8.0及以上版本;第二,奇數版本號的版本被認為是不穩定的開發版,不過從官網上下載下來的應該都是偶數的穩定版。

3. 安裝grunt-CLI

  注意,如果你的電腦不聯網,以下操作你都做不了,所以,首先保證電腦聯網。

  “CLI”被翻譯為“命令列”。要想使用grunt,首先必須將grunt-cli安裝到全域性環境中,使用nodejs的“npm install…”進行安裝。如果你不瞭解nodejs的npm如何安裝軟體,這裡就先不要問了,先照著我說的做。

  開啟控制檯(注意:windows系統下請使用管理員許可權開啟),輸入:

  

  注意,mac os 系統、部分linux系統中,在這句話的前面加上“sudo ”指令

  

  回車,命令列會出現一個轉動的小橫線,表示正在聯網載入。載入的時間看你網速的快慢,不過這個軟體比較小,一般載入時間不會很長,稍一會兒,就載入完了。你會看到以下介面。

  

  這時候要驗證一下grunt-cli是否安裝完成並生效,你只需要繼續在命令列中輸入“grunt”命令即可。如果生效,則會出現以下結果:

  

  你不要管這些結果是什麼意思,總之出現這些提示,證明你的grunt-cli安裝成功了。

4. 建立一個簡單的網站

  Grunt是應用於實際專案的,所以我們得有一個簡單的測試網站來演示grunt的安裝、使用。

  首先,我在電腦的D盤下面建了一個“grunt_test”資料夾,裡面建了三個空資料夾、兩個空文件,名稱如下圖。(注意 Gruntfile.js 檔案的首字母大寫!)

  

  其他的東西先不要管,先把package.json這個檔案寫一些東西。記住,既然檔案字尾名叫“json”,那麼檔案中的格式肯定是嚴格的json格式。什麼,不熟悉json?作為一個web前端程式猿,json是必備課。有一個教程《json2.js原始碼解讀》能讓你徹底瞭解json。

  書歸正傳。Package.json的內容我們寫成如下格式:

  

  很簡單,我們把這個網站或系統的名稱、版本寫了一下。但是,不光是寫在這裡佔空的,以後會用到的,具體如何用,我們下文會有介紹,先彆著急。

還有,最後一個“devDependencies”是什麼意思?字面意思解釋是“開發依賴項”,即我們現在這個系統,將會依賴於哪些工具來開發。現在程式碼一行都沒有寫,依賴於誰?誰也不依賴!所以,就先寫一個空物件。但是下文會慢慢把它填充起來。

另外,其實package.json中你可以增加任何符合json格式的程式碼,它生來自由,僅僅受json程式碼格式的限制。

  怎麼樣,看到這裡,是不是覺得下文很有懸念,很想看下去呀?那就繼續!

5. 安裝grunt

  主角總是姍姍來遲。《三國演義》在開篇三分一之後才請出來諸葛亮,《水滸傳》在第十八回才請出了宋江。而我們本文的主角,也出來的不早。

  接下來我們會有一系列外掛的安裝,他們的安裝過程和grunt一樣。但是他們的執行都是基於grunt的,因此才能把grunt叫做一個“構建工具”。Grunt沒有具體的作用,但是它能把有具體作用的一個一個外掛組合起來,形成一個整體效應。

  例如,你需要檢查js語法錯誤,然後再去壓縮js程式碼。如果這兩步你都去手動操作,會耗費很多成本。Grunt就能讓你省去這些手動操作的成本。

  書歸正傳。注意,這裡安裝grunt不再是全域性安裝了,需要你在控制檯進入到網站或系統的具體目錄下。這裡我們進入 D:\grunt_test 目錄下。然後輸入以下命令。

  

  注意,先不要按回車,先不要執行,先看看下文的描述!

  這裡需要解釋的是,“—save-dev”的意思是,在當前目錄安裝grunt的同時,順便把grunt儲存為這個目錄的開發依賴項。看到“開發依賴項”這一次,是不是覺得有些眼熟?上文在配置package.json時,其中的“devDependencies”中就會儲存開發依賴項。

  具體儲存為開發依賴項是一個什麼效果?動手安裝一下就是了。首先,在執行安裝grunt的命令之前,package.json中的“devDependencies”對應的是空物件。

現在我們來執行這行命令。你會看到幾條warning提示,不用管它。然後接下來就是載入狀態,一個旋轉的小橫線。稍等待一會兒,會提示你安裝成功。如下圖:

  

  現在你應該第一時間開啟package.json去看看,那裡的“devDependencies”有什麼變化。我這裡的變化如下圖,看看你的是不是和我的一樣?

  

  然後你再看看文件目錄中的檔案或者資料夾有什麼變化?我這裡多了一個“node_modules”資料夾,其中有一個“grunt”資料夾,再其中有若干文件。這裡就是儲存grunt原始檔的地方。

  

  這是見證奇蹟的時刻,彆著急,奇蹟還沒完呢。然後你在控制檯執行“grunt”命令。如果你得到一個warning提示,那說明grunt已經起作用了。如下圖:

  

  經過以上三步,說明grunt已經在這個目錄下成功安裝。

  那麼,為何我們在剛才執行grunt時候會有Warning提示呢?根據提示,我們得知的資訊是:Task “default” not found ,如何搞定這個問題?——當然是繼續往下看啊。

6. 配置Gruntfile.js

  顧名思義,Gruntfile.js 這個檔案,肯定是為了grunt做某種配置的。按照grunt的規定,我們首先把Gruntfile.js配置成如下格式。

  

  在以上程式碼中,我們看到了剛才執行grunt命令,warning提示中的“default”字眼。不妨我們此時再執行一下grunt命令,看看會不會再次出現“warning”、“default”等字眼。

  

  執行結果告訴我們“Done, without errors”。那就繼續往下吧。

  

  另外請注意Gruntfile.js中的一句話:

  

  這句話是在Gruntfile.js中獲取package.json中的內容。在上文配置package.json時我們說過:package.json中的內容不光是用來佔位置的,還可以在其他地方獲取。這裡不是已經獲取了package.json內容了嗎?至於獲取瞭如何使用,下文會有介紹,還是繼續往下看吧。

7. Grunt外掛介紹

  進入grunt官網的外掛列表頁面 http://www.gruntjs.net/plugins ,我們能看到grunt到目前位置的所有外掛。現在裡面有4560個外掛,這個數量每天都在增加。而且,這些既然出現在官網,肯定是經過稽核的。

  外掛分為兩類。第一類是grunt團隊貢獻的外掛,這些外掛的名字前面都帶有“contrib-”字首,而且在外掛列表中有星號標註。第二類是第三方提供的外掛,不帶有這兩個特徵。

  和jquery一樣,外掛那麼多,肯定不會全部用。grunt官網外掛列表的前幾個外掛中的前幾個外掛,下載量最多,它們肯定是大家都在用的外掛。第一名jshint外掛最近30天下載量將近89萬次,這是多麼驚人的下載量!

   我們們可以把前幾名外掛的作用簡單描述一下,看看你在實際編碼過程中是否需要?其實不用看就知道答案——肯定需要——要不然怎麼會下載量那麼高呢?

  • Contrib-jshint——javascript語法錯誤檢查;
  • Contrib-watch——實時監控檔案變化、呼叫相應的任務重新執行;
  • Contrib-clean——清空檔案、資料夾;
  • Contrib-uglify——壓縮javascript程式碼
  • Contrib-copy——複製檔案、資料夾
  • Contrib-concat——合併多個檔案的程式碼到一個檔案中
  • karma——前端自動化測試工具

  以上這些外掛,本文不會全部講到。但是隨著講解其中的一部分,我想你就能掌握使用grunt外掛的方法。知道方法了,然後你就可以參考官方文件去使用你想要的外掛。

  grunt集全世界web前端開發的智慧於一身,比你想想的更加強大,它的外掛庫能應對你在web前端開發遇到的任何事情。

  還等什麼,繼續往下看。

8. 使用uglify外掛(壓縮javascript程式碼)

  Uglify外掛的功能就是壓縮javascript程式碼。至於javascript程式碼壓縮的必要和意義,這裡就不用在贅述了吧?幾乎每一個javascript類庫或者框架,都有一個 **.min.js 壓縮版。

  問一句,你平時做javascript開發,都用什麼工具來壓縮程式碼?我想這個問題會有許多個答案。但是,使用grunt的uglify外掛進行壓縮,效果絕對不輸於任何外掛。

  要安裝一個外掛,你首先要進入這個外掛在grunt官網的說明文件頁面。我們在grunt官網外掛列表頁面,找到“contrib-uglify”點選進入。你要看這裡面的說明,然後根據說明進行安裝。這裡我們只講重點。

  安裝uglify外掛的方式,和安裝grunt是一樣的。還記得grunt是怎麼安裝的嗎?

  

  這裡又出現了熟悉的“—save-dev”,具體的作用在上文安裝grunt時已經說過了,不再贅述。執行這句命令。安裝完成之後,你會看到package.json中“devDependencies”節點的變化,以及“node_modules”資料夾裡的變化。這兩點都在安裝grunt時已經詳細說過。

  現在還不能用,還需要在Gruntfile.js 做配置。

  不過,先彆著急。我們既然要使用uglify來壓縮javascript程式碼,當然得建立一個js檔案來做實驗。我們在現有的“src”資料夾中新建一個“test.js”,並隨便寫一些程式碼。顯然,我們無法通過雙手和鍵盤寫出壓縮後的程式碼。

  

  測試檔案建立好了。我們接下來就要把這個js檔案進行壓縮。

  當然,要壓縮誰?往哪裡壓縮?這些都需要配置,在Gruntfile.js中配置。分為三步:

  第一步,在grunt.initConfig方法中配置 uglify 的配置引數。如下圖:

  

  上圖中,對uglify的配置有兩項。

  “options”中規定允許生成的壓縮檔案帶banner,即在生成的壓縮檔案第一行加一句話說明。注意,其中使用到了pkg獲取package.json的內容。

  “build”中配置了原始檔和目標檔案。即規定了要壓縮誰?壓縮之後會生成誰?注意,我們這裡將目標檔案的檔名通過pkg的name和version來命名。

  (PS:上文中說過的package.json的內容終於找到了他被應用的地方了。這樣的好處是:例如,對檔案版本的管理,你只需要在package.json中修改即可,grunt會自動根據最新的版本號生成相應版本的檔案。你不用手動去修改檔案的檔名。)

  最後,這裡只是對“options”和“build”的基本應用,還有許多中使用方式,可以去官網查閱。

  第二步,在 grunt.initConfig 方法之後,要讓grunt去載入這一個外掛。光配置了,不載入上,如何用啊?

  

  第三步,在grunt命令執行時,要不要立即執行uglify外掛?如果要,就寫上,否則不寫。我現在是需要的,所以我寫上。也有可能不需要,這種情況誰知道呢?

  

  以上說的這三步已經OK了,接下來我們去試試。在控制檯中執行grunt命令,看得到什麼結果。

  控制檯將輸入如下資訊:

  

  再去看看,是否生成了一個壓縮後的js檔案?

  

  果然。根據package.json中的name和version生成了檔名。而且,壓縮後的程式碼的banner也是符合Gruntfile.js中的配置要求的。

   以上就是uglify外掛的詳細安裝、配置說明。Javascript使用uglify壓縮,css可使用cssmin外掛壓縮。安裝、配置方法一樣的,不再贅述。

9. 使用jshint外掛(檢查javascript語法錯誤)

  如果你僅僅寫一個幾十行js程式碼做一個小測試,語法錯誤的檢查大可不必。但我相信看這篇文章的朋友,肯定不限於此,你可能每天都需要寫一大堆的js程式碼來完成自己的工作。即使再牛、再仔細的人也會犯一些低階錯誤,但是jshint不會。因此,你最好的做法就是每時每刻都讓jshint來幫助你檢查剛剛寫過的js程式碼,有錯誤立即發現立即處理。這樣一來,你們就沒必要每隔幾天都相聚在會議室進行人工程式碼走查了。及時程式碼走查,你也沒必要刻意的關注語法錯誤。

  還有一些js初級入門的朋友,或者已經有多年js經驗,卻“不思進取”的朋友。你到現在可能都不知道一些js語法歸法。例如:你到現在可能都不知道“==”和“===”到底有什麼區別,你到現在都不知道在語句塊內定義變數的壞處,還有更多更多你不知道的。怎麼辦?讓jshint來幫助你。

  接下來介紹jshint的安裝和配置。

  外掛的安裝和安裝grunt、uglify沒有任何差別,這裡不再贅述了。直接執行下面的命令

  

  配置jshint和配置uglify一樣。在配置uglify時候我們講到了三個步驟,這裡也是三個步驟。

  第一步,在grunt.initConfig方法中配置jshint。

  

  和uglify的配置一樣,分為“options”和“build”兩個部分。“build”中描述了jshint要檢查哪些js文件的語法。“options”中描述了要通過怎麼的規則檢查語法,這些規則的描述檔案就儲存在網站根目錄下的一個叫做“.jshintrc”的檔案中。因此我們在網站的根目錄下面新增上這個文件,並且填寫上檔案內容。

  

  .jshintrc檔案中程式碼的格式也要遵守嚴格的json語法,否則無效。那裡面這些配置是什麼意思呢?想詳細瞭解可以去百度搜尋“jshint 配置”關鍵字,你就能知道答案。這裡由於篇幅太多,不過多介紹。總之吧,這個.jshint是我常用的配置。

  第二步,載入外掛。和uglify的載入方法一樣。注意,這裡沒有先後順序。

  

  第三步,配置grunt命令啟動時,要執行的任務,這裡注意先後順序。你是希望先檢查語法呢?還是先合併呢?——聰明人應該都知道先檢查語法比較好,因為語法對,合併了有什麼意義?

  

  以上三步配置完了之後,我們可以測試一下這個jshint到底怎麼用。這裡我故意將當前建立的test.js檔案寫一個語法錯誤。

  

  然後我們執行“grunt”命令,看jshint能給我們識別出來這兩個錯誤嗎?結果如下:

  

  看到沒有,jshint很清除的識別出了這兩個錯誤。而且注意到沒有,jshint錯誤之後呢,其後面的uglify就沒有再繼續執行。這正式我們想要的結果。

  我們修改完這些錯誤,在此執行grunt命令,結果沒有提示錯誤,而且jshint和uglify都順利執行了。

      

10. 使用csslint外掛(檢查css語法錯誤)

  檢查css檔案的語法錯誤要使用csslint外掛,其安裝配置方法和jshint幾乎一模一樣。只不過csslint依賴於一個叫做“.csslintrc”的檔案作為語法檢驗的規則,我的“.csslintrc”檔案如下。其他內容我們就不在此贅述了。

  

11. 使用watch外掛(真正實現自動化)

  你可以一直有一個疑問,上面將的外掛中,每次執行外掛功能,都得執行一遍“grunt”命令,這樣的操作非常繁瑣,說好的“自動化”呢?彆著急,接下來就解決這個問題——通過watch外掛解決這個問題。

  首先安裝watch外掛,如果安裝不再贅述了。接下來要配置watch外掛,配置分為三個步驟,不再詳細描述了,只貼圖說明。

  第一步。配置watch將監控哪些檔案的變化,以及這些檔案一旦變化,要立即執行哪些外掛功能。如下圖,watch將監控src資料夾下所有js檔案和css檔案的變化,一旦變化,則立即執行jshint和uglify兩個外掛功能。

  

  第二步,直接貼圖

  

  第三步,直接貼圖

  

  這三步執行完了,即watch外掛配置完成。執行grunt命令,控制檯提示watch已經開始監聽。此時要想停止,按ctrl + c即可。

  

  既然在監聽,我們試一試看監聽有沒有效。我們將 test.js 程式碼中去掉一個分號,看它能否自動檢查出來這個錯誤。

  

  結果顯示,watch檢查到了test.js檔案的變化,而且通過執行jshint提示了語法錯誤。更重要的是,它現在還在監聽、並未停止。說明它正在等著你去修改錯誤,重新監聽檢查。那我們就不要辜負它了,再把語法錯誤修復了。看它會如何處理。

  

  它又檢測到了檔案變化,這次語法沒有錯誤,它很順利的執行了jshint和uglify,執行完畢之後重新進行監聽。多聽話的工具!

  好了,已經回答了你們的問題——自動化

12. 上文中所謂的“build”

  上文中描述各個外掛的配置時,都是用了“build”這一名稱作為一個配置項。

  

  那麼這裡是不是必須用“build”這一個名字?答案很明顯,當然不是。我之前之所以沒直接說,是因為我要先把外掛的安裝和配置講明白,不變一次傳輸太多知識,現在一併和大家說了。

  這裡可以用任何字串代替“build”(但要符合js語法規則)。甚至,你可以把“build”指向的內容分開來寫。這樣對多人協同開發很友好。好的設計就是這樣:讓使用者盡情發揮他們的自由來幹事,而不是去限制他們。

  

  如上圖,我對jshint的配置做了修改,大家可以去自己修改,然後執行grunt命令試試。命令列會有“test1”、“test2”的字眼。

13. 批量安裝外掛

  請各位看官繼續跟隨我思考問題,學而不思則罔。

  到現在為止,我剛剛安裝了3個外掛,“node_modules”資料夾所佔據的空間就有18MB了。大家猜一猜,我在上傳程式碼到開發庫的時候,會不會把“node_modules”中的內容也上傳呢?既然我這麼問了,答案肯定是不上傳。

  問題又來了,我如果作為開發環境的搭建者,我不把“node_modules”上傳,其他一起開發的人,怎麼得到這些grunt外掛和工具呢?有人回答讓他們自己去手動一個一個安裝——首先這是一個笨方法,其次如果我當年安裝的舊版本,而他們現在自己安裝的可能是新版本。新舊有可能不相容啊。

  該怎麼辦?

  其實答案很簡單——我上傳原始碼時候,肯定會把package.json上傳上去,而package.json中的“devDependencies”就記錄了這個系統的開發依賴項,然後我通過nodejs的npm即可批量安裝。

  做一個試驗。我在D盤下面新建一個目錄“grunt_test_1”,然後把“grunt_test”中的package.json拷過去。在開啟命令列跳轉到“grunt_test_1”,執行“npm install”命令,看看得到什麼結果。

  

  此時按回車執行命令,結果在“grunt_test_1”生成了“node_modules”資料夾,裡面安裝好了package.json中“devDependencies”配置的外掛。而且,版本都是一直的。

神奇吧!

  

14. 系統檔案結構

  使用grunt來搭建web前端開發環境時候,文件目錄和之前可能就不一樣了。因為你手動寫的程式碼檔案,絕對不是你最終輸出的檔案。這些還需要經過grunt各種外掛的檢驗、合併、壓縮才能最終輸出給使用者。

  這裡我拿自己的開源專案wangEditor的文件結構舉例子。

  

  上圖中,“src”資料夾裡面儲存的是原始的程式碼檔案,“dist”資料夾裡面儲存的是最終生成的程式碼檔案,“demo”裡面儲存的是一些測試頁面。

  當然了,各個系統的檔案組織形式不一樣,但是我建議大家還是按照這麼一個思想去組織文件結構。大家也可以去github上參考一下jquery、bootstrap這些著名開源專案的文件結構。看看jquery輸出的雖然是簡單的一個js檔案,但是它的開發環境是多麼的複雜。

  做好前端,不容易。

15. 完結

  這篇文章我使用word寫的,然後貼上到部落格園中釋出的。到現在為止,我寫了一共有20頁、6700多字,全部手寫、手動截圖。寫部落格寫到這個份上,我也算是拼了!

  

  如果你看完這篇文章還不會grunt,或者你懶得看文章、嫌累,我建議你去看看我錄製的使用grunt搭建全自動web前端開發環境這個視訊教程,視訊裡講的肯定詳細的多了,而且可以下載原始碼。

  最後,大家如果覺得本文對你有幫助,就點個贊吧!

-------------------------------------------------------------------------------------------------------------

學習作者教程:《前端JS高階面試》《前端JS基礎面試題》《React.js模擬大眾點評webapp》《zepto設計與原始碼分析》《json2.js原始碼解讀

也歡迎關注我的開源專案——wangEditor,輕量化web富文字編輯器

-------------------------------------------------------------------------------------------------------------

 

相關文章