npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2024 – Pkg Stats / Ryan Hefner

grunt-modules

v0.1.0

Published

Utility to modularize grunt files

Downloads

5

Readme

Grunt Modules

Grunt Modules allows you to split up your grunt file into modular pieces. It's very useful for managing large codebases. We use it to manage the build system for a 400+ file application at Turn and it works like a charm.

In Grunt you define pieces of your modules within each multitask. Grunt Modules inverts the configuration so that you can have your module define it's tasks instead, allowing you to put entire cross-sections of your configuration in their own files.

Use

  1. npm install grunt-modules
  2. Add var gruntModules = require('grunt-modules'); to the top of your Gruntfile.js
  3. Configure non-modular tasks in grunt.initConfig({/* config */}) as usual
  4. Include your modules via the gruntModules(grunt, modules) function.
var gruntModules = require('grunt-modules');
module.exports = function(grunt){
  grunt.initConfig({
    /* non-modular tasks */
  });

  gruntModules(grunt, {
    moduleName: require('./path/to/module.js'),
    anotherModuleName: require('./path/to/another/module.js')
    /* so on... */
  });
}

For Example...

// Gruntfile.js
var gruntModules = require('grunt-modules');
module.exports = function(grunt) {
  // A sample multitask which just echoes whatever 
	// configuration object is given to it
	grunt.registerMultiTask('echo', 'Echo back input', function(){
		grunt.log.writeln(this.data);
	});

	// Initialize the core config the standard way
	grunt.initConfig({
		echo: {
			inInitConfig: "I'm in init config!"
		}
	});

	// Extend the core config with a grunt module
	gruntModules(grunt, {
		aModule: require('./aModuleFile.js')
	});
};
// aModuleFile.js
// A module defines a function which takes in the grunt object 
// and module name and returns a configuration object.
module.exports = function(grunt, moduleName){
  return {
    // We can pass the multitask anything that the multitask 
    // would accept for an individual task
    echo: "I'm in aModuleFile!", // will be transformed to echo:aModule
  }
};
// In the command line
$ grunt echo
Running "echo:inInitConfig" (echo) task
I'm in init config!

Running "echo:aModule" (echo) task
I'm in aModuleFile!

Grunt Modules takes the mapping between "aModule" and the function which produces the task map in "aModuleFile.js" and uses it to extend the grunt configuration. The end result is the same as if we had used this file:

// Gruntfile.js
module.exports = function(grunt) {
  grunt.registerMultiTask('echo', 'Echo back input', function(){
    grunt.log.writeln(this.data);
  });

  grunt.initConfig({
    echo: {
      inInitConfig: "I'm in init config!",
      aModule: "I'm in aModuleFile!"
    }
  });

Modules

Modules are functions which take in a grunt object and the module name and return a configuration object. The configuration object should have multitask names as the keys, and a task configuration as the value.

// aModule.js
module.exports = function(grunt, moduleName){
  return {
    multiTaskName: {/*task config*/}
  }
}

Multitasks don't behave as regular tasks in the module file configuration. For example if we had a module named "CaramelPopcorn":

// CaramelPopcorn.js
// ...
  multiTaskName: {
    src: ['popcorn'],
    dest: 'caramel'
  }
// ...

It would have the same effect as if we had:

// Gruntfile.js
// ...
  multiTaskName: {
    CaramelPopcorn: {
      src: ['popcorn'],
      dest: 'caramel'
    }
  }
// ...

If you want to create multiple tasks for a given multitask in a module, you can do so with the $ convention. For exmaple:

// aModule.js
// ...
  multiTaskName: {/*task config*/},
  multiTaskName$another: {/*task config*/}
// ...

Would have the same effect as:

// Gruntfile.js
// ...
  multiTaskName: {
    aModule: {},
    aModule$another: {}
  }
// ...

Nested Modules

A module can nest other modules within itself. This is done by exporting an object instead of a function. When a module nests another module the . notation is used to define them in the Grunt configuration.

// aModule.js
module.exports = {
  nestedModule: require('./path/to/nested/module.js'),
  anotherNestedModule: require('./path/to/another/nested/module.js')
}
// Gruntfile.js
var gruntModules = require('grunt-modules');
module.exports = function(grunt) {
	grunt.registerMultiTask('echo', 'Echo back input', function(){
		grunt.log.writeln(this.data);
	});

	grunt.initConfig({/* core config */});

	// Extend the core config with a grunt module
	gruntModules(grunt, {
		aModule: require('./aModule.js')
	});
};

The core above will produce a grunt configuration that behaves the same as:

// Gruntfile.js
module.exports = function(grunt) {
  grunt.initConfig({
    multiTaskName: {
      "aModule.nestedModule": {/*config*/},
      "aModule.anotherNestedModule": {/*config*/},
    }
  });

	// Extend the core config with a grunt module
	gruntModules(grunt, {
		aModule: require('./aModule.js')
	});
};