使用 Gulp 構建 AngularJS / Jade 項目

jopen 9年前發布 | 24K 次閱讀 項目構建 angularjs gulp

 

我所經歷的大部分項目,并不是純粹的前端項目,相關的前端文件,都是使用 Express 來處理,除了 Jade 文件之外的,全部放在 Express 靜態文件目錄public中,Bower 也配置為將依賴包直接安裝到public/lib目錄,然后直接使用原路徑在 HTML 中引用對應的 JavaScript / CSS 文件,經常是一個頁面加載幾十個靜態資源。

上周在做一個 App 項目的商戶端,對應的 API 已經完成,只是用 AngularJS 來實現一個前端 Web 頁面,其中的 HTML 使用了 Jade 來完成。由于是一個完全的前端項目,終于決定嘗試用 Gulp 來進行構建。整體的需求如下:

  • 使用 Bower 管理前端依賴
  • 需要將 Jade 文件編碼成 HTML,并按照 Angular New Router 中的 Components 來組織目錄結構
  • 將 CSS / JavaScript 文件組裝為單個文件
  • 圖片和字體等靜態資源存放到對應目錄
  • 使用 Gulp 創建一個調試用的服務器,并能夠修改文件后自動重載瀏覽器頁面
  • </ul>

    項目的目錄與文件結構

    整體文件夾結構如下:

    ├── app
    │   ├── controllers // AngularJS 控制器
    │   │   └── home.js
    │   ├── modules // AngularJS 模塊
    │   │   └── app.js
    │   ├── services // AngularJS 服務
    │   │   └── city.client.service.js
    │   └── views // Jade 文件
    │       ├── index.jade
    │       └── _partial
    │           └── home.jade
    ├── bower.json
    ├── config.js
    ├── gulpfile.js
    ├── package.json
    ├── README.md
    └── static
        ├── css
        │   └── style.css
        └── images
            ├── avatar.png
            └── logo.gif

    另外還有個public目錄,作為發布目錄,提供給 Web 服務器對外發布。所有需要在瀏覽器使用的文件,最后使用都要生成或者復制到public中。

    使用 Bower 管理前端依賴

    悲劇,在我定這篇文章的大綱的時候, Bower 還在更新,結果沒兩天就宣布不再開發了。

    Bower 之所以在以前統治著前端包管理領域,原因在于它的扁平化包管理, NPM 中每個模塊都有獨立的屬于各自的目錄,來存儲對應的依賴包,雖然會占用比較多的磁盤,但卻可以防止模塊版本不同而造成的依賴問題。 Bower 本身并不直接決定應用的包依賴,它將模塊的依賴同模塊本身一樣安裝。

    自從 NPM 成立專門的公司來運營以后,已經致力于將自己從Node Package Manager提升為JavaScript Package Manager。所以也開始像 Bower 來組織模塊的依賴—— Bower 存在的理由又少了一個。

    這兩天,網上正在嘲笑bower --save并不會把當前已經安裝的依賴存儲到bower.json,不過我懷疑他們沒有看到過 NPM 3.3.x 是怎么處理依賴的,npm --save后的package.json估計會相當的不堪入目吧。

    Jade 模板文件轉換為 HTML 文件

    以前 Jade 文件是使用 Express 的view engine來轉譯,在專門的路由文件中,一一按照 Angular New Router 的 Components 標準來進行解析。使用 Gulp 轉換也是類似,借助gulp-jade模塊,設置gulp.src為 jade 文件路徑,gulp.dest為轉換后的 HTML 文件路徑,為了方便,將需要轉換的 jade 文件和對應的路徑組成一個數組,再在gulp.task中對數據進行遍歷,并執行轉換。

    var gulp = require('gulp');
    var jade = require('gulp-jade');

    var jadeFiles = [ {src: './app/views/index.jade', dest: './public/'}, {src: './app/views/_partial/home.jade', dest: './public/components/home/'} ];

    gulp.task('jade', function(){ jadeFiles.forEach(function(jf){ if(!jf.src || !jf.dest) return; gulp.src(jf.src) .pipe(jade({petty: true})) .pipe(gulp.dest(jf.dest)); }); });</pre>

    將 JavaScript / CSS 文件組裝為單個文件

    對于遵循 AngularJS 模塊化設計的前端應用, JavaScript 文件那必然是相當多,再加上使用一些擴展,就算是中小型項目,超過 70 個以上那也是相當常見,看 Chrome 開發工具中的 Network 頁那可以部是相當精彩,

    如果只是將多個 JavaScript 和 CSS 文件合為一個,使用gulp-concat模塊即可,壓縮 JavaScript 文件,可以再加一個gulp-uglify模塊,壓縮 CSS 文件,可以使用gulp-minify-css模塊。gulp.src支持使用數組的方式來指定要處理的文件列表。

    var gulp = require('gulp');
    var concat = require('gulp-concat');
    var uglify = require('gulp-uglify');
    var minifyCss = require('gulp-minify-css');
    var jsFiles = [
        './bower_components/jquery/dist/jquery.js', 
        './bower_components/bootstrap/dist/js/bootstrap.min.js', 
        ',/bower_components/PACE/pace.min.js', 
        './bower_components/angular/angular.js', 
        './bower_components/angular-new-router/dist/router.es5.js', 
        './bower_components/at-table/dist/angular-table.js', 
        './app/modules/businessApp.js', 
        './app/controllers/home.js'
    ];
    var cssFiles = [
        './bower_components/bootstrap/dist/css/bootstrap.min.css', 
        './bower_components/font-awesome/css/font-awesome.min.css', 
        './bower_components/PACE/themes/blue/pace-theme-loading-bar.css', 
        './static/css/start.css'
    ];
    // 在這兩個 `min` 任務之外,還有兩個不帶 `min` 的任務,區別在于不對文件壓縮
    gulp.task('scripts_min', function(){
      return gulp.src(jsFiles)
        .pipe(concat('all.js')) // 合并 JavaScript ,并設置合并后的文件名
        .pipe(uglify()) // 執行 JavaScript 壓縮
        .pipe(gulp.dest('./public/js'));
    });
    gulp.task('stylesheets_min', function(){
      return gulp.src(cssFiles)
        .pipe(concat('all.css')) // 合并 CSS ,并設置合并后的文件名
        .pipe(minifyCss()) // 執行 CSS 壓縮
        .pipe(gulp.dest('./public/stylesheet'));
    });

    管理圖片字體等靜態資源

    對于圖片、字體等文件,只是需要使用 Gulp 自帶的gulp.src和gulp.dest來復制到 Web 目錄即可。除了這些靜態文件,有些文件可能也需要單獨處理,比如 JavaScript 中的一些配置項文件,另外,如果使用加載狀態提示模塊,這個也是需要優秀加載的。順便安利一下 PACE ,它是個使用相當方便的加載提示模塊。

    gulp.task('pace', function(){
      // copy pace.js to js folder
      return gulp.src('./bower_components/PACE/pace.min.js')
        .pipe(gulp.dest('./public/js'));
    });

    其它需要直接復制的文件,也都是類似方法處理。

    使用 Gulp 來創建文件修改后瀏覽器自動刷新的 Web 服務器

    如果想要文件修改后,瀏覽器自動刷新,需要做兩方面的工作:

    • 監控 JavaScript / Jade / CSS 文件,修改后重新轉換或者壓縮
    • 監控 JavaScript / Jade / CSS 文件,修改后刷新瀏覽器
    • </ul>

      對于第一個,使用gulp-watch模塊來監視文件,并執行對應的 Task ,對于第二個,可以使用gulp-webserver模塊,它可以創建一個 Web 服務器,并且在瀏覽器和服務器之間創建 Socket.IO 長鏈接,一旦有文件修改,便通過長鏈接通知瀏覽器刷新頁面。

      var gulp = require('gulp');
      var webserver = require('gulp-webserver');

      gulp.task('watch', function(){ // 不同的文件個性,需要執行不同的任務來處理 gulp.watch(['app/views/', 'app/views/_partial/'], ['jade']); gulp.watch(['bower_components/'], ['scripts', 'stylesheets']); gulp.watch(['static/css/'], ['stylesheets']); gulp.watch(['app/controllers/', 'app/modules/', 'app/services/*'], ['scripts']); });

      gulp.task('webserver', function(){ gulp.src('./public/') .pipe(webserver({ host: '0.0.0.0', livereload: true, fallback: 'index.html' })); });</pre>

 本文由用戶 jopen 自行上傳分享,僅供網友學習交流。所有權歸原作者,若您的權利被侵害,請聯系管理員。
 轉載本站原創文章,請注明出處,并保留原始鏈接、圖片水印。
 本站是一個以用戶分享為主的開源技術平臺,歡迎各類分享!