Z
Zod5mo ago
ramblings

ramblings - Is there a way to make one field re...

Is there a way to make one field readonly instead of the entire schema? After I parse a data with the schema, I don't want to allow changing the ID.
No description
5 Replies
Scott Trinh
Scott Trinh5mo ago
You can make an intersection with a readonly object that just contains the id and a separate object that contains all of the other properties, I think. Although, in practice, I think readonly is fine since it's rare that consumers of data mutate the data directly rather than copying, but there are certainly use cases for direct mutation.
Scott Trinh
Scott Trinh5mo ago
import { z } from "zod";

const Rest = z.object({
name: z.string(),
});

const Id = z.object({
id: z.string().optional()
}).readonly();

const Schema = z.intersection(Rest, Id);

declare const data: z.output<typeof Schema>;
// ^?{ name: string; } & Readonly<{ id?: string | undefind }>;

data.name = "beep";

// Error:
data.id = "boop";
import { z } from "zod";

const Rest = z.object({
name: z.string(),
});

const Id = z.object({
id: z.string().optional()
}).readonly();

const Schema = z.intersection(Rest, Id);

declare const data: z.output<typeof Schema>;
// ^?{ name: string; } & Readonly<{ id?: string | undefind }>;

data.name = "beep";

// Error:
data.id = "boop";
ramblings
ramblings5mo ago
z.intersection schemas loses utilities such as Pick and Omit. I tried doing Rest.merge(Id) but merge can't take ZodReadOnly objects. Thank you for your help though, I just wanted extra type safety but I can live without it.
Scott Trinh
Scott Trinh5mo ago
Yeah, if it was me, I'd just throw readonly on the whole object and fix any mutations-in-place with more idiomatic copies or override the defintion with a big comment justifying why i was doing it.