实体预期对象返回 symfony

Entity expected object returned symfony

我正在尝试从数据库中获取项目并将其传递给新项目以推送到数据库。

$post = $entityManager->getRepository('App:Post')
            ->find($id);

$comment->setPost($post)

setPost 如下所示:

public function setPost(Post $post): self
    {
        $this->post = $post;

        return $this;
    }

$post 变量:

 /**
     * @ORM\ManyToOne(targetEntity="App\Entity\Post", inversedBy="comments")
     * @ORM\JoinColumn(nullable=false)
     */
    private $post;

但是当我尝试将 post 设置为 setPost($post) 时,出现以下错误:

Expected parameter of type '\App\Entity\Post', 'object' provided

我假设,您看到的错误来自您的集成开发环境 (IDE),例如 eclipse、vs code、phpstorm 等。但是代码 - 在实际执行时 - 应该可以工作。

现在,错误最有可能源于所说 IDE 后台的静态代码分析 运行,它将查看语句并尝试根据调用的方法进行分析,访问您的变量是哪种类型的属性等。

所以,让我们慢慢来(您可以将鼠标悬停在 $vars->methods() 上进行验证。我感兴趣的行是

$post = $entityManager->getRepository('App:Post')
            ->find($id);

所以 $entityManagerEntityManagerInterface 类型,它有一个 getRepository 方法和一个 string 类型的必需参数('App:Post' 在你的例子中) ,它会 return 一个类型 ObjectRepository 的对象,它有一个方法 find 需要一个参数(mixed,不要问),并且 returns ?object 表示 objectnull。所以,$postobject 类型(最好的情况,或者为 null,在这种情况下它会失败!)。现在,下一行显然需要 Post 类型的参数而不是 object 类型的参数,因此 warning/notice/error.

现在,静态代码分析在一定程度上很有帮助,但它并不是万无一失的,因为它有局限性。它不知道什么运行时 实际上 return,它只是假设在代码(学说)中找到的类型提示足够具体——它们不在你的情况。

简单的修复

添加一个文档字符串来告诉静态代码分析变量 $post 的实际类型是什么:

/** @var Post $post */
$post = $entityManager->getRepository('App:Post')
            ->find($id);

这明确告诉静态分析工具,$post 是类型 Post,也许你必须写 App\Entity\Post 甚至 \App\Entity\Post.

硬修复

或者,您可以实现自己的 PostRepository(学说提供 一些 帮助)并定义一个像 function findById($id) :Post 这样的函数——它会明确地告诉静态代码分析,当你在你的代码中调用它时 return 类型是什么(通过依赖注入注入你的函数:PostRepostory $postRepository):

$post = $postRepository->findById($id);

如果您使用许多不同的实体,这是一个非常冗长的解决方案,但根据您的项目,这可能是值得的,因为您明确命名依赖项而不是注入非常不明确的内容(正如我们看到)EntityManagerInterface。使用 EntityManagerInterface 可能会使测试变得糟糕(恕我直言!)。