如果你經(jīng)常參與web社區(qū),那么你應(yīng)該聽(tīng)說(shuō)過(guò)Browserify和Webpack工具。如果不使用它們,你將面臨手動(dòng)的在HTML輸入很多<script>
標(biāo)簽,并且需要將JS代碼放到合適的地方。
并且,我們還不能直接在瀏覽器使用ES6,在將代碼提供給用戶之前,我們需要用Babel將它們轉(zhuǎn)換為ES5代碼。
我們將使用Gulp和Browserify而不用Webpack。我并不認(rèn)為它們兩個(gè)誰(shuí)優(yōu)誰(shuí)劣,但我想說(shuō)Gulp+Browserify比等價(jià)的Webpack文件要直觀多了,我還沒(méi)有在任何React boilerplate項(xiàng)目中看到一個(gè)易于理解的webpack.config.js文件。
創(chuàng)建文件gulpfile.js并粘貼下面的代碼:
var gulp = require('gulp');
var gutil = require('gulp-util');
var gulpif = require('gulp-if');
var streamify = require('gulp-streamify');
var autoprefixer = require('gulp-autoprefixer');
var cssmin = require('gulp-cssmin');
var less = require('gulp-less');
var concat = require('gulp-concat');
var plumber = require('gulp-plumber');
var source = require('vinyl-source-stream');
var babelify = require('babelify');
var browserify = require('browserify');
var watchify = require('watchify');
var uglify = require('gulp-uglify');
var production = process.env.NODE_ENV === 'production';
var dependencies = [
'alt',
'react',
'react-router',
'underscore'
];
/*
|--------------------------------------------------------------------------
| Combine all JS libraries into a single file for fewer HTTP requests.
|--------------------------------------------------------------------------
*/
gulp.task('vendor', function() {
return gulp.src([
'bower_components/jquery/dist/jquery.js',
'bower_components/bootstrap/dist/js/bootstrap.js',
'bower_components/magnific-popup/dist/jquery.magnific-popup.js',
'bower_components/toastr/toastr.js'
]).pipe(concat('vendor.js'))
.pipe(gulpif(production, uglify({ mangle: false })))
.pipe(gulp.dest('public/js'));
});
/*
|--------------------------------------------------------------------------
| Compile third-party dependencies separately for faster performance.
|--------------------------------------------------------------------------
*/
gulp.task('browserify-vendor', function() {
return browserify()
.require(dependencies)
.bundle()
.pipe(source('vendor.bundle.js'))
.pipe(gulpif(production, streamify(uglify({ mangle: false }))))
.pipe(gulp.dest('public/js'));
});
/*
|--------------------------------------------------------------------------
| Compile only project files, excluding all third-party dependencies.
|--------------------------------------------------------------------------
*/
gulp.task('browserify', ['browserify-vendor'], function() {
return browserify('app/main.js')
.external(dependencies)
.transform(babelify)
.bundle()
.pipe(source('bundle.js'))
.pipe(gulpif(production, streamify(uglify({ mangle: false }))))
.pipe(gulp.dest('public/js'));
});
/*
|--------------------------------------------------------------------------
| Same as browserify task, but will also watch for changes and re-compile.
|--------------------------------------------------------------------------
*/
gulp.task('browserify-watch', ['browserify-vendor'], function() {
var bundler = watchify(browserify('app/main.js', watchify.args));
bundler.external(dependencies);
bundler.transform(babelify);
bundler.on('update', rebundle);
return rebundle();
function rebundle() {
var start = Date.now();
return bundler.bundle()
.on('error', function(err) {
gutil.log(gutil.colors.red(err.toString()));
})
.on('end', function() {
gutil.log(gutil.colors.green('Finished rebundling in', (Date.now() - start) + 'ms.'));
})
.pipe(source('bundle.js'))
.pipe(gulp.dest('public/js/'));
}
});
/*
|--------------------------------------------------------------------------
| Compile LESS stylesheets.
|--------------------------------------------------------------------------
*/
gulp.task('styles', function() {
return gulp.src('app/stylesheets/main.less')
.pipe(plumber())
.pipe(less())
.pipe(autoprefixer())
.pipe(gulpif(production, cssmin()))
.pipe(gulp.dest('public/css'));
});
gulp.task('watch', function() {
gulp.watch('app/stylesheets/**/*.less', ['styles']);
});
gulp.task('default', ['styles', 'vendor', 'browserify-watch', 'watch']);
gulp.task('build', ['styles', 'vendor', 'browserify']);
如果你從未使用過(guò)Gulp,這里有一個(gè)很棒的教程《An Introduction to Gulp.js》
下面簡(jiǎn)單介紹一下每個(gè)Gulp任務(wù)是干嘛的。
Gulp Task | Description |
---|---|
vendor |
將所有第三方JS文件合并到一個(gè)文件 |
browserify-vendor |
因?yàn)樾阅茉?,我們將NPM模塊和前端模塊分開(kāi)編譯和打包,因此每次重新編譯將會(huì)快個(gè)幾百毫秒 |
browserify |
僅將app文件編譯并打包,不包括其它模塊和庫(kù) |
browserify-watch |
包括上面的功能,并且監(jiān)聽(tīng)文件改變,然后重新編譯打包app文件 |
watch |
當(dāng)文件改變時(shí)重新編譯LESS文件 |
default |
運(yùn)行上面所有任務(wù)并開(kāi)始監(jiān)聽(tīng)文件改變 |
build |
運(yùn)行上面所有任務(wù)然后退出 |
下面,我們將注意力轉(zhuǎn)移到項(xiàng)目結(jié)構(gòu)上,我們將創(chuàng)建gulpfile.js需要的文件和文件夾。
更多建議: