Symfony中XML反序列化失败问题求助
Symfony XML反序列化失败:对象属性全部为null
问题描述
在Symfony框架中尝试XML反序列化,先后使用Symfony原生Serializer和JMS Serializer,结果生成的Dossiers对象的source、type、dossiers属性均为null。代码配置看起来无问题,期望XML数据能正确映射到数据对象,以便后续业务处理。
相关代码
Controller代码
<?php namespace App\Controller; use App\DataObjects\Dossiers; use JMS\Serializer\SerializerInterface; use Symfony\Bundle\FrameworkBundle\Controller\AbstractController; use Symfony\Component\HttpFoundation\Response; use Symfony\Component\Routing\Annotation\Route; #[Route('/test')] class TestController extends AbstractController { private $serializer; public function __construct(SerializerInterface $serializer) { $this->serializer = $serializer; } #[Route('/')] public function test(): Response { $xmlContent = '<?xml version="1.0" encoding="UTF-8" standalone="yes"?> <Dossiers source="Source" type="myType"> <Dossier> <Name>Name</Name> <Description>Description</Description> </Dossier> </Dossiers>'; // 反序列化XML内容 $dossiers = $this->serializer->deserialize($xmlContent, Dossiers::class, 'xml'); // 调试输出 echo "Source: " . $dossiers->getSource() . "<br>"; echo "Type: " . $dossiers->getType() . "<br>"; echo "Dossiers:<br>"; foreach ($dossiers->getDossiers() as $dossier) { echo " Name: " . $dossier->getName() . "<br>"; echo " Description: " . $dossier->getDescription() . "<br>"; } dd($dossiers); return new Response('Parsed XML'); } }
App\DataObjects\Dossiers代码
<?php namespace App\DataObjects; use JMS\Serializer\Annotation as JMS; /** * @JMS\XmlRoot("Dossiers") */ class Dossiers { /** * @JMS\XmlAttribute * @JMS\SerializedName("source") * @JMS\Type("string") */ private $source; /** * @JMS\XmlAttribute * @JMS\SerializedName("type") * @JMS\Type("string") */ private $type; /** * @JMS\SerializedName("Dossier") * @JMS\Type("array<App\DataObjects\Dossier>") * @JMS\XmlList(inline = true, entry = "Dossier") */ private $dossiers = []; public function getSource() { return $this->source; } public function setSource($source) { $this->source = $source; } public function getType() { return $this->type; } public function setType($type) { $this->type = $type; } public function getDossiers() { return $this->dossiers; } public function setDossiers(array $dossiers) { $this->dossiers = $dossiers; } }
App\DataObjects\Dossier代码
<?php namespace App\DataObjects; use JMS\Serializer\Annotation as JMS; class Dossier { /** * @JMS\XmlElement(cdata=false) * @JMS\SerializedName("Name") * @JMS\Type("string") */ private $name; /** * @JMS\XmlElement(cdata=false) * @JMS\SerializedName("Description") * @JMS\Type("string") */ private $description; public function getName() { return $this->name; } public function setName($name) { $this->name = $name; } public function getDescription() { return $this->description; } public function setDescription($description) { $this->description = $description; } }
当前返回结果
Source: Type: Dossiers: App\DataObjects\Dossiers {#146 ▼ -source: null -type: null -dossiers: [] }
排查与解决方法
1. 修复注解冲突
Dossiers类的dossiers属性同时使用了@JMS\SerializedName("Dossier")和@JMS\XmlList,二者存在冲突。XmlList已通过entry = "Dossier"指定了节点名称,移除多余的SerializedName注解即可:
/** * @JMS\Type("array<App\DataObjects\Dossier>") * @JMS\XmlList(inline = true, entry = "Dossier") */ private $dossiers = [];
2. 修正XML格式问题
原XML字符串包含多余缩进,可能导致解析异常,移除多余缩进后确保结构正确:
$xmlContent = '<?xml version="1.0" encoding="UTF-8" standalone="yes"?> <Dossiers source="Source" type="myType"> <Dossier> <Name>Name</Name> <Description>Description</Description> </Dossier> </Dossiers>';
3. 明确注入JMS Serializer服务
若同时存在Symfony原生Serializer,需在构造函数中明确指定注入JMS的Serializer:
use JMS\Serializer\SerializerInterface as JMSSerializerInterface; // ... public function __construct(JMSSerializerInterface $serializer) { $this->serializer = $serializer; }
4. 清除缓存
Symfony注解缓存可能导致修改不生效,执行以下命令清除缓存:
php bin/console cache:clear
完成以上步骤后,XML数据即可正确映射到Dossiers对象中。
内容的提问来源于stack exchange,提问作者Illmaren
相关产品推荐
相关产品推荐

