閱讀499 返回首頁    go 阿裏雲 go 技術社區[雲棲]


《JavaScript開發框架權威指南》——2.3 將Grunt添加到項目中

本節書摘來自異步社區《JavaScript開發框架權威指南》一書中的第2章,第2.3節,作者:【美】Tim Ambler , Nicholas Cloud著,更多章節內容可以訪問雲棲社區“異步社區”公眾號查看

2.3 將Grunt添加到項目中

在本章前麵,為了添加Grunt命令行工具,我們將npm包grunt-cli作為全局模塊進行了安裝。現在我們應該已經可以在命令行中使用Grunt命令,但是對於每個要使用Grunt的工程,仍然需要為其配置Grunt本地依賴。為此,隻需在工程根目錄下運行以下命令即可。本例假設npm已經針對示例所用項目進行了初始化,package.json文件也已經存在。

$ npm install grunt --save-dev
現在,我們項目的package.json文件應該已經包含與清單中的示例代碼相仿的Grunt條目。

清單2-5 更新後的package.json文件

// example-tasks/package.json

{
    "name": "example-tasks",
    "version": "1.0.0",
    "devDependencies": {
        "grunt": "0.4.5"
    }
}

將Grunt與項目進行整合的最後一個步驟是創建Gruntfile(見清單),並保存在工程根目錄下。我們的Gruntfile隻調用了一個函數loadTasks(),其作用將在接下來的小節進行討論。

清單2-6 我們的Gruntfile

// example-tasks/Gruntfile.js

module.exports = function(grunt) {
    grunt.loadTasks('tasks');
};

保持合理的Grunt模式
我們希望你在讀完本章之後發現,Grunt的確是一件處理日常工作流程中遇到的乏味的重複性工作的利器。但是即便如此,還是不得不承認我們對Grunt的第一反應絕對算不上積極。事實上,剛開始我們對它興趣不大。為了了解其中的原因,我們看一下放在Grunt官方文檔顯著位置的Gruntfile示例(見清單)。

清單2-7 Grunt官方文檔提供的Gruntfile示例

module.exports = function(grunt) {

    grunt.initConfig({
        pkg: grunt.file.readJSON('package.json'),
        concat: {
            options: {
                separator: ';'
            },
            dist: {
                src: ['src/**/*.js'],
                dest: 'dist/<%= pkg.name %>.js'
            }
        },
        uglify: {
            options: {
                banner: '/*! <%= grunt.template.today("dd-mm-yyyy") %> */\n'
            },
            dist: {
                files: {
                    'dist/<%= pkg.name %>.min.js': ['<%= concat.dist.dest %>']
                }
            }
        },
        qunit: {
            files: ['test/**/*.html']
        },
        jshint: {
            files: ['Gruntfile.js', 'src/* */*.js', 'test/**/*.js'],
            options: {
                // options here to override JSHint defaults
                globals: {
                    jQuery: true,
                    console: true,
                    module: true,
                    document: true
                }
            }
        },
        watch: {
            files: ['<%= jshint.files %>'],
            tasks: ['jshint', 'qunit']
        }
    });
    grunt.loadNpmTasks('grunt-contrib-uglify');
    grunt.loadNpmTasks('grunt-contrib-jshint');
    grunt.loadNpmTasks('grunt-contrib-qunit');
    grunt.loadNpmTasks('grunt-contrib-watch');
    grunt.loadNpmTasks('grunt-contrib-concat');

    grunt.registerTask('test', ['jshint', 'qunit']);

    grunt.registerTask('default', ['jshint', 'qunit', 'concat', 'uglify']);

};

清單中略顯臃腫的Gruntfile還是為相對簡單的項目準備的。對於規模更大的項目,Gruntfile會像吹氣球一樣膨脹好幾倍,最終結果就是一大堆根本無法閱讀又難以維護的東西。有經驗的開發者絕不會在寫代碼的時候,將不相關的功能模塊揉在一起。否則,我們為什麼還要在任務運行器上搞點兒花樣出來呢?

正如清單中的代碼所示,使Grunt模式保持合理的秘密就藏在Grunt的loadTasks()方法上。該例中task參數指向task文件夾,其路徑以工程的Gruntfile為參考位置。loadTask()方法一被調用,Grunt就會加載並執行在該文件夾下發現的所有Node模塊,並且每次都將Grunt對象的引用作為參數傳進去。這樣的行為使我們可以將項目的Grunt配置劃分為一係列相互獨立的模塊,每個模塊負責一個單獨的任務或插件的加載及配置工作。清單展示了其中一個小型模塊,模塊中定義的任務可以通過在命令行中執行grunt uglify來運行。

清單2-8 task文件夾中的示例模塊(uglify.js)

// example-tasks/tasks/uglify.js

module.exports = function(grunt) {

    grunt.loadNpmTasks('grunt-contrib-uglify');

    grunt.config('uglify', {
        'options': {
            'banner': '/*! <%= grunt.template.today("dd-mm-yyyy") %> */\n'
        },
        'dist': {
            'files': {
                'dist/app.min.js': ['src/index.js']
            }
        }
    });

};

最後更新:2017-06-05 14:32:20

  上一篇:go  Python 單元測試:assertTrue 是真值,assertFalse 是假值
  下一篇:go  《JavaScript開發框架權威指南》——2.2 Grunt是如何工作的