我正在尝试总结我对最流行的JavaScript包管理器,捆绑器和任务运行器的了解 . 如果我错了,请纠正我:
-
npm
&bower
是包管理器 . 他们只是下载依赖项,不知道如何自己构建项目 . 他们知道的是在获取所有依赖项后调用webpack
/gulp
/grunt
. -
bower
与npm
类似,但构建了扁平的依赖树(与递归执行的npm
不同) . 含义npm
获取每个依赖项的依赖项(可能会获取相同的几次),而bower
期望您手动包含子依赖项 . 有时bower
和npm
分别用于前端和后端(因为每兆字节在前端可能很重要) . -
grunt
和gulp
是任务运行器,用于自动化所有可自动化的东西(即编译CSS / Sass,优化图像,制作捆绑并缩小/转换它) . -
grunt
与gulp
(类似于maven
与gradle
或配置与代码相似) . Grunt基于配置单独的独立任务,每个任务打开/处理/关闭文件 . Gulp需要的代码量较少,并且基于节点流,这使得它可以构建管道链(无需重新打开同一个文件)并使其更快 . -
webpack
(webpack-dev-server
) - 对我来说,这是一个热门重新加载更改的任务运行器,可以让你忘记所有JS / CSS观察者 . -
npm
/bower
插件可能会替换任务运行器 . 他们的能力经常交叉,所以如果你需要使用gulp
/grunt
而不是npm
插件,会有不同的含义 . 但是任务运行者肯定更适合复杂的任务(例如"on each build create bundle, transpile from ES6 to ES5, run it at all browsers emulators, make screenshots and deploy to dropbox through ftp") . -
browserify
允许为浏览器打包节点模块 .browserify
vsnode
的require
实际上是AMD vs CommonJS .
Questions:
-
什么是
webpack
&webpack-dev-server
?官方文件说's a module bundler but for me it'只是一个任务运行员 . 有什么不同? -
你会在哪里使用
browserify
?对于node / ES6导入,我们不能这样做吗? -
你什么时候使用
gulp
/grunt
而不是npm
插件? -
请在需要使用组合时提供示例
8 回答
关于npm的一个小注释:npm3尝试以平面方式安装依赖项
https://docs.npmjs.com/how-npm-works/npm3#npm-v3-dependency-resolution
webpack-dev-server是一个实时重装Web服务器,Webpack开发人员使用它来获得他们所做的即时反馈 . 它应该只在开发期间使用 .
该项目深受nof5单元测试工具的启发 .
顾名思义,Webpack将为 web 创建一个单独的 pack 年龄 . 软件包将被最小化,并合并为一个文件(我们仍然生活在HTTP 1.1时代) . Webpack将组合资源(JavaScript,CSS,图像)和注入它们的神奇之处:
<script src="assets/bundle.js"></script>
.它也可以称为模块捆绑器,因为它必须了解模块依赖关系,以及如何获取依赖关系并将它们捆绑在一起 .
您可以在使用Webpack的完全相同的任务上使用Browserify . - 但Webpack更紧凑 .
请注意,Webpack2中的ES6 module loader features正在使用System.import,而不是单个浏览器本身支持的 .
你可以forget Gulp,Grunt,Brokoli,Brunch和Bower . 直接使用npm命令行脚本,你可以在这里为Gulp消除这些额外的包:
在为项目创建配置文件时,您可以使用Gulp和Grunt配置文件生成器 . 这样您就不需要安装Yeoman或类似工具 .
你可以在npmcompare找到一些技术比较
Comparing browserify vs. grunt vs. gulp vs. webpack
正如您所看到的,webpack得到了很好的维护,平均每4天推出一个新版本 . 但Gulp似乎拥有最大的社区(在Github上有超过20K的明星)Grunt似乎有点被忽视(与其他人相比)
因此,如果需要选择一个而不是另一个,我会选择Gulp
纱线是最近的包装经理,可能值得一提 . 所以,那里:https://yarnpkg.com/
Afaik,它可以获取npm和bower依赖关系,并具有其他赞赏的功能 .
Webpack
是一个捆绑包 . 与Browserfy
类似,它在代码库中查找模块请求(require
或import
)并以递归方式解析它们 . 更重要的是,您可以配置Webpack
来解决不仅类似JavaScript的模块,而且解决CSS,图像,HTML等问题 . 特别让我对Webpack
感到兴奋的是,你可以在同一个应用程序中结合编译和动态加载的模块 . 因此,可以获得真正的性能提升,特别是在HTTP / 1.x上 . 怎么样正是你这么做我在这里用例子描述http://dsheiko.com/weblog/state-of-javascript-modules-2017/作为捆绑器的替代品,人们可以想到Rollup.js
(https://rollupjs.org/),它在编译期间优化代码,但剥离所有找到的未使用的块 .对于
AMD
,而不是RequireJS
,可以使用原生ES2016 module system
,但加载System.js
(https://github.com/systemjs/systemjs)此外,我想指出
npm
经常被用作自动化工具,如grunt
或gulp
. 看看https://docs.npmjs.com/misc/scripts . 我个人现在使用npm脚本只避免使用其他自动化工具,尽管在过去我非常喜欢grunt
. 使用其他工具,您必须依赖无数的软件包插件,这些插件通常写得不好而且没有被主动维护 .npm
知道它的包,因此您可以通过以下名称调用任何本地安装的包:实际上,如果软件包支持CLI,您通常不需要任何插件 .
OK, 他们都有一些相似之处,他们以不同和相似的方式为你做同样的事情,我将它们划分为 3 main groups ,如下所示:
1) Module bundlers
webpack和browserify作为流行的,像任务运行器一样工作但具有更大的灵活性,因为它会将所有内容捆绑在一起作为您的设置,因此您可以将结果指向bundle.js,例如在包含CSS和Javascript的单个文件中,更多细节,请看下面的详细信息:
webpack
更多here
browserify
更多here
2) Task runners
gulp和grunt是任务运行者,基本上是他们所做的,创建任务并随时运行它们,例如你安装一个插件来缩小你的CSS,然后每次运行它来进行缩小,更多关于每个的详细信息:
gulp
更多here
grunt
更多here
3) Package managers
软件包管理器,他们所做的是管理你的应用程序所需的插件,并使用package.json通过github等为你安装,非常方便更新你的模块,安装它们并共享你的应用程序,更多详细信息:
npm
更多here
bower
更多here和最新的软件包管理器不应该错过,它在实际工作环境中比较年轻和快速,而我之前大多使用的是npm,为了重新安装模块,它会对node_modules文件夹进行双重检查以检查模块是否存在,似乎安装模块花费的时间更少:
yarn
更多here
Webpack和Browserify
Webpack和Browserify完成相同的工作,这是 processing your code to be used in a target environment (主要是浏览器,但你可以针对其他环境,如Node) . 此类处理的结果是一个或多个 bundles - 适合目标环境的汇编脚本 .
例如,让's say you wrote an ES6 code divided into modules and want be able to run it in browser. If those modules are Node modules, browser won't了解它们,因为它们仅存在于Node环境中 . ES6模块也获得了't work in older browsers like IE11. Moreover you might have used experimental language features (ES next proposals) that browsers don' t实现,所以运行这样的脚本只会抛出错误 . 像Webpack和Browserify这样的工具通过 translating such code to a form browser is able to execute 来解决这些问题 . 最重要的是,它们可以对这些捆绑包应用各种各样的优化 .
但是,Webpack和Browserify在许多方面有所不同,默认情况下Webpack提供了许多工具(例如代码拆分),而Browserify只能在下载插件后才能执行此操作,但是 using both leads to very similar results . 归结为个人偏好(Webpack更具时尚性) . 顺便说一句,Webpack不是一个任务运行器,它只是文件的处理器(它通过所谓的加载器和插件处理它们),它可以由任务运行器运行(以及其他方式) .
Webpack Dev Server
Webpack Dev Server为Browsersync提供了类似的解决方案 - 一个开发服务器,您可以在其中快速部署应用程序,并立即验证开发进度,开发服务器会自动刷新代码更改浏览器,甚至将更改后的代码传播到浏览器无需重新加载所谓的热模块更换 .
任务运行器与NPM脚本
我一直在使用Gulp的简洁和简单的任务写作,但后来发现我根本不需要Gulp和Grunt . 我所需要的一切都可以使用NPM脚本通过其API运行第三方工具 . Choosing between Gulp, Grunt or NPM scripts depends on taste and experience of your team.
虽然Gulp或Grunt中的任务很容易阅读,即使对于不太熟悉JS的人来说,它也是另一种需要和学习的工具,我个人更喜欢缩小我的依赖关系并使事情变得简单 . 另一方面,使用NPM脚本和运行第三方工具(例如,节点脚本配置和运行rimraf用于清洁目的)的(可运行的JS)脚本的组合替换这些任务可能更具挑战性 . 但在大多数情况下, those three are equal in terms of results.
例子
至于这些例子,我建议你看一下这个React starter project,它向你展示了NPM和JS脚本的完美结合,涵盖了整个构建和部署过程 . 您可以在根文件夹的package.json中的名为
scripts
的属性中找到这些NPM脚本 . 你会遇到像babel-node tools/run start
这样的命令 . Babel-node是一个CLI工具(不适合 生产环境 使用),它首先编译ES6文件tools/run
(位于tools的run.js文件) - 基本上是一个运行器实用程序 . 这个运行器将一个函数作为参数并执行它,在这种情况下是start
- 另一个实用程序(start.js)负责捆绑源文件(客户端和服务器)并启动应用程序和开发服务器(开发服务器将是可能是Webpack Dev Server或Browsersync) .更确切地说,start.js创建客户端和服务器端捆绑包,启动快速服务器并在成功启动后进入Browser-sync,在编写本文时看起来像这样(请参阅react starter project获取最新代码) .
重要的部分是
proxy.target
,它们设置了他们想要代理的服务器地址,可能是http://localhost:3000,而浏览器同步启动服务器监听http://localhost:3001,生成的资产通过自动更改检测和热模块替换来提供 . 正如您所看到的,还有另一个配置属性files
具有单独的文件或模式浏览器同步监视更改并重新加载浏览器(如果有的话),但正如评论所说,Webpack负责用HMR自己观看js源,所以他们在那里合作 .现在我没有任何这样的Grunt或Gulp配置的等效示例,但是Gulp(和Grunt有些相似)你会在gulpfile.js中编写单独的任务
你在哪里做的几乎与使用入门套件完全相同,这次是使用任务运行器,它为你解决了一些问题,但在学习使用过程中提出了自己的问题和一些困难,正如我所说,你拥有的依赖性越多,就越容易出错 . 这就是我想摆脱这些工具的原因 .
Update October 2018
如果您仍然不确定前端开发,可以在这里快速查看一个优秀的资源 .
https://github.com/kamranahmedse/developer-roadmap
Update June 2018
如果你从一开始就不去那里学习现代JavaScript很难 . 如果您是新来者,请记得查看这篇优秀的文章,以便更好地了解 .
https://medium.com/the-node-js-collection/modern-javascript-explained-for-dinosaurs-f695e9747b70
Update July 2017
最近,我从Grab团队找到了一份关于如何在2017年进行前端开发的非常全面的指南 . 您可以查看如下 .
https://github.com/grab/front-end-guide
我一直在寻找这个,因为那里有很多工具,每个工具都有不同的方面让我们受益 . 社区分为
Browserify, Webpack, jspm, Grunt and Gulp
等工具 . 你可能也听说过Yeoman or Slush
. 这不是一个真正的问题,对于每个试图理解明确前进道路的人来说,这只会令人困惑 .无论如何,我想贡献一些东西 .
1. Package Manager
软件包管理器简化了安装和更新项目依赖项,这些库是如下的库:
jQuery, Bootstrap
等 - 您网站上使用的所有内容,不是由您编写的 .浏览所有图书馆网站,下载和解压缩档案,将文件复制到项目中 - 所有这些都被终端中的一些命令所取代 .
NPM代表:
Node JS package manager
帮助您管理软件所依赖的所有库 . 您可以在名为package.json
的文件中定义您的需求并在命令行中运行npm install
然后BANG,您的软件包已下载并可以使用 . 可以用于front-end and back-end
库 .Bower:对于前端包管理,概念与NPM相同 . 所有库都存储在名为
bower.json
的文件中,然后在命令行中运行bower install
.NPM
Bower
Yarn:最近
JavaScript
published的新包管理器Facebook
与NPM
相比具有更多优势 . 使用Yarn,您仍然可以使用NPM和Bower注册表来获取包 . 如果您之前安装了一个软件包,yarn
会创建一个便于offline package installs
的缓存副本 .jspm:是
SystemJS
通用模块加载器的包管理器,构建于动态ES6
模块加载器之上 . 它不是一个全新的包管理器,它有自己的一套规则,而是在现有的包源之上工作 . 开箱即用,它适用于GitHub
和npm
. 由于大多数基于Bower
的软件包都基于GitHub
,我们也可以使用jspm
安装这些软件包 . 它有一个注册表,列出了大多数常用的前端软件包,以便于安装 .2. Module Loader/Bundling
任何规模的大多数项目都将在许多文件之间分配代码 . 您可以只使用单独的
<script>
标记包含每个文件,但是,<script>
Build 新的http连接,对于小文件 - 这是模块化的目标 - 设置连接的时间可能比传输数据要长得多 . 在下载脚本时,页面上不能更改任何内容 .例如
例如
计算机可以做得更好,这就是为什么你应该使用工具自动将所有内容捆绑到一个文件中 .
Then we heard about RequireJS, Browserify, Webpack and SystemJS
JavaScript
文件和模块加载器 . 它针对浏览器内使用进行了优化,但可以在其他JavaScript环境中使用,例如Node
.例如: myModule.js
在
main.js
中,我们可以导入myModule.js
作为依赖项并使用它 .然后在我们的
HTML
中,我们可以参考RequireJS
.CommonJS
格式化的模块 . 所以,Browserify
不是模块加载器的模块加载器:Browserify
完全是一个构建时工具,产生一组代码,然后可以在客户端加载 .从安装了node&npm的构建计算机开始,然后获取包:
以
CommonJS
格式编写模块当快乐时,发出捆绑命令:
Browserify以递归方式查找入口点的所有依赖项,并将它们组合到一个文件中:
JavaScript
,图像,CSS等)捆绑到一个文件中 . 它还使您能够通过不同类型的加载器处理文件 . 您可以使用CommonJS
或AMD
模块语法编写JavaScript
. 它以一种从根本上更加整合和自以为是的方式攻击构建问题 . 在Browserify
中,您使用Gulp/Grunt
以及一长串转换和插件来完成工作 .Webpack
提供足够的电源,你通常根本不需要Grunt
或Gulp
.基本用法非常简单 . 像Browserify一样安装Webpack:
并将命令传递给入口点和输出文件:
CommonJS, UMD, AMD, ES6
) . 它 Build 在ES6
模块加载器polyfill之上,并且足够智能以检测正在使用的格式并适当地处理它 .SystemJS
也可以使用插件转换ES6代码(使用Babel
或Traceur
)或其他语言,如TypeScript
和CoffeeScript
.$('body') . append(“我导入了jQuery!”);
然后在导入模块之前在System.config()中配置这些内容 . 通常在运行jspm init时,会出现一个名为config.js的文件 . 要使这些脚本运行,我们需要在HTML页面上加载system.js和config.js . 之后,我们将使用SystemJS模块加载器加载display.js文件 . index.html <script src =“jspm_packages / system.js”> </ script>
<script src =“config.js”> </ script> <SCRIPT> System.import( “脚本/ display.js”); </ SCRIPT> 注意:当Angular 2应用它时,你也可以使用npm和Webpack . 由于jspm是为了与SystemJS集成而开发的,它可以在现有的npm源之上运行,因此您的答案取决于您 . ---- **3. Task runner** 任务运行器和构建工具主要是命令行工具 . 为什么我们需要使用它们:一句话: **automation** . 执行重复性任务(例如 **minification, compilation, unit testing, linting** )时,您需要做的工作就越少,这些任务以前需要花费很多时间才能完成命令行甚至手动操作 . - [Grunt](http://gruntjs.com/):您可以为开发环境创建自动化,以预处理代码或使用配置文件创建构建脚本,并且处理复杂任务似乎非常困难 . 在过去几年流行 . `Grunt` 中的每个任务都是一组不同的插件配置,它们只能以严格独立的顺序方式一个接一个地执行 . ```java grunt.initConfig({ clean: { src: ['build/app.js', 'build/vendor.js'] }, copy: { files: [{ src: 'build/app.js', dest: 'build/dist/app.js' }] } concat: { 'build/app.js': ['build/vendors.js', 'build/app.js'] } // ... other task configurations ... }); grunt.registerTask('build', ['clean', 'bower', 'browserify', 'concat', 'copy']); ``` - [Gulp](http://gulpjs.com/):自动化就像 `Grunt` 但是不是配置,你可以用流来编写 `JavaScript` ,就像节点应用程序一样 . 喜欢这些天 . 这是一个 `Gulp` 样本任务声明 . ```java //import the necessary gulp plugins var gulp = require('gulp'); var sass = require('gulp-sass'); var minifyCss = require('gulp-minify-css'); var rename = require('gulp-rename'); //declare the task gulp.task('sass', function(done) { gulp.src('./scss/ionic.app.scss') .pipe(sass()) .pipe(gulp.dest('./www/css/')) .pipe(minifyCss({ keepSpecialComments: 0 })) .pipe(rename({ extname: '.min.css' })) .pipe(gulp.dest('./www/css/')) .on('end', done); }); ``` >查看更多:https://medium.com/@preslavrachev/gulp-vs-grunt-why-one-why-the-other-f5d3b398edc4#.fte0nahri ---- **4. Scaffolding tools** - `Slush and Yeoman` :您可以使用它们创建启动项目 . 例如,您计划使用HTML和SCSS构建原型,然后手动创建一些文件夹,如scss,css,img,fonts . 您只需安装 `yeoman` 并运行一个简单的脚本即可 . 那么一切都在这里给你 . 查找更多[here](http://yeoman.io/) . ```java npm install -g yo npm install --global generator-h5bp yo h5bp ``` >查看更多:https://www.quora.com/What-are-the-differences-between-NPM-Bower-Grunt-Gulp-Webpack-Browserify-Slush-Yeoman-and-Express ---- 我的回答与问题的内容并不完全匹配,但当我在谷歌上搜索这些知识时,我总是在顶部看到这个问题,所以我决定总结一下 . 希望你们发现它有用 .