【发布时间】:2015-10-08 08:29:36
【问题描述】:
背景
我正在为 Angular SPA(单页应用程序)创建一个脚手架生成器。它将依赖于标准角度生成器('yo angular')设置的环境,并且还依赖于标准角度子生成器来生成应用程序所需的一些额外服务和控制器。换句话说,我正在“装饰”一个基本的 Angular 应用程序。
如果用户之前安装了 Angular 应用程序(我查找标记文件并在我的代码中设置布尔值“angularAppFound”),生成器将正常工作。但是,我希望它也是“一站式”的,因为如果他们还没有设置角度应用程序,我的生成器会在我安装额外的角度工件之前为他们调用角度生成器 在一次运行中。
显然,如果没有 Angular 应用程序,我的依赖任务将无法工作。
数据
我的代码如下所示:
// need this to complete before running other task
subgeneratorsApp: function () {
if (!this.angularAppFound) {
var done = this.async();
this.log('now creating base Angular app...');
// doesn't work (does not drive .on)
//this.composeWith('angular', {args: [ this.appName ]} )
// works (drives .on)
this.invoke('angular', {args: [ this.appName ]} )
.on('end',function(){
this.log('>>>in end handler of angular base install');
done();
}.bind(this));
}
},
// additional steps to only run after full angular install
subgeneratorServices: function () {
Object.keys(this.artifacts.services).forEach( function (key, index, array) {
this.composeWith('angular:service', {args: [ this.artifacts.services[key] ]} );
}.bind(this));
},
subgeneratorControllers: function () {
Object.keys(this.artifacts.controllers).forEach( function (key, index, array) {
this.composeWith('angular:controller', {args: [ this.artifacts.controllers[key] ]} );
}.bind(this));
},
通过查看日志和结果,我凭经验确定 'composeWith' 不会驱动 .on 方法,而 'invoke' 会。
如果.on方法没有被驱动,done()也没有被驱动,并且生成器在安装完angular base之后停止并且不驱动后续步骤(因为生成器认为步骤永远不会结束)。
我可以使用调用,但它已被弃用:
(!) generator#invoke() is deprecated. Use generator#composeWith() - see http://yeoman.io/authoring/composability.html
问题
在组合生成器时,核心思想是保持两者解耦。他们不应该关心顺序,他们应该以任何顺序运行并输出相同的结果。
然后我应该如何处理我的情况,因为订购 很重要(除了使用“调用”)?在不牺牲“一站式”处理的情况下,我想不出任何其他方式来重新组织我的生成器。
我应该简单地说用户必须在单独的步骤中安装 Angular 并且不允许“一站式”处理吗?
'composeWith' 不发出 'end' 事件是设计使然吗?
如果没有,您建议我打开一个错误报告,还是有其他方法可以做到(不推荐使用)?
非常感谢。
【问题讨论】:
-
在查看 base.js (github.com/yeoman/generator/blob/master/lib/base.js) 的源代码时,我确实看到了一个 'this.emit('end');'在运行路径上,由 composeWith() 函数调用。据我所知,composeWith 没有理由不发出“结束”事件。
标签: node.js yeoman yeoman-generator yeoman-generator-angular