API Platform提交关联实体时无法验证子实体OrderDetails问题
问题原因及修复方案
1. 核心问题:缺少关联对象递归校验配置
Symfony/API Platform 校验组件默认不会自动校验关联的嵌套对象,你当前只在Order的$details属性上加了@Assert\NotBlank(),只会校验details对象是否存在,不会深入校验details内部的字段规则,所以quantity的校验规则完全没有触发,直接到数据库层抛出非空错误。
2. 次要问题:双向OneToOne关联映射不完整
你在Order类的OneToOne注解中配置了mappedBy="order",说明Order是关联的反向端,OrderDetails是关联的拥有端,但你贴出的OrderDetails代码中没有定义对应的$order关联字段,会导致反序列化时无法自动绑定父子关联,级联持久化时也可能出现外键为空的问题。
具体修改步骤
第一步:给Order的关联属性加@Assert\Valid()注解
修改Order类中$details的注解配置,开启嵌套对象校验:
/** * @ORM\OneToOne(targetEntity=OrderDetails::class, mappedBy="order", cascade={"persist","remove"}) * @Assert\NotBlank() * @Assert\Valid() // 新增这行,触发OrderDetails内部的校验规则 * @Groups({"ORDER_READ","ORDER_PUT", "ORDER_POST"}) */ private ?OrderDetails $details = null; // 建议修改为允许null,由NotBlank约束非空即可
第二步:补全OrderDetails的关联字段
在OrderDetails类中补充和Order的关联配置:
// 新增Order关联属性 /** * @ORM\OneToOne(targetEntity=Order::class, inversedBy="details") * @ORM\JoinColumn(name="order_id", referencedColumnName="ID", nullable=false) * @Groups({"ORDER_PUT", "ORDER_POST"}) */ private ?Order $order = null; // 补充对应的getter、setter,同步双向关联 public function getOrder(): ?Order { return $this->order; } public function setOrder(?Order $order): self { $this->order = $order; if ($order !== null && $order->getDetails() !== $this) { $order->setDetails($this); } return $this; }
可选优化:调整关联方向更适配业务场景
如果你不想在OrderDetails中暴露order字段,可以把Order调整为关联的拥有端,修改Order的OneToOne注解即可:
/** * @ORM\OneToOne(targetEntity=OrderDetails::class, inversedBy="order", cascade={"persist","remove"}) * @ORM\JoinColumn(name="detail_id", referencedColumnName="ID", nullable=false) * @Assert\NotBlank() * @Assert\Valid() * @Groups({"ORDER_READ","ORDER_PUT", "ORDER_POST"}) */ private OrderDetails $details;
对应的OrderDetails的$order属性修改为mappedBy="details"即可。
内容的提问来源于stack exchange,提问作者Raidri
相关产品推荐
相关产品推荐

