0

我正在尝试将我的 phpstan 设置提升到第 3 级,但我收到如下错误:

Property Something::$repository (SpecificRepository) does not accept RepositoryInterface.

在一个看起来像这样的类上:

class Something
{
    /** @var SpecificRepository */
    protected $repository;

    public function __construct(ORM $orm)
    {
        $this->orm = $orm;
        $this->repository = $orm->getRepository(Something::class);
    }
}

我知道我的 ORM 的getRepository方法返回RepositoryInterface,因为它不能更具体,但我需要@vartypehint 来告诉我的 IDE 工具和 phpstan,在这个类中,$repository更具体地是一个SpecificRepository. 我该怎么做?

4

2 回答 2

1

PHPStan 不会运行您的代码或查看您的参数以了解此方法将返回特定类型的对象——它只是查看该方法的返回签名。因此,从 PHPStan 的角度来看,不能保证getRepository()会返回 的实例SpecificRepository,这意味着不能保证$this->repository会包含 的实例SpecificRepository。但是,您试图通过您的 typehint 告诉 PHPStan——@var而 PHPStan (正确地)告诉您您错了。为了在更具体的类上获得 IDE 自动完成的好处,您可以将属性键入到其通用接口,然后编写一个 getter 类来验证您期望的更具体的类:

protected RepositoryInterface $repository;

protected function getSpecificRepository(): SpecificRepository
{
    if ($this->repository instanceof SpecificRepository === false) {
        throw new Exception('Expected an instance of SpecificRepository');
    }
    return $this->repository;
}

然后$this->getSpecificRepository()在您的代码中使用而不是$this->repository.

于 2022-02-14T18:05:05.410 回答
1

$em->getRepository(Something::class);如果满足两个条件,PHPStan 可以理解返回 SpecificRepository:

  1. 您安装 phpstan-doctrine 扩展
  2. 某物是一个实体类,它已repositoryClass在其实体元数据中设置。
于 2022-02-14T20:05:33.173 回答