1

一直在用这个挠头。我有一个 symfony 2 json api,它为一个 android 应用程序提供数据。

api 序列化数据并使用 JMSSerializerBundle 将其发送到应用程序,完全没有问题。然后我使用 GSON 反序列化为本机 java 对象。

然后我的应用程序进行更改并将数据发布回 api。

我的问题是,当我反序列化从应用程序发送的 json 并尝试对其进行持久化/合并时,会在数据库中为已经存在的实体创建新对象。symfony 2 可以判断一个对象是否是新的吗?我会认为如果它有一个带有记录的 ID,它就会知道它是要更新而不是创建的。

这是我的控制器代码:

public function postSuggestionAction()
{

    $content = $this->get("request")->getContent();

    if (!empty($content))
    {
        $serializer = $this->get('jms_serializer');
        $suggestion = $serializer->deserialize($content, 'Calling\WebBundle\Entity\Suggestion', 'json');

        $em = $this->getDoctrine()->getManager();
        $em->persist($suggestion);
        $em->merge($suggestion->getCategory());
        $em->merge($suggestion->getNumber());
        $em->merge($suggestion->getCaller());
        $em->flush();

        $view = $this->view(true, 200);
        return $this->handleView($view);

    }

    $view = $this->view(false, 404);
    return $this->handleView($view);



}

在此先感谢史蒂夫

4

1 回答 1

1

更新

看来 EntityManager::merge() 方法确实应该有效。但是,您需要在实体的映射中使用 cascade=MERGE 或 cascade=ALL 选项。你的代码应该变成:

public function postSuggestionAction()
{

    $content = $this->get("request")->getContent();

    if (!empty($content))
    {
        $serializer = $this->get('jms_serializer');
        $detachedSggestion = $serializer->deserialize($content, 'Calling\WebBundle\Entity\Suggestion', 'json');

        $em = $this->getDoctrine()->getManager();
        $suggestion = $em->merge($detachedSuggestion);
        $em->flush();

        $view = $this->view(true, 200);
        return $this->handleView($view);

    }

    $view = $this->view(false, 404);
    return $this->handleView($view);



}

原始答案 不,除了基于区分(唯一)列查询实体的 Doctrine 之外,没有其他办法。最好的方法是从 JSON 中获取 ID,但如果不这样做,则需要有一种方法来比较实体以查看它们是否相等。然后,您可以从数据库中查询它。

你的逻辑是:

  • 在数据库中搜索对象(SELECT s FROM Suggestion WHERE s.id = :id; 如果你有 id)
  • 返回对象或 null ; 如果为空,请保留您的逻辑,否则将您的 JSON 更改反映到您的对象,然后持久保存。
于 2013-04-04T15:52:46.423 回答