Using the key of string enum using nativeEnum?
So I have been using this Country enum and wondering if we can validate the keys instead of the value?
https://gist.github.com/evolkmann/740d24889c509c08484a8ff72af5dd64
Currently, the nativeEnum validates the value and could not find an option to make it validate the key instead.
Currently using this as I cannot flip the enum just for Zod
z.string().length(2).regex(/^[A-Z]{2}$/, 'Invalid country code').nullable()
This how I did it
z.enum(Object.keys(Enum) as [keyof typeof Enum, ...(keyof typeof Enum[]])
Let me know if you have a better idea than this.
Hi, @hls-app. I'm Dosu, and I'm helping the Zod team manage their backlog. I'm marking this issue as stale.
Issue Summary:
- You were looking for a way to validate the keys of a string enum using
nativeEnumin Zod. - You shared a workaround using regex for country codes.
- User @nabil-rady suggested using
z.enum(Object.keys(Enum) as [keyof typeof Enum, ...(keyof typeof Enum[])]). - You acknowledged this suggestion with a thumbs-up, indicating it might be helpful.
Next Steps:
- Please let me know if this issue is still relevant to the latest version of Zod. If so, you can keep the discussion open by commenting here.
- Otherwise, this issue will be automatically closed in 7 days.
Thank you for your understanding and contribution!
Zod's z.nativeEnum and z.enum only validate enum values, not keys—there's no built-in way to validate enum keys directly with these methods (docs, code). Your current regex-based workaround is totally reasonable for ISO country codes, but if you want to ensure the string is actually a key of your Country enum, you can use a custom refinement for type safety:
import { z } from "zod";
import { Country } from "./your-enum-file";
const countryKeySchema = z
.string()
.refine((val) => Object.keys(Country).includes(val), {
message: "Invalid country code",
})
.nullable();
This checks that the input is one of the enum's keys at runtime. If you ever can generate a list of keys at build time, you could use z.enum(Object.keys(Country) as [keyof typeof Country]), but that's not always ergonomic with TypeScript enums.
Let me know if this solves your problem—if so, feel free to close the issue!
To reply, just mention @dosu.
How did I do? Good | Irrelevant | Incorrect | Verbose | Hallucination | Report 🐛 | Other