API Platform生成TypeScript类型时ID等必填字段被标记为非必填的问题
API Platform/Symfony生成Swagger Schema时,ORM必填字段未标记为required的解决办法
问题场景
使用最新版API Platform/Symfony管理API,通过@rtk-query/codegen-openapi生成TypeScript类型时发现:ORM主键id、设置了nullable: false的关联字段createdBy等本该必填的字段,被标记为非必填;仅添加了#[Assert\NotNull]注解的date字段被识别为必填。Swagger Schema的required数组仅包含date,但这些字段在数据库层面是强制非空的。
生成的TypeScript类型
export type UserMeasurementJsonldUserMeasurementRead = { "@context"?: | string | { "@vocab": string; hydra: "http://www.w3.org/ns/hydra/core#"; [key: string]: any; }; "@id"?: string; "@type"?: string; id?: string; date: string; userDescription?: string | null; createdAt?: string; createdBy?: UserJsonldUserMeasurementRead; };
对应的Swagger Schema片段
"UserMeasurement.jsonld-UserMeasurement.read":{ "type":"object", "description":"", "deprecated":false, "properties":{ "@id":{ "readOnly":true, "type":"string" }, "id":{ "readOnly":true, "type":"string", "format":"uuid" }, "date":{ "type":"string", "format":"date-time" }, "userDescription":{ "type":[ "string", "null" ] }, "createdAt":{ "type":"string", "format":"date-time" }, "createdBy":{ "$ref":"#\/components\/schemas\/User.jsonld-UserMeasurement.read" } }, "required":[ "date" ] }
PHP实体代码
class UserMeasurement { #[ORM\Id] #[ORM\Column(type: "uuid", unique: true)] #[ORM\GeneratedValue(strategy: "CUSTOM")] #[ORM\CustomIdGenerator(class: UuidGenerator::class)] #[Groups(groups: ['UserMeasurement:read'])] protected UuidInterface $id; #[ORM\Column(type: Types::DATE_MUTABLE, name: '_date')] //#[Assert\DateTime] // dump(assert non fonctionnel) #[Assert\NotNull] #[Groups(groups: ['UserMeasurement:read', 'UserMeasurement:write'])] private ?\DateTimeInterface $date = null; #[ORM\Column(type: Types::TEXT, nullable: true)] #[Localizable] #[Assert\NotBlank(allowNull: true)] #[Groups(groups: ['UserMeasurement:read', 'UserMeasurement:write'])] private ?string $userDescription = null; #[ORM\Column] #[Groups(groups: ['UserMeasurement:read'])] private ?\DateTimeImmutable $createdAt = null; #[ORM\ManyToOne] #[ORM\JoinColumn(nullable: false)] #[Groups(groups: ['UserMeasurement:read'])] private ?User $createdBy = null; ... }
解决方法
不需要给所有字段添加#[Assert\NotNull],API Platform默认仅将**验证约束(如Assert注解)**同步到Swagger的required数组,可通过以下两种方式让ORM层面的必填字段自动加入required:
1. 全局启用ORM验证同步
在config/packages/api_platform.yaml中开启orm_validations配置,自动将ORM非空约束映射为Swagger的必填字段:
api_platform: mapping: paths: ['%kernel.project_dir%/src/Entity'] validator: enabled: true orm_validations: true
该配置会自动识别:
- 主键字段(
#[ORM\Id]) #[ORM\Column(nullable: false)]标记的字段#[ORM\JoinColumn(nullable: false)]标记的关联字段
2. 给单个字段手动标记必填
如果不需要全局同步,可给特定字段添加#[ApiProperty(required: true)]注解:
use ApiPlatform\Metadata\ApiProperty; class UserMeasurement { #[ORM\Id] #[ORM\Column(type: "uuid", unique: true)] #[ORM\GeneratedValue(strategy: "CUSTOM")] #[ORM\CustomIdGenerator(class: UuidGenerator::class)] #[Groups(groups: ['UserMeasurement:read'])] #[ApiProperty(required: true)] protected UuidInterface $id; // ... #[ORM\ManyToOne] #[ORM\JoinColumn(nullable: false)] #[Groups(groups: ['UserMeasurement:read'])] #[ApiProperty(required: true)] private ?User $createdBy = null; }
注意事项
- 主键字段默认在数据库层面必填,但API Platform不会自动将其加入
required,需通过上述方式手动配置。 - 对于ORM自动填充的字段(如
createdAt,可通过实体构造函数赋值),也可使用同样方法标记为必填。
内容的提问来源于stack exchange,提问作者Gaylord.P
相关产品推荐
相关产品推荐

