Grunt - 快速指南



Grunt - 概述

什麼是 Grunt?

Grunt 是一個 JavaScript 任務執行器,可以用作 JavaScript 物件的命令列工具。它是一個構建在 NodeJS 之上的任務管理器。

為什麼要使用 Grunt?

  • Grunt 可以非常輕鬆地執行重複性任務,例如編譯、單元測試、壓縮檔案、執行測試等。

  • Grunt 包含內建任務,可以擴充套件外掛和指令碼的功能。

  • Grunt 的生態系統非常龐大;您可以用很少的精力自動化任何操作。

歷史

GruntJS 的第一行原始碼於 2011 年新增。Grunt v0.4 於 2013 年 2 月 18 日釋出。Grunt v0.4.5 於 2014 年 5 月 12 日釋出。Grunt 的穩定版本是 1.0.0 rc1,於 2016 年 2 月 11 日釋出。

優點

  • 使用 Grunt,您可以輕鬆地執行檔案的壓縮、編譯和測試。

  • Grunt 統一了 Web 開發人員的工作流程。

  • 您可以使用 Grunt 輕鬆地處理新的程式碼庫,因為它包含較少的基礎設施。

  • 它可以加快開發工作流程並提高專案的效能。

缺點

  • 每當 npm 包更新時,您都需要等待 Grunt 的作者更新它。

  • 每個任務都設計用於執行指定的工作。如果要擴充套件指定的任務,則需要使用一些技巧才能完成工作。

  • Grunt 包含大量用於各個外掛的配置引數。通常,Grunt 配置檔案較長。

Grunt - 特性

Grunt 是一個基於 JavaScript 的任務執行器,這意味著它可以自動化工作流程中的重複性任務,並且可以用作 JavaScript 物件的命令列工具。

GruntJS 的一些最突出的特性如下所示:

  • Grunt 使工作流程像編寫設定檔案一樣簡單。

  • 您可以用最少的精力自動化重複性任務。

  • Grunt 是一個基於 NodeJS 的流行任務執行器。它靈活且被廣泛採用。

  • 它採用了一種直接的方法,包括 JS 中的任務和 JSON 中的配置。

  • Grunt 壓縮 JavaScript、CSS 檔案、測試檔案、編譯 CSS 預處理器檔案(SASS、LESS)等。

  • Grunt 包含內建任務,可以擴充套件外掛和指令碼的功能。

  • 它可以加快開發工作流程並提高專案的效能。

  • 您可以使用 Grunt 輕鬆地處理新的程式碼庫,因為它包含較少的基礎設施。

  • Grunt 的生態系統非常龐大;您可以用很少的精力自動化任何操作。

  • Grunt 減少了在執行重複性任務時出錯的可能性。

  • Grunt 目前擁有超過 4000 個外掛。

  • 它可以用於大型生產站點。

Grunt - 安裝

本章提供瞭如何在系統上安裝 Grunt 的分步過程。

Grunt 的系統要求

  • 作業系統 - 跨平臺

  • 瀏覽器支援 - IE(Internet Explorer 8+)、Firefox、Google Chrome、Safari、Opera

Grunt 的安裝

步驟 1 - 我們需要 NodeJs 來執行 Grunt。要下載 NodeJs,請開啟連結 https://nodejs.com.tw/en/,您將看到如下所示的螢幕:

Grunt Installation

下載壓縮檔案的最新功能版本。

步驟 2 - 接下來,執行安裝程式以在您的計算機上安裝NodeJs

步驟 3 - 接下來,您需要設定環境變數

路徑使用者變數

  • 右鍵單擊我的電腦
  • 選擇屬性
  • 接下來,選擇高階選項卡,然後單擊環境變數
Grunt Installation
  • 環境變數視窗下,雙擊PATH,如螢幕所示。

Grunt Installation
  • 您將獲得一個編輯使用者變數視窗,如所示。在變數值欄位中新增 NodeJs 資料夾路徑,如C:\Program Files\nodejs\node_modules\npm。如果已為其他檔案設定了路徑,則需要在其後新增分號(;),然後新增 NodeJs 路徑,如下所示:

Grunt Installation

最後,單擊確定按鈕。

系統變數

  • 系統變數下,雙擊Path,如以下螢幕所示。

Grunt Installation
  • 您將獲得一個編輯系統變數視窗,如所示。在變數值欄位中新增 NodeJs 資料夾路徑,如C:\Program Files\nodejs\,然後單擊確定,如下所示:

Grunt Installation

步驟 4 - 要在您的系統上安裝 grunt,您需要全域性安裝 Grunt 的命令列介面 (CLI),如下所示:

npm install -g grunt-cli

執行上述命令會將grunt命令放入您的系統路徑中,這使其能夠從任何目錄執行。

安裝grunt-cli不會安裝 Grunt 任務執行器。grunt-cli的作用是執行已安裝在Gruntfile旁邊的 Grunt 版本。它允許一臺機器同時安裝多個版本的 Grunt。

步驟 5 - 現在,我們將建立配置檔案以執行 Grunt。

package.json

package.json檔案放置在專案的根目錄中,位於Gruntfile旁邊。package.json用於在您在與 package.json 相同的資料夾中執行命令npm install時正確執行每個列出的依賴項。

可以透過在命令提示符中鍵入以下命令來建立基本的package.json

npm init

基本的package.json檔案將如下所示:

{
   "name": "tutorialspoint",
   "version": "0.1.0",
   "devDependencies": {
      "grunt-contrib-jshint": "~0.10.0",
      "grunt-contrib-nodeunit": "~0.4.1",
      "grunt-contrib-uglify": "~0.5.0"
   }
}

您可以透過以下命令將 Grunt 和 gruntplugins 新增到現有的pacakge.json檔案中:

npm install <module> --save-dev

在上述命令中,<module>表示要本地安裝的模組。上述命令還會自動將<module>新增到devDependencies中。

例如,以下命令將安裝最新版本的Grunt並將其新增到您的devDependencies中:

npm install grunt --save-dev

Gruntfile.js

Gruntfile.js檔案用於定義我們 Grunt 的配置。這是我們編寫設定的地方。基本的Gruntfile.js檔案如下所示:

// our wrapper function (required by grunt and its plugins)
// all configuration goes inside this function
module.exports = function(grunt) {
   // CONFIGURE GRUNT
   grunt.initConfig({
      // get the configuration info from package.json file
      // this way we can use things like name and version (pkg.name)
      pkg: grunt.file.readJSON('package.json'),

      // all of our configuration goes here
      uglify: {
         // uglify task configuration
         options: {},
         build: {}
      }
   });

   // log something
   grunt.log.write('Hello world! Welcome to Tutorialspoint!!\n');

   // Load the plugin that provides the "uglify" task.
   grunt.loadNpmTasks('grunt-contrib-uglify');

   // Default task(s).
   grunt.registerTask('default', ['uglify']);
};

Grunt - 入門

要使用 Grunt,您需要安裝 Node.js。Node.js 的安裝已在前面的章節中進行了說明。您可以使用 Node.js 包管理器安裝 Grunt 和 Grunt 外掛。

在系統上設定 Grunt 之前,您可以使用以下命令更新 Node 包管理器:

npm update -g npm

如果您使用的是 Mac 或 Linux,則需要在命令列的開頭使用sudo字樣以授予管理員訪問許可權,如下所示:

sudo npm update -g npm

CLI 安裝

CLI 代表命令列介面,它執行已安裝的 Grunt 版本。要開始使用 Grunt,您需要全域性安裝 Grunt 的命令列介面 (CLI),如下所示:

npm install -g grunt-cli

執行上述命令會將 grunt 命令放入您的系統路徑中,這使其能夠從任何目錄執行。您無法透過安裝grunt-cli來安裝 Grunt 任務執行器。它允許一臺機器同時安裝多個版本的 Grunt。

CLI 的工作原理

每當執行 Grunt 時,CLI 會使用require()系統在您的系統上查詢已安裝的 Grunt。使用grunt-cli,您可以從專案中的任何目錄執行 Grunt。如果您使用的是本地安裝的 Grunt,則 grunt-cli 使用本地安裝的 Grunt 庫並應用來自 Grunt 檔案的配置。

處理現有專案和新專案

如果您正在處理一個已配置的專案,其中包含package.jsonGruntfile,則請按照以下說明進行操作:

  • 找到專案根目錄的路徑。
  • 您可以使用npm install命令安裝依賴項。
  • 使用grunt命令執行 Grunt。

如果您正在建立一個新專案,則將兩個檔案package.jsonGruntfile包含到您的專案中。

  • package.json - package.json檔案放置在專案的根目錄中,並且在您在同一資料夾中執行命令npm install時用於執行每個列出的依賴項。

  • Gruntfile.js - Gruntfile.js檔案用於編寫專案的配置設定。

package.json

package.json檔案放置在專案的根目錄中,位於Gruntfile旁邊,並且在您在同一資料夾中執行命令npm install時用於執行每個列出的依賴項。

您可以透過以下列出的不同方式建立package.json

  • 您可以使用grunt-init建立 package.json 檔案。
  • 您也可以使用npm-init命令建立 package.json 檔案。

您可以編寫如下所示的規範:

{
   "name": "tutorialspoint",
   "version": "0.1.0",
   "devDependencies": {
      "grunt-contrib-jshint": "~0.10.0",
      "grunt-contrib-nodeunit": "~0.4.1",
      "grunt-contrib-uglify": "~0.5.0"
   }
}

您可以透過使用以下命令將 Grunt 和 gruntplugins 新增到現有的 pacakge.json 檔案中:

npm install <module> --save-dev

這裡,<module>表示要本地安裝的模組。上述命令將安裝指定的模組並自動將其新增到devDependencies部分。

例如,以下命令將安裝最新版本的Grunt並將其新增到您的devDependencies中:

npm install grunt --save-dev

Gruntfile

Gruntfile.js檔案是預設位置,您將在其中為 Grunt 新增配置設定。Grunt 檔案包含以下部分:

  • 包裝函式
  • 專案和任務配置
  • 載入 Grunt 外掛和任務
  • 自定義任務

基本的Gruntfile.js檔案如下所示:

// our wrapper function (required by grunt and its plugins)
// all configuration goes inside this function
module.exports = function(grunt) {

   // CONFIGURE GRUNT
   grunt.initConfig({
      // get the configuration info from package.json file
      // this way we can use things like name and version (pkg.name)
      pkg: grunt.file.readJSON('package.json'),

      // all of our configuration goes here

   });

   // Load the plugin that provides the "uglify" task
   grunt.loadNpmTasks('grunt-contrib-uglify');

   // Default task(s)
   grunt.registerTask('default', ['uglify']);
};

包裝函式

在上面的程式碼中,module.exports是一個包裝函式,整個配置都位於此函式內部。這是一種將配置顯示給應用程式其餘部分的方式。

module.exports = function(grunt) {
   //do grunt-related things here
}

專案和任務配置

準備好 Grunt 配置後,您可以配置 Grunt 任務。專案配置可以寫入grunt.initConfig()部分。在grunt.initConfig()函式內部,從 package.json 檔案中獲取配置資訊並將其儲存到pkg中。您可以使用pkg.name呼叫專案名稱,使用pkg.version呼叫版本。

載入 Grunt 外掛和任務

使用grunt.loadNpmTasks方法從指定的外掛載入任務。您可以使用npm本地安裝外掛,並且它必須相對於 Gruntfile。您可以使用簡單的命令載入外掛,如下所示:

grunt.task.loadNpmTasks(pluginName)

自定義任務

當您透過命令列執行 Grunt 時,Grunt 將查詢default任務。在上面的程式碼中,我們使用了一個名為uglify的任務,它可以使用grunt命令執行。這與顯式執行grunt uglify命令相同,您可以在陣列中指定任務數量。

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

Grunt - 配置任務

您可以在Gruntfile.js 檔案中定義專案特定的配置資料。

Grunt 配置

可以透過使用grunt.initConfig()方法在 Gruntfile 中初始化任務配置資料。在grunt.initConfig()函式內部,獲取來自 package.json 檔案的配置資訊。配置將包含一個名為properties的任務和任意資料。

grunt.initConfig({
   jshint: {
      // configuration for jshint task
   },
   cssmin: {
      // configuration for cssmin task
   },
   // Arbitrary non-task-specific properties
   my_files: ['dir1/*.js', 'dir2/*.js'],
});

任務配置和目標

當您執行任務時,Grunt 會在以任務命名的屬性下查詢配置。我們將定義具有多個配置和目標選項的任務,如下所示:

grunt.initConfig({
   jshint: {
      myfile1: {
         // configuration for "myfile1" target options
      },
      myfile2: {
         // configuration for "myfile2" target options
      },
   },
   cssmin: {
      myfile3: {
         // configuration for "myfile3" target options
      },
   },
});

這裡,jshint 任務具有 myfile1myfile2 目標,而 cssmin 任務具有 myfile3 目標。當您執行 grunt jshint 時,它將遍歷任務和目標以處理指定目標的配置。

選項

在任務配置內定義 options 屬性,該屬性會覆蓋任務預設值。每個目標都包含 options 屬性,該屬性會覆蓋任務級別的選項。它將具有以下格式:

grunt.initConfig({
   jshint: {
      options: {
         // task-level options that overrides task defaults
      },
      myfile: {
         options: {
            // "myfile" target options overrides task defaults
         },
      },

      myfile1: {
         // there is no option, target will use task-level options
      },
   },
});

檔案

Grunt 提供了一些關於指定任務應操作哪些檔案的思路,並使用不同的方法來指定 src-dest 檔案對映。以下是 srcdest 對映支援的一些其他屬性:

  • filter - 它是一個函式,用於指定匹配的 src 檔案路徑並返回 true 或 false 值。

  • nonull - 當設定為 true 時,它定義不匹配的模式。

  • dot - 它匹配以句點開頭的檔名或其他檔名。

  • matchBase - 它匹配包含斜槓且與路徑基本名稱匹配的模式。

  • expand - 它處理 src-dest 檔案對映。

緊湊格式

它指定每個目標的 src-dest 檔案對映,可用於只讀任務,並且只需要 src 屬性,不需要 dest 屬性。

grunt.initConfig({
   jshint: {
      myfile1: {
         src: ['src/file1.js','src/file2.js']
      },
   },
   cssmin: {
      myfile2: {
         src: ['src/file3.js','src/file4.js'],
         dest: 'dest/destfile.js',
      },
   },
});

檔案物件格式

它指定每個目標的 src-dest 檔案對映,其中屬性名稱為 dest 檔案,其值為 src 檔案。

grunt.initConfig({
   jshint: {
      myfile1: {
         files: {
            'dest/destfile.js':['src/file1.js','src/file2.js'],
            'dest/destfile1.js':['src/file3.js','src/file4.js'],
         },
      },
      myfile2: {
         files: {
            'dest/destfile2.js':['src/file22.js','src/file23.js'],
            'dest/destfile21.js':['src/file24.js','src/file25.js'],
         },
      },
   },
});

檔案陣列格式

它透過使用每個對映的其他屬性來指定每個目標的 src-dest 檔案對映。

grunt.initConfig({
   jshint: {
      myfile1: {
         files: [
            {src:['src/file1.js','src/file2.js'],dest:'dest/file3.js'},
            {src:['src/file4.js','src/file4.js'],dest:'dest/file5.js'},
         ],
      },
      myfile2: {
         files: [
            {src:['src/file6.js','src/file7.js'],dest:'dest/file8/', nonull:true},
            {src:['src/file9.js','src/file10.js'],dest:'dest/file11/', filter:'isFalse'},
         ],
      },
   },
});

舊格式

dest-as-target 檔案格式在多工存在之前就存在了,其中目標檔案路徑是目標的名稱。以下格式已棄用,程式碼中不應使用。

grunt.initConfig({
   jshint: {
      'dest/destfile2.js':['src/file3.js','src/file4.js'],
      'dest/destfile5.js':['src/file6.js','src/file7.js'],
   },
});

自定義過濾器函式

您可以透過使用 filter 屬性,更詳細地幫助目標檔案。以下格式僅在匹配實際檔案時才清理檔案。

grunt.initConfig({
   clean: {
      myfile:{
         src: ['temp/**/*'],
         filter: 'isFile',
      },
   },
});

萬用字元模式

萬用字元表示擴充套件檔名。Grunt 透過使用 內建的 node-globminimatch 庫 支援萬用字元。萬用字元模式包括以下幾點:

  • * 匹配任意數量的字元,但不匹配 /
  • ? 匹配單個字元,但不匹配 /
  • ** 匹配任意數量的字元,包括 /
  • {} 指定以逗號分隔的“或”表示式列表。
  • ! 將在開頭否定模式匹配。

例如:

{src: 'myfile/file1.js', dest: ...} // it specifies the single file

{src: 'myfile/*.js', dest: ...} //it matches all the files ending wth .js

{src: 'myfile/{file1,file2}*.js', dest: ...} //defines the single node glob pattern

{src: ['myfile/*.js', '!myfile/file1.js'], dest: ...} // all files will display in alpha

// order except for file1.js

動態構建檔案物件

當您處理單個檔案時,可以使用其他屬性來動態構建檔案列表。當您將 expand 屬性設定為 true 時,它將啟用以下一些屬性:

  • cwd 將所有 src 匹配到此路徑。

  • src 匹配要匹配的模式,相對於 cwd

  • dest 屬性指定目標路徑字首。

  • ext 將用在 dest 路徑中生成的 value 替換現有副檔名。

  • extDot 指示指示副檔名的句點所在位置。它使用第一個句點或最後一個句點;預設情況下,它設定為第一個句點。

  • flattendest 路徑中刪除所有路徑部分。

  • rename 指定包含新目標和檔名的字串。

Rename 屬性

它是一個唯一的 JavaScript 函式,返回一個字串,您不能對 rename 使用字串值。在以下示例中,copy 任務將建立 README.md 的備份。

grunt.initConfig({
   copy: {
      backup: {
         files: [{
            expand: true,
            src: ['docs/README.md'],    // creating a backup of README.md
            rename: function () {       // specifies the rename function
               return 'docs/BACKUP.txt'; // returns a string with the complete destination
            }
         }]
      }
   }
});

模板

您可以使用 <% %> 分隔符指定模板。讀取配置時,它們將自動擴充套件。它包括兩種型別的屬性:

  • <%= prop.subprop %> 屬性用於擴充套件配置中prop.subprop 的值,可以引用字串值、陣列和其他物件。

  • <% %> 屬性執行用於控制流或迴圈的內聯 JavaScript 程式碼。

例如:

grunt.initConfig({
   concat: {
      myfile: {
         options: {
            banner: '/* <%= val %> */\n',
         },
         src: ['<%= myval %>', 'file3/*.js'],
         dest: 'build/<%= file3 %>.js',
      },
   },
   // properties used in task configuration templates
   file1: 'c',
   file2: 'b<%= file1 %>d',
   file3: 'a<%= file2 %>e',
   myval: ['file1/*.js', 'file2/*.js'],
});

匯入外部資料

您可以從 package.json 檔案 匯入外部資料。grunt-contrib-uglify 外掛可用於縮小原始檔,並使用元資料建立橫幅註釋。您可以使用 grunt.file.readJSONgrunt.file.readYAML 匯入 JSON 和 YAML 資料。

例如:

grunt.initConfig({
   pkg: grunt.file.readJSON('package.json'),
   uglify: {
      options: {
         banner: '/*! <%= pkg.name %> <%= grunt.template.today("yyyy-mm-dd") %> */\n'
      },
      dist: {
         src: 'src/<%= pkg.name %>.js',
         dest: 'dist/<%= pkg.name %>.min.js'
      }
   }
});

Grunt - 示例檔案

在本章中,讓我們使用以下外掛建立一個簡單的 Grunt 檔案:

  • grunt-contrib-uglify
  • grunt-contrib-concat
  • grunt-contrib-jshint
  • grunt-contrib-watch

安裝所有上述外掛,並按照以下步驟建立一個簡單的 Gruntfile.js

步驟 1 - 您需要建立一個 wrapper 函式,該函式封裝 Grunt 的配置。

module.exports = function(grunt) {};

步驟 2 - 初始化您的配置物件,如下所示:

grunt.initConfig({});

步驟 3 - 接下來,將專案設定從 package.json 檔案讀取到 pkg 屬性中。它使我們能夠在您的 package.json 檔案中引用屬性值。

pkg: grunt.file.readJSON('package.json')

步驟 4 - 接下來,您可以為任務定義配置。讓我們建立我們的第一個任務 concat 來連線 src/ 資料夾中存在的所有檔案,並將連線的 .js 檔案儲存在 dist/ 資料夾下。

concat: {
   options: {
      // define a string to insert between files in the concatenated output
      separator: ';'
   },
   dist: {
      // files needs to be concatenated
      src: ['src/**/*.js'],
      // location of the concatenated output JS file
      dest: 'dist/<%= pkg.name %>.js'
   }
}

步驟 5 - 現在,讓我們建立另一個名為 uglify 的任務來縮小我們的 JavaScript。

uglify: {
   options: {
      // banner will be inserted at the top of the output which displays the date and time
      banner: '/*! <%= pkg.name %> <%= grunt.template.today() %> */\n'
   },
   dist: {
      files: {
         'dist/<%= pkg.name %>.min.js': ['<%= concat.dist.dest %>']
      }
   }
}

上述任務在 dist/ 資料夾內建立一個檔案,其中包含縮小的 .js 檔案。<%= concat.dist.dest %> 將指示 uglify 縮小 concat 任務生成的的檔案。

步驟 6 - 讓我們透過建立 jshint 任務來配置 JSHint 外掛。

jshint: {
   // define the files to lint
   files: ['Gruntfile.js', 'src/**/*.js'],
   // configure JSHint
   options: {
      // more options here if you want to override JSHint defaults
      globals: {
         jQuery: true,
      }
   }
}

上述 jshint 任務接受一個檔案陣列,然後是一個選項物件。上述任務將在 Gruntfile.jssrc/**/*.js 檔案中查詢任何編碼違規。

步驟 7 - 接下來,我們有 watch 任務,它查詢任何指定檔案的更改並執行您指定的任務。

watch: {
   files: ['<%= jshint.files %>'],
   tasks: ['jshint']
}

步驟 8 - 接下來,我們必須載入已透過 _npm 安裝的所有 Grunt 外掛。

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

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

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

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

步驟 9 - 最後,我們必須定義 default 任務。

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

只需在命令列上鍵入 grunt 命令即可執行 default 任務。

這是您完整的 Gruntfile.js

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: '/*! <%= pkg.name %> <%= grunt.template.today() %> */\n'
         },
         dist: {
            files: {
               'dist/<%= pkg.name %>.min.js': ['<%= concat.dist.dest %>']
            }
         }
      },
      jshint: {
         // define the files to lint
         files: ['Gruntfile.js', 'src/**/*.js'],
         // configure JSHint
         options: {
            // more options here if you want to override JSHint defaults
            globals: {
               jQuery: true,
            }
         }
      },
      watch: {
         files: ['<%= jshint.files %>'],
         tasks: ['jshint']
      }
   });

   grunt.loadNpmTasks('grunt-contrib-uglify');
   grunt.loadNpmTasks('grunt-contrib-jshint');
   grunt.loadNpmTasks('grunt-contrib-watch');
   grunt.loadNpmTasks('grunt-contrib-concat');

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

};

Grunt - 建立任務

在本章中,讓我們學習 建立任務。每當您執行 Grunt 時,都會指定一個或多個要執行的任務,通知 Grunt 您希望它執行的操作。如果您指定了 default 任務,則它將預設執行。

別名任務

每當指定任務列表時,一個或多個其他任務都可以透過新任務進行別名化。執行別名將依次執行 taskList 中指定的每個任務。taskList 引數應為任務陣列,如下所示:

grunt.registerTask(taskName, [description, ] taskList)	

例如,當您使用 jshintconcatuglify 任務定義 taskList 並將 taskName 指定為 default 時,如果 Grunt 在未指定任何任務的情況下執行,則所有列出的任務都將自動執行。

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

您還可以指定任務引數,如下所示:

grunt.registerTask('dist', ['concat:dist', 'uglify:dist']);	

在上述任務中,別名 dist 執行 concatuglify 任務。

多工

每當您執行多個任務時,Grunt 都會在 Grunt 配置中搜索同名屬性。這些任務可以有多個配置,這些配置將使用任意命名的 targets 定義。

當您同時指定任務和目標時,只會處理指定的 target 配置。

grunt concat:foo

上述命令將只執行目標 foo

當您只指定任務時,將處理所有目標。

grunt concat

上述命令將遍歷 concat 任務的所有目標。

當您使用 grunt.task.renameTask 重新命名任務時,Grunt 會在 config 物件中搜索具有 new 任務名稱的屬性。

grunt.initConfig({
   log: {
      foo: [1, 2, 3],
      bar: 'Welcome to tutorialspoint',
      sap: true
   }
});

grunt.registerMultiTask('log', 'Log stuff.', function() {
   grunt.log.writeln(this.target + ': ' + this.data);
});

在上面的示例中,如果 Grunt 透過 grunt log:foo 執行,則多工將記錄 foo: 1,2,3;如果透過 grunt log:bar 執行,則將記錄 bar: Welcome to tutorialspoint。當 Grunt 作為 grunt log 執行時,它將首先記錄 foo: 1,2,3,然後記錄 bar: Welcome to tutorialspoint,最後記錄 sap: true

基本任務

每當您執行基本任務時,Grunt 不會搜尋配置或環境。而是執行指定的 task 函式,並將作為函式引數指定的任何冒號分隔的引數傳遞進去。

grunt.registerTask(taskName, [description, ] taskFunction)	

在以下示例中,如果 Grunt 透過 grunt foo:testing:123 命令執行,則任務將記錄 foo, testing 123。每當任務在沒有引數的情況下作為 grunt foo 執行時,任務將 log foo, no args

grunt.registerTask('foo', 'A simple task to logs stuff.', function(arg1, arg2) {
   if (arguments.length === 0) {
      grunt.log.writeln(this.name + ", no args");
   } else {
      grunt.log.writeln(this.name + ", " + arg1 + " " + arg2);
   }
});

自定義任務

如果您不想遵循 多工 結構,您可以定義自定義任務,如下所示:

grunt.registerTask('default', 'My "default" task description.', function() {
  grunt.log.writeln('Currently running the "default" task.');
});  

可以在另一個任務中執行任務,如下所示:

grunt.registerTask('foo', 'My "foo" task.', function() {
   // Enqueue bar and baz tasks, to run after foo completes, in-order.
   grunt.task.run('bar', 'baz');
   // Or:
   grunt.task.run(['bar', 'baz']);
});  

您還可以建立非同步任務,如下所示:

grunt.registerTask('asyncfoo', 'My "asyncfoo" task.', function() {
   // Force task into async mode and grab a handle to the done() function.
   var done = this.async();
   // Run some sync stuff.
   grunt.log.writeln('Processing your task..');
   // Run some async stuff.
   setTimeout(function() {
      grunt.log.writeln('Finished!');
      done();
   }, 1000);
});

您可以建立可以訪問其名稱和引數的任務,如下所示:

grunt.registerTask('foo', 'My task "foo" .', function(a, b) {
   grunt.log.writeln(this.name, a, b);
});

// Usage:
// grunt foo
//   logs: "foo", undefined, undefined
// grunt foo:bar
//   logs: "foo", "bar", undefined
// grunt foo:bar:baz
//   logs: "foo", "bar", "baz"

您可以建立任務,以便每當記錄任何錯誤時,任務都可能失敗,如下所示:

grunt.registerTask('foo', 'My task "foo" .', function() {
   if (failureOfSomeKind) {
      grunt.log.error('This is an error message.');
   }

   // If this task had errors then fail by returning false
   if (ifErrors) { return false; }

   grunt.log.writeln('This is success message');
});  

每當任務失敗時,所有後續任務都將終止,除非指定了 --force

grunt.registerTask('foo', 'My task "foo" .', function() {
   // Fail synchronously.
   return false;
});

grunt.registerTask('bar', 'My task "bar" .', function() {
   var done = this.async();
   setTimeout(function() {
      // Fail asynchronously.
      done(false);
   }, 1000);
});  

任務可能依賴於其他任務才能成功執行。請記住,grunt.task.requires 實際上不會執行其他任務,而只是檢查它是否已執行且未失敗。

grunt.registerTask('foo', 'My task "foo" .', function() {
   return false;
});

grunt.registerTask('bar', 'My task "bar" .', function() {
   // Fail task if foo task failed or never ran.
   grunt.task.requires('foo');
   // This code executes if the foo task executed successfully.
   grunt.log.writeln('Hello, World.. Welcome to Tutorialspoint!..');
});

// Usage:
// grunt foo bar doesn't log, because foo failed to execute.
// **Note: This is an example of space-separated sequential commands,
// (similar to executing two lines of code: `grunt foo` then `grunt bar`)
// grunt bar doesn't log, because foo never ran.  

如果找不到所需的配置屬性,任務甚至可能失敗。

grunt.registerTask('foo', 'My task "foo" .', function() {
   // Fail task if meta.name config properties is missing
   // Format 1: String 
   grunt.config.requires('meta.name');
   // or Format 2: Array
   grunt.config.requires(['meta', 'name']);
   // Log... conditionally.
   grunt.log.writeln('This only log if meta.name is defined in the config.');
});  

任務可以訪問配置屬性,如下所示:

grunt.registerTask('foo', 'My task "foo" .', function() {
   // Log the value of the property. Returns null if the property is undefined.
   grunt.log.writeln('The meta.name property is: ' + grunt.config('meta.name'));
   // Also logs the value of the property. Returns null if the property is undefined.
   grunt.log.writeln('The meta.name property is: ' + grunt.config(['meta', 'name']));
});  
廣告

© . All rights reserved.