You can not select more than 25 topics
			Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
		
		
		
		
		
			
		
			
				
					
					
						
							200 lines
						
					
					
						
							5.0 KiB
						
					
					
				
			
		
		
	
	
							200 lines
						
					
					
						
							5.0 KiB
						
					
					
				'use strict'; | 
						|
 | 
						|
Object.defineProperty(exports, "__esModule", { | 
						|
  value: true | 
						|
}); | 
						|
exports.requirer = requirer; | 
						|
exports.hasAccess = hasAccess; | 
						|
exports.getConfig = getConfig; | 
						|
exports.load = load; | 
						|
exports.describe = describe; | 
						|
exports.call = call; | 
						|
exports.main = main; | 
						|
 | 
						|
var _path = require('path'); | 
						|
 | 
						|
var _path2 = _interopRequireDefault(_path); | 
						|
 | 
						|
var _fs = require('fs'); | 
						|
 | 
						|
var _fs2 = _interopRequireDefault(_fs); | 
						|
 | 
						|
var _chalk = require('chalk'); | 
						|
 | 
						|
var _chalk2 = _interopRequireDefault(_chalk); | 
						|
 | 
						|
var _lodash = require('lodash.padend'); | 
						|
 | 
						|
var _lodash2 = _interopRequireDefault(_lodash); | 
						|
 | 
						|
var _microcli = require('microcli'); | 
						|
 | 
						|
var _microcli2 = _interopRequireDefault(_microcli); | 
						|
 | 
						|
var _omelette = require('omelette'); | 
						|
 | 
						|
var _omelette2 = _interopRequireDefault(_omelette); | 
						|
 | 
						|
var _common = require('./common'); | 
						|
 | 
						|
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; } | 
						|
 | 
						|
const DEFAULT_RUNFILE_PATH = './runfile.js'; | 
						|
function requirer(filePath) { | 
						|
  return require(_path2.default.resolve(filePath)); | 
						|
} | 
						|
 | 
						|
function hasAccess(filePath) { | 
						|
  return _fs2.default.accessSync(_path2.default.resolve(filePath)); | 
						|
} | 
						|
 | 
						|
function getConfig(filePath) { | 
						|
  let config; | 
						|
  try { | 
						|
    config = requirer(filePath).runjs || {}; | 
						|
  } catch (error) { | 
						|
    config = {}; | 
						|
  } | 
						|
  return config; | 
						|
} | 
						|
 | 
						|
function load(config, logger, requirer, access) { | 
						|
  const runfilePath = config['runfile'] || DEFAULT_RUNFILE_PATH; | 
						|
  // Load requires if given in config | 
						|
  if (Array.isArray(config['requires'])) { | 
						|
    config['requires'].forEach(modulePath => { | 
						|
      logger.log(_chalk2.default.gray(`Requiring ${modulePath}...`)); | 
						|
      requirer(modulePath); | 
						|
    }); | 
						|
  } | 
						|
 | 
						|
  // Process runfile | 
						|
  logger.log(_chalk2.default.gray(`Processing ${runfilePath}...`)); | 
						|
 | 
						|
  try { | 
						|
    access(runfilePath); | 
						|
  } catch (error) { | 
						|
    throw new _common.RunJSError(`No ${runfilePath} defined in ${process.cwd()}`); | 
						|
  } | 
						|
 | 
						|
  const runfile = requirer(runfilePath); | 
						|
  if (runfile.default) { | 
						|
    return runfile.default; | 
						|
  } | 
						|
  return runfile; | 
						|
} | 
						|
 | 
						|
function describe(obj, logger, namespace) { | 
						|
  if (!namespace) { | 
						|
    logger.log(_chalk2.default.yellow('Available tasks:')); | 
						|
  } | 
						|
 | 
						|
  Object.keys(obj).forEach(key => { | 
						|
    const value = obj[key]; | 
						|
    const nextNamespace = namespace ? `${namespace}:${key}` : key; | 
						|
    const help = value.help; | 
						|
 | 
						|
    if (typeof value === 'function') { | 
						|
      // Add task name | 
						|
      const funcParams = help && help.params; | 
						|
      let logArgs = [_chalk2.default.bold(nextNamespace)]; | 
						|
 | 
						|
      // Add task params | 
						|
      if (Array.isArray(funcParams) && funcParams.length) { | 
						|
        logArgs[0] += ` [${funcParams.join(' ')}]`; | 
						|
      } | 
						|
 | 
						|
      // Add description | 
						|
      if (help && (help.description || typeof help === 'string')) { | 
						|
        const description = help.description || help; | 
						|
        logArgs[0] = (0, _lodash2.default)(logArgs[0], 40); // format | 
						|
        logArgs.push('-', description.split('\n')[0]); | 
						|
      } | 
						|
 | 
						|
      // Log | 
						|
      logger.log(...logArgs); | 
						|
    } else if (typeof value === 'object') { | 
						|
      describe(value, logger, nextNamespace); | 
						|
    } | 
						|
  }); | 
						|
 | 
						|
  if (!namespace) { | 
						|
    logger.log('\n' + _chalk2.default.blue('Type "run [taskname] --help" to get more info if available.')); | 
						|
  } | 
						|
} | 
						|
 | 
						|
function tasks(obj, namespace) { | 
						|
  let list = []; | 
						|
  Object.keys(obj).forEach(key => { | 
						|
    const value = obj[key]; | 
						|
    const nextNamespace = namespace ? `${namespace}:${key}` : key; | 
						|
 | 
						|
    if (typeof value === 'function') { | 
						|
      list.push(nextNamespace); | 
						|
    } else if (typeof value === 'object') { | 
						|
      list = list.concat(tasks(value, nextNamespace)); | 
						|
    } | 
						|
  }); | 
						|
  return list; | 
						|
} | 
						|
 | 
						|
function call(obj, args, logger, subtaskName) { | 
						|
  const taskName = subtaskName || args[2]; | 
						|
 | 
						|
  if (typeof obj[taskName] === 'function') { | 
						|
    const cli = (0, _microcli2.default)(args.slice(1), obj[taskName].help, null, logger); | 
						|
 | 
						|
    cli((options, ...params) => { | 
						|
      obj[taskName].apply({ options }, params); | 
						|
    }); | 
						|
    return obj[taskName]; | 
						|
  } | 
						|
 | 
						|
  let namespaces = taskName.split(':'); | 
						|
  const rootNamespace = namespaces.shift(); | 
						|
  const nextSubtaskName = namespaces.join(':'); | 
						|
 | 
						|
  if (obj[rootNamespace]) { | 
						|
    const calledTask = call(obj[rootNamespace], args, logger, nextSubtaskName); | 
						|
    if (calledTask) { | 
						|
      return calledTask; | 
						|
    } | 
						|
  } | 
						|
 | 
						|
  if (!subtaskName) { | 
						|
    throw new _common.RunJSError(`Task ${taskName} not found`); | 
						|
  } | 
						|
} | 
						|
 | 
						|
function autocomplete(config) { | 
						|
  const logger = new _common.SilentLogger(); | 
						|
  const completion = (0, _omelette2.default)('run <task>'); | 
						|
  completion.on('task', ({ reply }) => { | 
						|
    const runfile = load(config, logger, requirer, hasAccess); | 
						|
    reply(tasks(runfile)); | 
						|
  }); | 
						|
  completion.init(); | 
						|
} | 
						|
 | 
						|
function main() { | 
						|
  try { | 
						|
    const config = getConfig('./package.json'); | 
						|
    autocomplete(config); | 
						|
    const runfile = load(config, _common.logger, requirer, hasAccess); | 
						|
    const ARGV = process.argv.slice(); | 
						|
 | 
						|
    if (ARGV.length > 2) { | 
						|
      call(runfile, ARGV, _common.logger); | 
						|
    } else { | 
						|
      describe(runfile, _common.logger); | 
						|
    } | 
						|
  } catch (error) { | 
						|
    if (error instanceof _common.RunJSError || error instanceof _microcli.CLIError) { | 
						|
      _common.logger.error(error.message); | 
						|
      process.exit(1); | 
						|
    } else { | 
						|
      _common.logger.log(error); | 
						|
      process.exit(1); | 
						|
    } | 
						|
  } | 
						|
} |