@qbyco/tjs-cli
Version:
TrafaletJS CLI Tool
374 lines (286 loc) • 12.6 kB
JavaScript
const fs = require('fs');
const path = require('path');
const mkdirp = require('mkdirp');
const CLICommand = require("../../lib/cli/Command/CLICommand");
const Stub = require("../../lib/stub/stub");
class Make extends CLICommand {
constructor(lib) {
super('make');
this.lib = lib;
this.configPath = path.join(this.lib.cwd, 'trafaletjs.json');
}
/**
* @method componentAction
* @description Create a component for a module
* @param {String} name
* @param {Object} options
*/
componentAction (name, options) {
console.log(this.lib.chalk.white.bold('\nTrafaletJS CLI ----------------\n'));
if(!fs.existsSync(this.configPath)) {
console.log(this.lib.chalk.red('Please specify a trafaletjs version'));
return false;
}
this.config = require(this.configPath);
this.options = {
appPath: path.join(this.lib.cwd, this.config.appPath),
uiPath: path.join(this.lib.cwd, this.config.uiPath),
statePath: path.join(this.lib.cwd, this.config.statePath),
storagePath: path.join(this.lib.cwd, this.config.storagePath)
};
if ("object" === typeof name) {
console.log(this.lib.chalk.red(' Component name not supplied!\n'));
return false;
}
if( -1 === name.indexOf('/')) {
console.log(this.lib.chalk.red(' Component name not valid! Use format: moduleName/componentName\n'));
return false;
}
let
moduleName = name.split('/')[0],
componentName = name.split('/')[1],
componentPath = path.join(this.options.uiPath, moduleName, 'components'),
modulePath = path.join(this.options.uiPath, moduleName),
module,
moduleTemplate = new Stub('components/module.html'),
componentTemplate = new Stub('components/component.js'),
componentTemplateOptions = '\n',
templateName;
if(fs.existsSync(path.join(componentPath, componentName + '.js'))) {
console.log(this.lib.chalk.red(' Component with this name already exist!\n'));
return false;
}
componentTemplate.parse('module', moduleName);
componentTemplate.parse('componentName', componentName);
componentTemplate.parse('componentTpl', componentName.toLowerCase());
if(undefined !== options['template']) {
templateName = options['template'];
} else {
templateName = moduleName + '-' + componentName.toLowerCase();
}
componentTemplateOptions += ' template: "' + templateName + '",\n';
if(undefined !== options['namespace']) {
componentTemplateOptions += ' namespace: "' + options['namespace'] + '",\n';
}
if(undefined !== options['abstract']) {
componentTemplateOptions += ' abstract: true,\n';
}
if(undefined !== options['extend']) {
componentTemplateOptions += ' extend: "' + options['extend'] + '",\n';
}
componentTemplate.parse('templateOptions', componentTemplateOptions);
// New module create module first
if(! fs.existsSync(path.join(modulePath, 'module.js'))) {
module = this.moduleAction(moduleName, {
withComponent: true
});
}
console.log(this.lib.chalk.green(' - Write file: ' + moduleName + '/' + componentName + '.js'));
fs.writeFileSync(path.join(componentPath, componentName + '.js'), componentTemplate.getStubContent());
console.log(this.lib.chalk.green(' - Append component HTML to module ' + moduleName + '\n'));
moduleTemplate.parse('componentName', componentName);
moduleTemplate.parse('componentTpl', templateName);
fs.appendFileSync(path.join(modulePath, 'module.html'), moduleTemplate.getStubContent());
if(undefined !== module && undefined !== module['stub']) {
module['stub'].parse('componentNameUse', 'module.use("' + componentName + '");');
module['stub'].parse('componentNameRender', 'this.singleInstance("' + componentName + '").render(data, container);');
fs.appendFileSync(path.join(modulePath, 'module.js'), module['stub'].getStubContent());
} else {
console.log(this.lib.chalk.yellow(' [NOTE!] Open module ' + moduleName + '/module.js and append line: " module.use("' + componentName + '"); " to be able to use it!\n'));
}
}
/**
* @method controllerAction
* @description Create a controller
* @param {String} name
* @param {Object} options
*/
controllerAction (name, options) {
console.log(this.lib.chalk.white.bold('\nTrafaletJS CLI ----------------\n'));
if(!fs.existsSync(this.configPath)) {
console.log(this.lib.chalk.red('Please specify a trafaletjs version'));
return false;
}
this.config = require(this.configPath);
this.options = {
appPath: path.join(this.lib.cwd, this.config.appPath),
uiPath: path.join(this.lib.cwd, this.config.uiPath),
statePath: path.join(this.lib.cwd, this.config.statePath),
storagePath: path.join(this.lib.cwd, this.config.storagePath)
};
let
filePath = path.join(this.options.appPath, name + '.js'),
controllerTemplate = new Stub('components/logic.js');
if ("object" === typeof name) {
console.log(this.lib.chalk.red(' Controller name not supplied!'));
return false;
}
if(fs.existsSync(filePath)) {
console.log(this.lib.chalk.red(' Controller name: ' + name + ' already exists!'));
return false;
}
if(! fs.existsSync(filePath)) {
fs.writeFileSync(filePath, '');
}
controllerTemplate.parse('name', this.config.name.capitalizeFirstLetter());
controllerTemplate.parse('controller', name.capitalizeFirstLetter());
if(undefined !== options['withModule']) {
controllerTemplate.parse('view', 'View = TJS.module.load("' + options['withModule'] + '");');
controllerTemplate.parse('viewRender', 'View.render.apply(View, arguments);');
} else {
controllerTemplate.parse('view', '');
controllerTemplate.parse('viewRender', '');
}
if(undefined !== options['withContainer']) {
controllerTemplate.parse('container', 'View.setContainer("' + options['withContainer'] + '");');
} else {
controllerTemplate.parse('container', '');
}
console.log(this.lib.chalk.green(' - Create controller: ' + name + ' complete!\n'));
fs.appendFileSync(filePath, controllerTemplate.getStubContent());
}
/**
* @method moduleAction
* @description Create a module
* @param {String} name
* @param {Object} options
* @return {*}
*/
moduleAction (name, options) {
if(!fs.existsSync(this.configPath)) {
console.log(this.lib.chalk.red('Please specify a trafaletjs version'));
return false;
}
this.config = require(this.configPath);
this.options = {
appPath: path.join(this.lib.cwd, this.config.appPath),
uiPath: path.join(this.lib.cwd, this.config.uiPath),
statePath: path.join(this.lib.cwd, this.config.statePath),
storagePath: path.join(this.lib.cwd, this.config.storagePath)
};
if ("object" === typeof name) {
console.log(this.lib.chalk.red(' Module name not supplied!'));
return false;
}
let
modulePath = path.join(this.options.uiPath, name),
moduleJsTemplate = new Stub('components/module.js'),
withComponent = false;
if(undefined !== options['withComponent']) {
withComponent = true;
} else {
console.log(this.lib.chalk.white.bold('\nTrafaletJS CLI ----------------\n'));
}
mkdirp.sync(path.join(modulePath, 'components'));
// Module does not exist. Create base files
if(! fs.existsSync(path.join(modulePath, 'module.js'))) {
console.log(this.lib.chalk.green(' - Create module: ' + name ));
fs.writeFileSync(path.join(modulePath, 'module.js'), '');
fs.writeFileSync(path.join(modulePath, 'module.html'), '');
moduleJsTemplate.parse('module', name);
} else {
// Module already exists
console.log(this.lib.chalk.yellow(' - Skip module creation! Already exists'));
return this;
}
// Return this stub to component creation for further writing
if(withComponent) {
return {
stub: moduleJsTemplate
};
}
// Write module.js file
else {
moduleJsTemplate.parse('componentNameRender', '');
moduleJsTemplate.parse('componentNameUse', '');
console.log(this.lib.chalk.green(' - New module ' + name + ' created!'));
fs.appendFileSync(path.join(modulePath, 'module.js'), moduleJsTemplate.getStubContent());
return this;
}
}
stateAction (name, options) {
console.log(this.lib.chalk.white.bold('\nTrafaletJS CLI ----------------\n'));
if ("object" === typeof name) {
console.log(this.lib.chalk.red(' State name not supplied!\n'));
process.exit();
}
this.config = require(this.configPath);
this.options = {
appPath: path.join(this.lib.cwd, this.config.appPath),
uiPath: path.join(this.lib.cwd, this.config.uiPath),
statePath: path.join(this.lib.cwd, this.config.statePath),
storagePath: path.join(this.lib.cwd, this.config.storagePath)
};
if
(
fs.existsSync(path.join(this.options.statePath, 'definitions', name + '.js')) ||
fs.existsSync(path.join(this.options.statePath, 'contracts', name + '.js'))
) {
console.log(this.lib.chalk.red(' - State with this name already exist!\n'));
process.exit();
}
let
stateName = name.toLowerCase(),
stateContractName,
tmpStateNameArr = [],
stateNameArr = stateName.split('.'),
//Templates
defineStub = new Stub('components/stateDefinitions.js'),
contractStub = new Stub('components/stateContractDefine.js');
for(let i_part = 0; i_part < stateNameArr.length; i_part += 1) {
tmpStateNameArr.push(stateNameArr[i_part].capitalizeFirstLetter());
}
stateName = tmpStateNameArr.join('.').toLowerCase();
stateContractName = tmpStateNameArr.join('') + 'Contract';
console.log(this.lib.chalk.green(' - Create state definition ' + name ));
defineStub.parse('name', this.config.name.capitalizeFirstLetter());
defineStub.parse('stateContractName', stateContractName);
fs.writeFileSync(path.join(this.options.statePath, 'contracts', name + '.js'), defineStub.getStubContent());
if(undefined !== options['withAdd']) {
console.log(this.lib.chalk.green(' - Create state contract with a default value\n'));
contractStub = new Stub('components/stateContractAdd.js');
}
contractStub.parse('name', this.config.name.capitalizeFirstLetter());
contractStub.parse('stateName', stateName);
contractStub.parse('stateContractName', stateContractName);
fs.writeFileSync(path.join(this.options.statePath, 'definitions', name + '.js'), contractStub.getStubContent());
}
storageAction (name, options) {
if(!fs.existsSync(this.configPath)) {
console.log(this.lib.chalk.red('Please specify a trafaletjs version'));
return false;
}
this.config = require(this.configPath);
this.options = {
appPath: path.join(this.lib.cwd, this.config.appPath),
uiPath: path.join(this.lib.cwd, this.config.uiPath),
statePath: path.join(this.lib.cwd, this.config.statePath),
storagePath: path.join(this.lib.cwd, this.config.storagePath)
};
if (fs.existsSync(path.join(this.options.storagePath, name + '.js'))) {
console.log(this.lib.chalk.red(' - Storage file with this name already exist!\n'));
process.exit();
}
const storageName = name.toLowerCase();
//Templates
const storeStub = new Stub('components/storage.js');
storeStub.parse('name', storageName);
storeStub.parse('name', this.config.name.capitalizeFirstLetter());
fs.writeFileSync(path.join(this.options.storagePath, name + '.js'), storeStub.getStubContent());
}
help () {
let help = new Map();
help.set('controller [name] [--withModule, --withContainer]', 'Create a controller');
help.set('module [name]', 'Create a module');
help.set('component [moduleName/componentName] [--abstract, --extend, --template, --namespace]', 'Create a component');
help.set('state [name] [--withAdd]', 'Create a state object template');
help.set('storage [name]', 'Create a storage file');
return help;
}
}
module.exports = {
init: function (lib) {
lib.cli.getRepository().addCommand(new Make(lib));
},
run: function (lib) {}
};