假设我有一个带有工厂方法的类:
export class Foo {
constructor(options) {
this.a = options.a;
this.b = options.b;
}
/**
* @param {{
* a: number,
* b: number
* }} options
* @return {!Foo}
*/
static create(options) {
return new Foo(options);
}
}
我希望依赖注入Foo
的工厂方法在另一个类中,例如:
/**
* @param {{
* createFoo: !function(!Object): !Foo
* }} options
*/
问题:Closure编译器说这与形式参数不匹配。
found : {
createFoo: function ({a: number, b: number): Foo,
}
required: {
createFoo: function (Object): Foo,
}
显然我可以在记录中重写类型签名和硬编码,但我真的想引用Foo.create
所以每次添加新参数时都不需要更新整个代码库选项对象。
我怎样才能为CC做这个?
答案 0 :(得分:3)
一种方法是在typedef中写入一次类型,然后在两个地方引用它。 (我还没试过这个,但我认为它应该有用)
/** @typedef {function({a: number, b:number}): Foo} */
var FooCreator;
export class Foo {
...
/**
* @type {FooCreator}
*/
static create(options) {
return new Foo(options);
}
}
/**
* @param {{
* createFoo: FooCreator
* }} options
*/
答案 1 :(得分:2)
一般问题是你需要的函数比Foo.create方法更容易接受。尼克桑托斯写了一个很好的解释:
http://closuretools.blogspot.com/2012/06/subtyping-functions-without-poking-your.html
使用松散的函数类型“函数”或“!函数”将按预期工作。
我用这个定义来验证:
/** @param {{createFoo: !Function}} options */
function f(options) {}
f({createFoo: Foo.create});