Skip to content

Instantly share code, notes, and snippets.

@alexcarpenter
Created February 11, 2018 15:42
Show Gist options
  • Save alexcarpenter/3b8d9337404b7001a56700127150a86d to your computer and use it in GitHub Desktop.
Save alexcarpenter/3b8d9337404b7001a56700127150a86d to your computer and use it in GitHub Desktop.
gulpfile.js
const gulp = require('gulp');
const sourcemaps = require('gulp-sourcemaps');
const sass = require('gulp-sass');
const autoprefixer = require('gulp-autoprefixer');
const cssnano = require('gulp-cssnano');
const critical = require('critical');
const imagemin = require('gulp-imagemin');
const uglify = require('gulp-uglify');
const changed = require('gulp-changed');
const plumber = require('gulp-plumber');
const sequence = require('run-sequence');
const gutil = require('gulp-util');
const fancyLog = require('fancy-log');
const chalk = require('chalk');
const del = require('del');
const browserSync = require('browser-sync').create();
const reload = browserSync.reload;
const config = require('./project.config');
const onError = err => {
console.log(err);
};
gulp.task('clean', () => {
return del(config.paths.clean);
});
gulp.task('styles', () => {
return gulp
.src(config.paths.styles.glob)
.pipe(
process.env.NODE_ENV !== 'production' ? sourcemaps.init() : gutil.noop()
)
.pipe(plumber({ errorHandler: onError }))
.pipe(sass())
.pipe(autoprefixer())
.pipe(
process.env.NODE_ENV !== 'production'
? sourcemaps.write('maps')
: gutil.noop()
)
.pipe(process.env.NODE_ENV === 'production' ? cssnano() : gutil.noop())
.pipe(gulp.dest(config.paths.styles.dest))
.pipe(browserSync.stream({ match: '**/*.css' }));
});
gulp.task('criticalCss', ['styles'], callback => {
doSynchronousLoop(config.critical.pages, processCriticalCSS, () => {
callback();
});
});
gulp.task('scripts', () => {
return gulp
.src(config.paths.scripts.glob)
.pipe(changed(config.paths.scripts.dest))
.pipe(uglify())
.pipe(gulp.dest(config.paths.scripts.dest));
});
gulp.task('vendorJs', () => {
return gulp
.src(config.paths.scripts.vendorJs)
.pipe(uglify())
.pipe(gulp.dest(config.paths.scripts.dest));
});
gulp.task('inlineJs', () => {
return gulp
.src(config.paths.scripts.inlineJs)
.pipe(gulp.dest('./templates/_assets/js'));
});
gulp.task('images', () => {
return gulp
.src(config.paths.images.glob)
.pipe(changed(config.paths.images.dest))
.pipe(
imagemin({
progressive: true,
interlaced: true,
multipass: true,
svgoPlugins: [
{ removeTitle: false },
{ cleanupListOfValues: { floatPrecision: 2 } },
{ cleanupNumericValues: { floatPrecision: 2 } },
{ convertPathData: { floatPrecision: 2 } }
]
})
)
.pipe(gulp.dest(config.paths.images.dest));
});
gulp.task(
'watch',
['styles', 'scripts', 'vendorJs', 'inlineJs', 'images'],
() => {
browserSync.init({
notify: false,
proxy: config.urls.local
});
gulp.watch(config.paths.styles.glob, ['styles']);
gulp.watch(config.paths.scripts.glob, ['scripts']);
gulp.watch(config.paths.templates.glob).on('change', reload);
}
);
gulp.task('build', () => {
sequence('clean', [
config.critical.init ? 'criticalCss' : 'styles',
'scripts',
'vendorJs',
'inlineJs',
'images'
]);
});
function doSynchronousLoop(data, processData, done) {
if (data.length > 0) {
const loop = (data, i, processData, done) => {
processData(data[i], i, () => {
if (++i < data.length) {
loop(data, i, processData, done);
} else {
done();
}
});
};
loop(data, 0, processData, done);
} else {
done();
}
}
function processCriticalCSS(element, i, callback) {
const criticalSrc = config.urls.local + element.url;
const criticalDest =
config.critical.dest + element.template + '_critical.min.css';
fancyLog(
'-> Generating critical CSS: ' +
chalk.cyan(criticalSrc) +
' -> ' +
chalk.magenta(criticalDest)
);
critical.generate(
{
src: criticalSrc,
dest: criticalDest,
inline: false,
ignore: [],
base: config.critical.base,
css: ['./web/assets/css/main.css'],
minify: true,
width: 1200,
height: 1200
},
(err, output) => {
callback();
}
);
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment