·9 min read·Regular Expressions

Regex for Phone Number Validation: International Patterns

Learn regex patterns for validating US, UK, international, and E.164 phone numbers. Understand formatting variations, country codes, and when to use regex vs libraries.

Try our free Regex Tester

Test phone number regex patterns with real-time highlighting and explanations.

Open Tool

The Challenge of Phone Number Validation

Phone number validation is one of the hardest problems in form validation. Unlike email addresses, which follow a single RFC standard, phone numbers have no universal format. There are over 200 countries, each with its own numbering plan, varying digit lengths, and multiple acceptable display formats.

Consider just the United States. A single phone number can be written in at least six common ways:

  • 555-123-4567
  • (555) 123-4567
  • 555.123.4567
  • 5551234567
  • +1 555 123 4567
  • 1-555-123-4567

Now multiply that by every country in the world. UK numbers have a different length depending on whether they are mobile or landline. German numbers vary from 3 to 12 digits after the area code. Indian mobile numbers are 10 digits, but landlines can be 8. Some countries like Ivory Coast recently added a digit to all numbers, changing their validation rules overnight.

This complexity means that a single regex pattern cannot perfectly validate all phone numbers worldwide. But regex can still be incredibly useful for validating specific formats, sanitizing input, and catching obviously invalid entries. The key is knowing which pattern to use for which situation. You can test all the patterns in this article live using our Regex Tester.

US Phone Number Patterns

US phone numbers follow the North American Numbering Plan (NANP): a 3-digit area code followed by a 7-digit subscriber number. The country code is +1. Here are regex patterns from simple to comprehensive:

Pattern 1: Digits Only (10 digits)

/^\d{10}$/

The simplest pattern. Matches 5551234567 and nothing else. Useful when you strip all formatting before validation.

Pattern 2: Dashes Format (xxx-xxx-xxxx)

/^\d{3}-\d{3}-\d{4}$/

Matches the most common US format: 555-123-4567. Too strict for real-world use since users type numbers in many ways.

Pattern 3: Parentheses Format ((xxx) xxx-xxxx)

/^\(\d{3}\)\s?\d{3}-\d{4}$/

Matches (555) 123-4567 and (555)123-4567. The \s? makes the space after the closing parenthesis optional.

Pattern 4: Flexible US Pattern (Recommended)

/^\+?1?[-.\s]?\(?\d{3}\)?[-.\s]?\d{3}[-.\s]?\d{4}$/

This is the recommended pattern for US phone numbers. It handles all common formats:

  • \\+?1? — Optional +1 country code
  • [-.\s]? — Optional separator (dash, dot, or space)
  • \\(?\\d{3}\\)? — Area code with optional parentheses
  • \\d{3}[-.\\s]?\\d{4} — Subscriber number with optional separator

This matches 555-123-4567, (555) 123-4567, +1 555 123 4567, 5551234567, and more. Test it in our Regex Tester to see it in action.

UK and European Formats

European phone numbers have different structures than US numbers. Here are patterns for the most common European formats:

UK Mobile Numbers

/^(\+44|0)7\d{9}$/

UK mobile numbers start with 07 (domestic) or +447 (international), followed by 9 digits. This pattern matches 07911123456 and +447911123456. The total length is 11 digits domestically or 13 with the country code.

UK Landline Numbers

/^(\+44|0)[1-9]\d{8,9}$/

UK landlines start with area codes like 020 (London) or 0161 (Manchester). The total length varies between 10 and 11 digits because some area codes are shorter with longer subscriber numbers.

German Numbers

/^(\+49|0)[1-9]\d{6,13}$/

German phone numbers are notoriously variable in length. Area codes range from 2 to 5 digits, and subscriber numbers range from 3 to 8 digits. Mobile numbers start with 015, 016, or 017. This wide range makes regex validation less precise.

French Numbers

/^(\+33|0)[1-9]\d{8}$/

French numbers are consistently 10 digits domestically (starting with 0) or 12 internationally (starting with +33). Mobile numbers start with 06 or 07. France has one of the more regex-friendly numbering plans in Europe.

International E.164 Format

E.164 is the international standard for phone number formatting, defined by the International Telecommunication Union (ITU). It is the format you should use when storing phone numbers in a database because it is globally unambiguous.

The E.164 format has simple rules:

  • 1. Starts with a + sign
  • 2. Followed by the country code (1-3 digits)
  • 3. Followed by the subscriber number
  • 4. No spaces, dashes, or other separators
  • 5. Maximum total length: 15 digits (not counting the +)
  • 6. Minimum total length: 7 digits (some small countries)
// E.164 regex pattern
/^\+[1-9]\d{6,14}$/

// Examples that match:
// +14155552671    (US)
// +442071234567   (UK)
// +81312345678    (Japan)
// +4930123456     (Germany)
// +33123456789    (France)
// +5511999887766  (Brazil)

Breaking down the pattern: \\+ requires the plus sign, [1-9] requires the first digit to be non-zero (no country code starts with 0), and \\d{6,14} allows 6 to 14 more digits for a total of 7 to 15.

E.164 is the recommended storage format because it eliminates ambiguity. The number 020 7123 4567 could be interpreted differently depending on which country you are calling from, but +442071234567 is unambiguous worldwide. Accept any format in your forms, but convert to E.164 before storing. You can use our String Encoder/Decoder to inspect the character codes if you suspect encoding issues with phone number input.

Building a Flexible Pattern

In practice, you often need a single regex that accepts multiple international formats without being country-specific. Here is a practical approach that balances flexibility with reasonable validation:

// Flexible international phone pattern
/^\+?[0-9]{1,4}?[-.\s]?\(?[0-9]{1,3}\)?[-.\s]?[0-9]{1,4}[-.\s]?[0-9]{1,4}[-.\s]?[0-9]{1,9}$/

This pattern is deliberately permissive. It handles optional country codes, optional separators (dashes, dots, spaces), and optional parentheses around area codes. It accepts most real-world phone number formats while still rejecting obviously invalid input like single digits or alphabetic strings.

A better approach for production code is to strip and validate:

function validatePhone(input) {
  // 1. Strip all non-digit characters except leading +
  const hasPlus = input.trim().startsWith("+");
  const digits = input.replace(/\D/g, "");

  // 2. Validate digit count
  if (digits.length < 7 || digits.length > 15) {
    return { valid: false, error: "Phone number must be 7-15 digits" };
  }

  // 3. Convert to E.164 for storage
  const e164 = hasPlus ? `+${digits}` : digits;

  return { valid: true, e164, digits };
}

// Usage:
validatePhone("(555) 123-4567");
// { valid: true, e164: "5551234567", digits: "5551234567" }

validatePhone("+1-555-123-4567");
// { valid: true, e164: "+15551234567", digits: "15551234567" }

validatePhone("+44 20 7123 4567");
// { valid: true, e164: "+442071234567", digits: "442071234567" }

This strip-then-validate approach is more robust than trying to match every possible format with a single regex. The regex only needs to count digits, which is simple and reliable. You can format the number for display separately using a formatting function.

For form input, consider using an input mask that automatically formats as the user types. This gives users visual feedback and ensures consistent formatting. Test your patterns with various inputs using our Regex Tester to verify they match what you expect and reject what they should. You can also use our JSON Formatter to validate API payloads containing phone number fields.

When to Use Libraries Instead

Regex is great for simple, single-country validation and quick input sanitization. But for serious international phone number handling, dedicated libraries are significantly better. Here is when to switch:

Google libphonenumber

The gold standard for phone number validation. Originally built for Android, it is available in JavaScript (google-libphonenumber), Python (phonenumbers), Java, and more:

// JavaScript with google-libphonenumber
const PNF = require("google-libphonenumber");
const phoneUtil = PNF.PhoneNumberUtil.getInstance();

try {
  const number = phoneUtil.parse("+442071234567", "GB");

  console.log(phoneUtil.isValidNumber(number));        // true
  console.log(phoneUtil.getNumberType(number));         // FIXED_LINE
  console.log(phoneUtil.getRegionCodeForNumber(number)); // GB
  console.log(
    phoneUtil.format(number, PNF.PhoneNumberFormat.E164)
  ); // +442071234567
  console.log(
    phoneUtil.format(number, PNF.PhoneNumberFormat.NATIONAL)
  ); // 020 7123 4567
  console.log(
    phoneUtil.format(number, PNF.PhoneNumberFormat.INTERNATIONAL)
  ); // +44 20 7123 4567
} catch (e) {
  console.error("Invalid phone number:", e.message);
}

libphonenumber provides capabilities that regex simply cannot match:

  • Country-specific validation — Knows the valid area codes and digit lengths for every country.
  • Number type detection — Identifies mobile, landline, toll-free, premium rate, and VoIP numbers.
  • Automatic formatting — Formats numbers in national, international, and E.164 styles.
  • Region detection — Determines which country a number belongs to from the digits alone.
  • Regular updates — Phone numbering plans change frequently. libphonenumber is updated regularly with new data.

The tradeoff is bundle size. The full libphonenumber library is about 300 KB gzipped because it contains metadata for every country. For client-side use, consider the lighter libphonenumber-js package (about 150 KB with full metadata or 45 KB with minimal metadata).

When Regex Is Still the Right Choice

Use regex when you only need to validate one or two specific country formats, when bundle size is critical, when you just need basic digit count validation after stripping formatting, or for quick input sanitization before sending to a backend that handles full validation. For everything else, use libphonenumber.

Frequently Asked Questions

What is the best regex for phone numbers?
There is no single best regex because formats vary by country. For US numbers, use /^\+?1?[-.\s]?\(?\d{3}\)?[-.\s]?\d{3}[-.\s]?\d{4}$/ which handles common formats. For international numbers in E.164 format, use /^\+[1-9]\d{6,14}$/. For production apps handling multiple countries, use Google's libphonenumber library instead.
Should I validate phone format or just digits?
Strip all non-digit characters (except the leading +) first, then validate the digit count. This is more reliable than matching every possible format. A US number should have 10 digits (or 11 with country code 1). International numbers range from 7 to 15 digits. Validate the stripped digits, then format for display separately.
What is the E.164 format?
E.164 is the international phone number standard defined by the ITU. It starts with + followed by the country code and subscriber number, with no spaces or separators. Maximum length is 15 digits. Examples: +14155552671 (US), +442071234567 (UK). Use E.164 for database storage because it is globally unambiguous.
Can regex validate if a phone number exists?
No. Regex can only validate format — whether a number has the right digit count and pattern. To check if a number is actually assigned to a real phone line, you need a validation API service like Twilio Lookup, NumVerify, or Abstract API that queries carrier databases in real time.

Test Your Phone Regex Now

Paste any regex pattern and test it against phone numbers with real-time highlighting, match groups, and explanations. Free and private.

Open Regex Tester

Related Tools