Search code examples
javascriptlessgruntjsglob

grunt replace all less files into css files


I use grunt to convert all my less files into css files,using this:

less: {
  development: {
    files: {
      "css/*.css": "less/*.less"
    }
  }
}

This worked on version 0.3.0, but now that I have upgraded to v0.4.0 it doesn't work anymore.

The following code (not using * in the destination) works on both versions, so the problem is with the star on the destination file.

less: {
  development: {
    files: {
      "css/test.css": "less/*.less"
    }
  }
}

Any idea ?


Solution

  • This isn't a bug. Grunt no longer supports globbing in dest using that configuration. However, you can use the "files array" format, like this:

    files: [
      {
        expand: true,
        cwd: 'src',
        src: ['*.less'],
        dest: 'assets/css/',
        ext: '.css'
      }
    ]
    

    Also, if you use a library like Bootstrap and you want to build each LESS file (component) into a separate, individual CSS file, it's not very easy to accomplish "out of the box". The reason is that each LESS file would need to have its own @import statements for variables.less and mixins.less (and a couple of others like forms.less and navbar.less, since they are referenced in other files).

    To make this really easy, try the Grunt plugin, assemble-less (disclaimer: I'm one of the maintainers of the project, and I'm also on the core team for less.js). assemble-less is a fork of grunt-contrib-less by Tyler Kellen, but it adds some experimental features that will accomplish what you need (if you want stability, please stick with grunt-contrib-less). For example:

    // Project configuration.
    grunt.initConfig({
    
      less: {
        // Compile all targeted LESS files individually
        components: {
          options: {
            imports: {
              // Use the new "reference" directive, e.g.
              // @import (reference) "variables.less";
              reference: [
                "bootstrap/mixins.less", 
                "bootstrap/variables.less" 
              ]
            }
          },
          files: [
            {
              expand: true,
              cwd: 'bootstrap/less',
              // Compile each LESS component excluding "bootstrap.less", 
              // "mixins.less" and "variables.less" 
              src: ['*.less', '!{boot,var,mix}*.less'],
              dest: 'assets/css/',
              ext: '.css'
            }
          ]
        }
      }
      ...
    }
    

    The imports feature essentially prepends the specified @import statements onto the source files. The reference option allows you to "reference" other less files while only outputting styles that are specifically referenced via mixins or :extend. You might need to reference a few more files than shown here, since Bootstrap cross-references styles from other components, like forms.less, buttons.less, etc. (See the Gruntfile in assemble-less for examples.)

    So after running the assemble-less task with the configuration in the example above, the assets/css folder would have:

    • alerts.css
    • badges.css
    • breadcrumbs.css
    • button-groups.css
    • buttons.css
    • carousel.css
    • close.css
    • code.css
    • component-animations.css
    • dropdowns.css
    • forms.css
    • glyphicons.css
    • grid.css
    • input-groups.css
    • jumbotron.css
    • labels.css
    • list-group.css
    • media.css
    • modals.css
    • navbar.css
    • navs.css
    • normalize.css
    • pager.css
    • pagination.css
    • panels.css
    • popovers.css
    • print.css
    • progress-bars.css
    • responsive-utilities.css
    • scaffolding.css
    • tables.css
    • theme.css
    • thumbnails.css
    • tooltip.css
    • type.css
    • utilities.css
    • wells.css

    There are other features that should help you with this, but the imports feature is super powerful since it allows you to add directives directly to the Gruntfile.