使用 Grunt.js 进行 JavaScript 应用的打包与部署
1. 加载任务到 NPM 并添加 concat 插件
在将应用的 JavaScript 代码组装成单个文件时,我们需要将任务加载到 NPM 并添加 concat 插件到默认任务。具体操作步骤如下:
- 在命令行执行 grunt 命令,以将应用的 JavaScript 代码组装成单个文件。
- 为了保持 Gruntfile.js 文件的简洁和可读性,我们可以将每个插件的配置提取到单独的文件中。
2. 提取插件配置到单独文件
为了使主 Gruntfile.js 文件尽可能小且易于阅读,我们将插件配置提取到单独的文件中。具体步骤如下:
1. 创建一个名为 tasks 的新目录,用于存放插件配置文件。
2. 在 tasks 目录中创建一个名为 concat.js 的文件,内容如下:
module.exports = {
options: {
separator: '\n'
},
dist: {
src: ['js/app/**/*.js'],
dest: 'dist/<%= pkg.name %>.js'
}
};
- 更新
Gruntfile.js文件,使其使用concat.js文件,代码如下:
function config(name) {
return require('./tasks/' + name);
}
module.exports = function(grunt) {
grunt.initConfig({
pkg: grunt.file.readJSON('package.json'),
concat: config('concat')
});
grunt.loadNpmTasks('grunt-contrib-concat');
grunt.registerTask('default', ['concat']);
};
通过这些步骤,我们减少了 Gruntfile.js 文件的大小,提高了其可读性,同时创建了一种简单的机制来加载新插件到 Grunt.js 配置中。
3. 进行代码检查以消除常见错误
代码检查(Linting)是分析代码中常见错误和潜在问题的过程。对于 JavaScript 应用,代码检查还包括语法验证。具体操作如下:
1. 安装并添加 grunt-contrib-jshint 插件,在命令行执行以下命令:
npm install grunt-contrib-jshint --save-dev
- 在
tasks目录中创建一个名为jshint.js的文件,内容如下:
module.exports = {
files: ['Gruntfile.js', 'js/app/**/*.js', 'js/test/**/*.js'],
options: {
globals: {
jQuery: true,
console: true,
module: true
}
}
};
- 更新
Gruntfile.js文件,将jshint.js文件包含进来,并将其添加到默认任务中,代码如下:
function config(name) {
return require('./tasks/' + name);
}
module.exports = function(grunt) {
grunt.initConfig({
pkg: grunt.file.readJSON('package.json'),
concat: config('concat'),
jshint: config('jshint')
});
grunt.loadNpmTasks('grunt-contrib-concat');
grunt.loadNpmTasks('grunt-contrib-jshint');
grunt.registerTask('default', ['jshint', 'concat']);
};
运行 grunt 命令时,将对所有 JavaScript 源文件进行代码检查。如果有错误,JSHint 会报告并指出问题所在,方便我们修复。
4. 预编译 Handlebars 模板
Montric 应用的模板位于 templates 目录下的单独 .hbs 文件中。为了让 Ember.js 理解这些模板,我们需要将它们预编译到应用中。具体步骤如下:
1. 安装 grunt-ember-templates 插件,在命令行执行以下命令:
npm install grunt-ember-templates --save-dev
- 在
tasks目录中创建一个名为emberTemplates.js的文件,内容如下:
module.exports = {
compile: {
options: {
templateName: function(sourceFile) {
return sourceFile.replace(/templates\//, '');
}
},
files: {
"dist/templates.js": "templates/**/*.hbs"
}
}
};
- 更新
Gruntfile.js文件,将emberTemplates.js文件包含进来,并将其添加到默认任务中,代码如下:
function config(name) {
return require('./tasks/' + name);
}
module.exports = function(grunt) {
grunt.initConfig({
pkg: grunt.file.readJSON('package.json'),
concat: config('concat'),
jshint: config('jshint'),
emberTemplates: config('emberTemplates')
});
grunt.loadNpmTasks('grunt-contrib-concat');
grunt.loadNpmTasks('grunt-contrib-jshint');
grunt.loadNpmTasks('grunt-ember-templates');
grunt.registerTask('default',
['jshint', 'emberTemplates', 'concat']);
};
运行 grunt 命令后,所有模板将被编译成一个名为 templates.js 的文件,位于 dist 目录中。为了方便最终部署,我们更新 concat.js 文件,将预编译的模板文件包含进来:
module.exports = {
options: {
separator: '\n'
},
dist: {
src: ['js/app/**/*.js', 'dist/templates.js'],
dest: 'dist/<%= pkg.name %>.js'
}
};
流程总结
下面是当前的组装流程的 mermaid 流程图:
graph LR
A[查找 js/app 中的 *.js 文件] --> B[对文件内容进行代码检查]
C[查找 templates 中的 *.hbs 文件] --> D[编译成 Ember.TEMPLATES]
B --> E[将内容合并到 app.js]
D --> E
通过以上步骤,我们完成了 JavaScript 代码的合并、代码检查和模板预编译,为最终部署做好了准备。接下来,我们将对合并后的代码进行压缩,以创建适合生产环境部署的单个文件。
使用 Grunt.js 进行 JavaScript 应用的打包与部署
5. 压缩源代码
虽然之前合并后的文件可以用于生产应用,但在服务器和用户浏览器之间传输这样的 JavaScript 文件会比较冗长,因为代码中包含了空格、内联注释等对计算机无用的冗余信息。压缩(Minifying)就是尽可能去除这些冗余信息,同时不破坏应用功能的过程。具体操作如下:
1. 安装 grunt-contrib-uglify 插件,在命令行执行以下命令:
npm install grunt-contrib-uglify --save-dev
安装后, package.json 文件会添加该插件的依赖:
{
"name": "Montric",
"version": "0.9.0",
"devDependencies": {
"grunt": "~0.4.1",
"grunt-contrib-concat": "~0.3.0",
"grunt-contrib-jshint": "~0.6.0",
"grunt-ember-templates": "~0.4.10",
"grunt-contrib-uglify": "~0.2.2"
}
}
- 配置
uglify插件,在tasks目录中创建一个名为uglify.js的文件,内容如下:
module.exports = {
options: {
banner: '/*! <%= pkg.name %> <%= grunt.template.today("dd-mm-yyyy") %> */\n'
},
dist: {
files: {
'dist/<%= pkg.name %>.min.js': ['<%= concat.dist.dest %>']
}
}
};
在这段代码中, banner 属性指定了最终输出文件顶部显示的文本, files 属性定义了输出文件和输入文件。这里输入文件是 concat 插件创建的目标文件,输出文件是 dist 目录下的 Montric.min.js 。
3. 更新 Gruntfile.js 文件,将 uglify.js 文件包含进来,并将其添加到默认任务中,代码如下:
function config(name) {
return require('./tasks/' + name);
}
module.exports = function(grunt) {
grunt.initConfig({
pkg: grunt.file.readJSON('package.json'),
concat: config('concat'),
jshint: config('jshint'),
emberTemplates: config('emberTemplates'),
uglify: config('uglify')
});
grunt.loadNpmTasks('grunt-contrib-concat');
grunt.loadNpmTasks('grunt-contrib-jshint');
grunt.loadNpmTasks('grunt-ember-templates');
grunt.loadNpmTasks('grunt-contrib-uglify');
grunt.registerTask('default',
['jshint', 'emberTemplates', 'concat', 'uglify']);
};
运行 grunt 命令后, dist 目录中会生成三个文件: Montric.js 、 templates.js 和 Montric.min.js ,其中 Montric.min.js 是压缩后的文件,适合最终部署到生产环境。
6. 后续可探索的构建步骤
除了上述步骤,还可以进一步探索以下构建步骤:
- 在 concat 插件之前运行 QUnit 测试 :确保代码在合并之前通过测试,提高代码质量。
- 合并和压缩 CSS :减少 CSS 文件数量和大小,优化页面加载速度。
Grunt.js 社区活跃,有大量插件可供选择,你可以在 http://gruntjs.com/plugins/ 找到适合自己需求的插件。
7. Grunt.js 的优缺点分析
Grunt.js 作为一个新工具,有其独特的优势和不足之处:
| 优点 | 缺点 |
| ---- | ---- |
| 专为构建现代 JavaScript 应用设计,具有现代的以插件为中心的结构。 | 插件配置方式宽松,没有标准的配置方法,需要查阅每个插件的文档来更改或添加配置属性。 |
| 基于 Node.js,是原生的 JavaScript 构建工具,可直接访问强大的 JavaScript 解释器,便于集成 JavaScript 特定工具。 | 会在项目目录中创建 node_modules 目录,占用大量磁盘空间(如 33MB 且包含 2500 多个文件),污染项目目录。 |
总结
在 JavaScript 应用的组装和打包阶段,使用构建工具可以减少文件数量和传输的数据量,提高应用性能。Grunt.js 是一个基于 Node.js 的构建工具,与 Ember.js 应用使用相同的语言,在编译模板文件时可直接使用 JavaScript 解释器。
下面是完整的组装流程的 mermaid 流程图:
graph LR
A[查找 js/app 中的 *.js 文件] --> B[对文件内容进行代码检查]
C[查找 templates 中的 *.hbs 文件] --> D[编译成 Ember.TEMPLATES]
B --> E[将内容合并到 app.js]
D --> E
E --> F[对合并后的文件进行压缩]
F --> G[生成最终的 min.js 文件]
通过本文介绍的步骤,你可以完成 JavaScript 应用的打包和部署。希望你在后续的开发中继续探索 Ember.js 和 Grunt.js 的更多功能,开发出更优秀的 Web 应用。
超级会员免费看
776

被折叠的 条评论
为什么被折叠?



