UNPKG

ng6-cli

Version:

Tooling to build applications with Angular 1.5, ES6, and Webpack.

422 lines (296 loc) 11 kB
var path = require('path'); var BaseClass = require('ouro-base'); var chalk = require('chalk'); var _ = require('lodash'); var Case = require('case'); var merge = require('deepmerge'); var Promise = require('bluebird'); var gulp = require('gulp'); var rename = require('gulp-rename'); var ejs = require('gulp-ejs'); var batchReplace = require('gulp-batch-replace'); //todo: replace augmented context variables (name.camel, name_title, etc) with methods using EJS in the templates module.exports = BaseClass.extend({ init: function(cli) { this.cli = cli; this.templates = cli.templates; }, createApp: function(template, name, destination) { var self = this; console.log(chalk.cyan(':: creating new app:'), chalk.white(name) + chalk.gray(' ('+path.resolve(destination)+')')); if( this.templates.get('app', template) ) { this.template('app', template) .context({name: name}) .dest(destination) .then(function() { if(self.templates.get('app', template).done ) { self.templates.get('app', template).done(name, destination); } }); } else { return false; } }, createLibrary: function(template, name, destination) { var self = this; console.log(chalk.cyan(':: creating new library:'), chalk.white(name) + chalk.gray(' ('+path.resolve(destination)+')')); if( this.templates.get('library', template) ) { this.template('library', template) .context({name: name}) .dest(destination) .then(function() { if(self.templates.get('library', template).done ) { self.templates.get('library', template).done(name, destination); } }); } else { return false; } }, createModule: function(name, destination, callback) { console.log(chalk.cyan(':: creating new module:'), chalk.white(name) + chalk.gray(' ('+path.normalize(path.relative(this.cli.reflect.projectRoot(), destination)+'/'+name+'.module.js)'))); var self = this; this.template('module', 'default') .options({rename: {name: name}}) .context({moduleName: this.cli.reflect.getModuleName(destination), name: name, 'name.camel': Case.camel(name)}) .dest(destination) .then(function() { var parentModulePath = self.cli.reflect.findParentModule(destination); if( parentModulePath ) { self.cli.refactor.addModuleImport({ identifier: name, child: path.resolve(destination + '/' + name + '.module.js'), parent: parentModulePath }); self.cli.refactor.addAngularDependency({ identifier: name, module: parentModulePath }); } if( callback ) { callback.apply(self, []); } }); }, createArtifact: function(type, template, name, destination, callback) { var self = this; var artifactName = Case.camel(name); var pathName = Case.kebab(name); this.template(type, template) .options({rename: {name: pathName}}) .context({moduleName: this.cli.reflect.getModuleName(destination), name: pathName, 'name_camel': Case.camel(name), 'name_title': Case.title(name)}) .dest(destination) .then(function () { var identifier = artifactName; var parentModulePath = self.cli.reflect.findParentModule(path.resolve(destination)); //determine whether importing module or specific artifact var importType = type; if( type === 'component' ) { importType = 'module'; } else if( type === 'directive' && template === 'element' ) { importType = 'module'; } //add service suffix if not set if( type === 'service' ) { identifier = Case.pascal(identifier); if( identifier.substr(identifier.length-'service'.length, identifier.length) !== 'Service' ) { identifier += 'Service'; } } var modulePath = path.normalize(path.relative(self.cli.reflect.projectRoot(), destination) + '/' + pathName +'.' + importType+'.js'); console.log(chalk.cyan(':: creating new ' + type + ': '), chalk.white(identifier) + chalk.gray(' (' + modulePath + ')')); self.cli.refactor.addModuleImport({ identifier: identifier, child: path.resolve(destination + '/' + pathName + '.' + importType + '.js'), parent: parentModulePath }); if( importType === 'module' ) { self.cli.refactor.addAngularDependency({ identifier: name, module: parentModulePath }); } else { self.cli.refactor.addAngularDefinition({ name: identifier, type: type, module: parentModulePath }); } if(self.templates.get(type, template).done ) { self.templates.get(type, template).done(name, destination); } if( callback ) { callback.apply(self, []); } }); }, createTemplate: function(name) { var type = this.cli.reflect.getType(name); var template = this.cli.reflect.getTemplate(name); var destination = path.resolve(this.cli.reflect.projectRoot() + '/templates/' + type + '/' + template); console.log(chalk.cyan(':: creating new template: ' + chalk.white(name))); this.template('template', 'default') .context({name: name}) .dest(destination) .then(function () { //done }); }, createCommand: function(name) { var destination = path.resolve(this.cli.reflect.projectRoot() + '/commands/' + name); console.log(chalk.cyan(':: creating new command: ' + chalk.white(name))); this.template('command', 'default') .context({name: name}) .dest(destination) .then(function () { //done }); }, template: function(type, templateName) { var template = this.templates.get(type, templateName); if(template) { var templatePath = []; if( _.isArray(template.templatePath) ) { templatePath = template.templatePath.map(function(path) { return path + '/template/**/*'; }); } else { templatePath.push(template.templatePath + '/template/**/*'); } return this.source(templatePath, template); } else { return false; } }, source: function(sourcePath, template) { var worker = { //essential references cli: this.cli, templates: this.templates, template: template, //populate data with cli config and request options data: { cli: { config: this.cli.config.config, request: this.cli.request.request, options: merge(this.cli.config.config.options, this.cli.request.request.options) } }, //setup source path(s) sourcePath: [sourcePath], //setup template configuration config: {replace: [], rename: {}}, //expose methods available to this generation task context: this.context, options: this.options, dest: this.dest, generate: this.generate }; if( template && template.config ) { worker.config = merge(worker.config, template.config()); } return worker; }, context: function(context) { this.data = merge(this.data, context); return this; }, options: function(options) { this.config = merge(this.config, options); //make sure we always have at least an empty array if( !this.config.replace ) { this.config.replace = []; } //make sure we always have at least an empty array if( !this.config.rename ) { this.config.rename = {}; } return this; }, dest: function(destination) { var self = this; self.destination = destination; return new Promise(function(resolve, reject) { if (self.cli.isEnabled('debug')) { console.log(chalk.gray(':: source:'), chalk.white(self.sourcePath)); console.log(chalk.gray(':: destination:'), chalk.white(destination)); } Promise.each(self.sourcePath, function(sourcePath) { return self.generate.apply(self, [sourcePath]); }) .then(function() { resolve(); }) .catch(function(err) { reject(err); }); }); }, generate: function(sourcePath) { var self = this; return new Promise(function(resolve, reject) { if (self.cli.isEnabled('debug')) { console.log(chalk.gray(':: generating template:'), chalk.white(sourcePath)); } var stream = gulp.src(sourcePath, {dot: true}) .pipe(rename(function (path) { //rename exact file name var dir = self.config.rename[path.dirname]; if( dir ) { var file = dir[path.basename + path.extname]; if( file ) { if( typeof file === 'object' ) { if (file.basename) { path.basename = file.basename; } if (file.extname) { path.extname = file.extname; } } else { file = file.split('.'); path.basename = file[0]; if( file[1] ) { path.extname = '.' + file[1]; } } } } //replace the keyword 'name.' at the beginning of a file with the artifact name if( path.basename.split('.')[0] === 'name' ) { var basename = path.basename.split('.'); var newName = Case.kebab(self.data.name); basename.shift(); basename.unshift(newName); if (self.cli.isEnabled('debug')) { console.log(chalk.gray(':: renaming file:'), chalk.white(basename.join('.') + path.extname)); } path.basename = basename.join('.'); } //replace first segment name... if( self.config.rename.startsWith ) { for( var startsWith in self.config.rename.startsWith ) { if( path.basename.split('.')[0] === startsWith ) { var basename1 = path.basename.split('.'); var newName1 = Case.kebab(self.config.rename.startsWith[startsWith]); basename1.shift(); basename1.unshift(newName1); if (self.cli.isEnabled('debug')) { console.log(chalk.gray(':: renaming file:'), chalk.white(basename1.join('.') + path.extname)); } path.basename = basename1.join('.'); } } } })) .pipe(batchReplace(self.config.replace)) .pipe(ejs(self.data)) .pipe(gulp.dest(self.destination)); stream.on('end', function () { resolve({}); }); stream.on('error', function (err) { reject(err); }); }); } });