colinhacks / zod

TypeScript-first schema validation with static type inference
https://zod.dev
MIT License
32.65k stars 1.13k forks source link

[Feature] Add phone number parsing #3378

Open GustavoOS opened 4 months ago

GustavoOS commented 4 months ago

The idea is using a zod schema like z.string().phone() and let parse any phone number format valid world-wide.

colinhacks commented 4 months ago

Super hard to do correctly. If someone wants to make a specific API proposal here, I'm all ears. But this is the kind of thing that's almost impossible to make everyone (or even most people) happy.

maurer2 commented 4 months ago

Validation for E.164 phone numbers could be added via regex. It should validate most, albeit not all e164 numbers, correctly. See documentation from Twilio/Sendgrid: https://www.twilio.com/docs/glossary/what-e164#regex-matching-for-e164

Cheers

iffa commented 4 months ago

You can achieve this easily yourself with something like the following, and using libphonenumber-js at least somewhat guarantees good results:

import parsePhoneNumber from "libphonenumber-js";
import * as z from "zod";

/**
 * Zod schema that validates a phone number using `libphonenumber-js`.
 * Attempts to parse the provided value with a default country of `FI`.
 *
 * If the phone number is valid, the schema transforms the phone number into
 * an international format (e.g. `+358401234567`).
 */
export const zPhoneNumber = z.string().transform((value, ctx) => {
  const phoneNumber = parsePhoneNumber(value, {
    defaultCountry: "FI",
  });

  if (!phoneNumber?.isValid()) {
    ctx.addIssue({
      code: z.ZodIssueCode.custom,
      message: "Invalid phone number",
    });
    return z.NEVER;
  }

  return phoneNumber.formatInternational();
});
jimmi-joensson commented 2 weeks ago

At react-international-phone they recommend using google-libphonenumber for validation. Maybe Zod can rely on that for integrated phone validation as well?