JMS序列化XML时如何不借助中间实体填充嵌套路径属性?
解决JMS Serializer反序列化嵌套XML节点无中间实体的问题
当然可以不用中间实体就能填充$cc字段!问题出在你用错了注解——@JMS\SerializedName并不支持XML中的路径写法,要定位嵌套节点得用@JMS\XmlPath注解。
问题根源
@JMS\SerializedName在XML序列化场景下,仅用于映射当前层级的节点名称,无法解析"cc/bb"这种嵌套路径格式。所以Serializer找不到对应节点,导致$cc始终为空。
解决方案
把$cc字段上的@JMS\SerializedName("cc/bb")替换为@JMS\XmlPath("cc/bb"),同时保留@XmlList(entry="b")来映射子节点列表。修改后的A类如下:
final class A { /** * @JMS\Type("array<B>") * @JMS\XmlList(entry="b") * @JMS\SerializedName("bb") */ private $bb; /** * @JMS\Type("array<B>") * @JMS\XmlList(entry="b") * @JMS\XmlPath("cc/bb") */ private $cc; }
原理说明
@JMS\XmlPath注解支持XPath相对路径,这里的"cc/bb"是相对于<a>节点(也就是A类对应的根节点)的路径,能精准定位到XML中<cc>下的<bb>节点,再配合@XmlList(entry="b")就能把<bb>里的所有<b>节点序列化为B对象的数组。
这样修改后,运行你的反序列化代码:
$object = $this->serializer->deserialize($xml, A::class, 'xml');
$object->cc就会被正确填充为包含三个B对象的数组,每个对象的c属性对应cbc1、cbc2、cbc3。
内容的提问来源于stack exchange,提问作者Tomek Kobyliński
相关产品推荐
相关产品推荐

