我尝试使用JMS序列化器反序列化期间从数据库(Symfony,Doctrine)中加载对象。假设我有一个简单的Football API应用程序,两个实体 Team 和 Game ,ID为45和46的团队已经在数据库中。
从json创建新游戏时:
{
"teamHost": 45,
"teamGues": 46,
"scoreHost": 54,
"scoreGuest": 42,
}
游戏实体:
class Game {
/**
* @ORM\Id()
* @ORM\GeneratedValue()
* @ORM\Column(type="integer")
*/
private $id;
/**
* @ORM\ManyToOne(targetEntity="App\Entity\Team")
* @ORM\JoinColumn(nullable=false)
*/
private $teamHost;
/**
* @ORM\ManyToOne(targetEntity="App\Entity\Team")
* @ORM\JoinColumn(nullable=false)
*/
private $teamGuest;
我想创建一个 Game 对象,该对象已经从数据库中加载了团队。
$game = $this->serializer->deserialize($requestBody, \App\Entity\Game::class, 'json');
在寻找解决方案时,我发现了类似jms_serializer.doctrine_object_constructor
的东西,但是文档中没有特定的示例。
您可以在反序列化期间帮助我从数据库创建对象吗?
答案 0 :(得分:2)
您需要创建一个自定义处理程序: https://jmsyst.com/libs/serializer/master/handlers
一个简单的例子:
<?php
namespace App\Serializer\Handler;
use App\Entity\Team;
use Doctrine\ORM\EntityManagerInterface;
use JMS\Serializer\Context;
use JMS\Serializer\GraphNavigator;
use JMS\Serializer\Handler\SubscribingHandlerInterface;
use JMS\Serializer\JsonDeserializationVisitor;
class TeamHandler implements SubscribingHandlerInterface
{
private $em;
public function __construct(EntityManagerInterface $em)
{
$this->em = $em;
}
public static function getSubscribingMethods()
{
return [
[
'direction' => GraphNavigator::DIRECTION_DESERIALIZATION,
'format' => 'json',
'type' => Team::class,
'method' => 'deserializeTeam',
],
];
}
public function deserializeTeam(JsonDeserializationVisitor $visitor, $id, array $type, Context $context)
{
return $this->em->getRepository(Team::class)->find($id);
}
}
尽管如此,我还是建议采用通用方法来由单个处理程序处理您想要的任何实体。
示例:https://gist.github.com/Glifery/f035e698b5e3a99f11b5
另外,这个问题已经被问过了: JMSSerializer deserialize entity by id