Summary
The TypeScript-Zod renderer currently emits nullable date-time fields as a union containing z.coerce.date() and z.null(). Because z.coerce.date() accepts null and coerces it to the Unix epoch, a JSON field with null round-trips as "1970-01-01T00:00:00.000Z" instead of null.
Reproduction
This was found while adding the regression fixture in #2879:
{
"invoices": [
{ "name": "invoice-1", "createdAt": "2023-01-15T10:30:00Z" },
{ "name": "invoice-2", "createdAt": null }
]
}
The generated schema includes:
"createdAt": z.union([z.coerce.date(), z.null()])
The second object's createdAt: null is parsed by z.coerce.date() before the null branch can preserve it, so the fixture output differs from the input.
Expected behavior
Nullable date-time fields should preserve null when parsing/serializing.
Notes
#2879 is skipping its new fixture for TypeScript-Zod so the unrelated Dart regression fix can pass CI.
Summary
The TypeScript-Zod renderer currently emits nullable date-time fields as a union containing
z.coerce.date()andz.null(). Becausez.coerce.date()acceptsnulland coerces it to the Unix epoch, a JSON field withnullround-trips as"1970-01-01T00:00:00.000Z"instead ofnull.Reproduction
This was found while adding the regression fixture in #2879:
{ "invoices": [ { "name": "invoice-1", "createdAt": "2023-01-15T10:30:00Z" }, { "name": "invoice-2", "createdAt": null } ] }The generated schema includes:
The second object's
createdAt: nullis parsed byz.coerce.date()before the null branch can preserve it, so the fixture output differs from the input.Expected behavior
Nullable date-time fields should preserve
nullwhen parsing/serializing.Notes
#2879 is skipping its new fixture for TypeScript-Zod so the unrelated Dart regression fix can pass CI.