factory

Quick and easy template scaffolding for Node

Factory

Quick and easy template scaffolding for Node

npm install factory
var factory = require('factory');
 
var widgetFactory = factory({
    template: 'templates/widget',
    placeholders: [
        {
            name: 'foo',
            type: 'input',
            message: 'Enter a value for foo'
        },
        {
            name: 'bar',
            type: 'input',
            message: 'Enter a value for bar'
        }
    ]
});
 
var options = {
    destination: 'app/widgets',
    overwrite: true,
};
var context = {
    foo: 'baz'
};
 
// Node-style callback interface 
widgetFactory(options, context, function(errorresults) {
    if (error) {
        console.error('Widget creation failed: ' + error);
    } else {
        console.info('Widget created successfully');
    }
});
 
// Promise interface 
widgetFactory(options, context)
    .then(function(results) {
        console.info('Widget created successfully');
    }).catch(function(error) {
        console.error('Widget creation failed: ' + error);
    });

Contents of templates/widget/<%= foo %>.js:

module.exports = function <%= foo %>() {
    console.log('<%= bar %>');
};

Output at app/widgets/baz.js:

module.exports = function baz() {
    console.log('[user-prompted value]');
};
  • The factory() function takes two arguments:
    • template: path to the template folder
    • placeholders: array of inquirer prompts used to gather data for injecting into templates
  • You can then call the function that is returned, specifying a destination path and any copy options, and optionally passing in a key/value object containing template placeholder values
  • The user is prompted for the value of any placeholders which were not provided in the placeholder values object
  • The files are copied from the template folder to the destination folder, replacing any placeholders in filenames and file content with the supplied values (using lodash template syntax)

Create a factory from an existing template

Template filenames/contents can use lodash template syntax to specify placeholder values. These are injected into the template when the factory function is invoked.

Options:

NameTypeRequiredDefaultDescription
templatestringYesN/APath to the template folder
placeholdersArrayNo[]Array of inquirer prompts used to gather data for injecting into templates

Returns:

  • function(options, [context], [callback])

    Factory function used to create instances of the template

    The user will be prompted for the value of any placeholders which are not specified in the context object.

    Options:

    NameTypeRequiredDefaultDescription
    options.destinationstringYesN/ADestination directory for output files
    options.overwritebooleanNofalseWhether to overwrite existing files
    contextobjectNo{}Preset template placeholder values
    callbackfunctionNonullNode-style callback that is invoked when the operation completes/fails

    Returns:

    • Promise<Array> Promise, fulfilled with array of copy results:

      [
          {
              "src": "/path/to/src",
              "dest": "/path/to/dest",
              "stats": <Stats>
          },
          {
              "src": "/path/to/src/file.txt",
              "dest": "/path/to/dest/file.txt",
              "stats": <Stats>
          },
          {
              "src": "/path/to/src/subfolder",
              "dest": "/path/to/dest/subfolder",
              "stats": <Stats>
          },
          {
              "src": "/path/to/src/subfolder/nested.txt",
              "dest": "/path/to/dest/subfolder/nested.txt",
              "stats": <Stats>
          }
      ]

The value returned by the generated factory function implements the EventEmitter interface, and emits the following events:

EventHandler signature
factory.events.ERRORfunction(error, ErrorInfo)
factory.events.COMPLETEfunction(Array<CopyOperation>)
factory.events.CREATE_DIRECTORY_STARTfunction(CopyOperation)
factory.events.CREATE_DIRECTORY_ERRORfunction(error, CopyOperation)
factory.events.CREATE_DIRECTORY_COMPLETEfunction(CopyOperation)
factory.events.CREATE_SYMLINK_STARTfunction(CopyOperation)
factory.events.CREATE_SYMLINK_ERRORfunction(error, CopyOperation)
factory.events.CREATE_SYMLINK_COMPLETEfunction(CopyOperation)
factory.events.COPY_FILE_STARTfunction(CopyOperation)
factory.events.COPY_FILE_ERRORfunction(error, CopyOperation)
factory.events.COPY_FILE_COMPLETEfunction(CopyOperation)

...where the types referred to in the handler signature are as follows:

PropertyTypeDescription
srcstringSource path of the file/folder/symlink that failed to copy
deststringDestination path of the file/folder/symlink that failed to copy
PropertyTypeDescription
srcstringSource path of the relevant file/folder/symlink
deststringDestination path of the relevant file/folder/symlink
statsfs.StatsStats for the relevant file/folder/symlink
var factory = require('factory');
 
var widgetFactory = factory({
    template: 'templates/widget'
});
 
var options = {
    destination: 'app/widgets'
};
var context = {};
widgetFactory(options, context)
    .on(factory.events.COPY_FILE_START, function(copyOperation) {
        console.info('Copying file ' + copyOperation.src + '...');
    })
    .on(factory.events.COPY_FILE_COMPLETE, function(copyOperation) {
        console.info('Copied to ' + copyOperation.dest);
    })
    .on(factory.events.ERROR, function(errorcopyOperation) {
        console.error('Unable to copy ' + copyOperation.dest);
    })
    .then(function(results) {
        console.info('Widget created successfully');
    }).catch(function(error) {
        console.error('Widget creation failed: ' + error);
    });