buildnpmgulpgulp-watchgulp-less

gulp-less doesn't make CSS files anymore


I'm using gulp for generating CSS from LESS. It has worked perfectly, but now the script seems to ignore the LESS files.

Here is my gulpfile.js (it is definitely correct, since I have not change it in the last time):

// Include Gulp plugins
var gulp = require('gulp'),
    less = require('gulp-less'),
    watch = require('gulp-watch'),
    prefix = require('gulp-autoprefixer'),
    plumber = require('gulp-plumber'),
    filter = require('gulp-filter'),
    rename = require('gulp-rename'),
    path = require('path')
;
// Compile LESS to CSS
gulp.task('build-less', function() {
    const fileFilter = filter(['*', '!mixins.less', '!variables.less']);
    gulp.src('./public/less/*.less') // path to less file
        .pipe(fileFilter)
        .pipe(plumber())
        .pipe(less())
        .pipe(gulp.dest('./public/css/')) // path to css directory
    ;
});
// Get vendors' code
gulp.task('build-vendors', function() {
    gulp.src(['./public/components/bootstrap/less/theme.less', './public/components/bootstrap/less/bootstrap.less']) // path to less file
        .pipe(plumber())
        .pipe(less())
        .pipe(rename(function (path) {
            //rename all files except 'bootstrap.css'
            if (path.basename + path.extname !== 'bootstrap.css') {
                path.basename = 'bootstrap-' + path.basename;
            }
        }))
        .pipe(gulp.dest('./public/css')) // path to css directory
    ;
});
// Run the build process
gulp.task('run', ['build-less', 'build-vendors']);
// Watch all LESS files, then run build-less
gulp.task('watch', function() {
    gulp.watch('public/less/*.less', ['run'])
});
// Default will run the 'entry' task
gulp.task('default', ['watch', 'run']);

And here is the call and the output:

$ gulp
[11:21:03] Using gulpfile /var/www/path/to/project/gulpfile.js
[11:21:03] Starting 'watch'...
[11:21:03] Finished 'watch' after 21 ms
[11:21:03] Starting 'build-less'...
[11:21:03] Finished 'build-less' after 13 ms
[11:21:03] Starting 'build-vendors'...
[11:21:03] Finished 'build-vendors' after 4.65 ms
[11:21:03] Starting 'run'...
[11:21:03] Finished 'run' after 5.37 μs
[11:21:03] Starting 'default'...
[11:21:03] Finished 'default' after 6.05 μs

The whatch also works correctly -- when I edit my LESS files I get an output like this:

[11:22:22] Starting 'build-less'...
[11:22:22] Finished 'build-less' after 1.96 ms
[11:22:22] Starting 'build-vendors'...
[11:22:22] Finished 'build-vendors' after 1.78 ms
[11:22:22] Starting 'run'...
[11:22:22] Finished 'run' after 5.08 μs

I also tried to run the build-less directly:

$ gulp build-less
[11:24:06] Using gulpfile /var/www/path/to/project/gulpfile.js
[11:24:06] Starting 'build-less'...
[11:24:06] Finished 'build-less' after 13 ms

No errors, but also no changes at the CSS files.

What might go wrong here and how to fix it?


Solution

  • gulp-filter uses multimatch to match file paths against globbing patterns. The documentation for multimatch has this to say about *:

    * matches any number of characters, but not /

    Since you're trying to match files with paths like public/less/foo.less (which contain a /) using a single asterisk * doesn't work. You have to use two asterisks **:

    gulp.task('build-less', function() {
      const fileFilter = filter(['**/*', '!**/mixins.less', '!**/variables.less']);
      gulp.src('./public/less/*.less') // path to less file
        .pipe(fileFilter)
        .pipe(plumber())
        .pipe(less())
        .pipe(gulp.dest('./public/css/')); // path to css directory
    });