我有一个工厂方法,其签名与此类似:
/**
* @param class-string $class
* @param callable? $callback
* @return static
*/
public function instance(string $class, callable? $callback);
根据第一个参数,将创建一个实例。而不是返回实例,而是返回$this——因此可以提供一个可选的回调,工厂调用它,传递新实例。
我想知道的是,如果传递的字符串是字面的,那么phpstan/vscode是否可以被告知传递给可调用对象的参数是我指定类的实例,这样当我引用可调用对象中的对象时,它可以对可用的方法/道具提出建议,这样phpstan就不会抱怨缺少方法,而我也不会键入可调用的参数?
创建的对象确实扩展了一个公共基类,但子类将有自己的方法。
举一个电话的例子也许会更清楚:
$obj->factory(Foo::class, function ($foo) {
//
}
我希望避免重复明确的提示:
$obj->factory(Foo::class, function (Foo $foo) {
//
}
您可以使用泛型来实现这一点。
看看这个例子:https://phpstan.org/r/cf596842-d9cb-4996-b2af-08d6683dd366
基本上你需要这样的声明:
/**
* @template T of object
* @param class-string<T> $class
* @param (callable(T):mixed)|null $callback
* @return static
*/
public function instance(string $class, callable|null $callback)
这里我们说的是可调用函数有一个必需的参数。它的类型是传递给instance
方法的第一个参数的对象。
你可以在这里和这里阅读更多关于泛型的内容。