ToolSite

Common Regex Patterns Every Developer Should Know

Ready-to-use regex patterns for email, URL, phone, date, IPv4, hex color, and password validation. Copy, paste, test, and customize with our free regex tester.

By ToolSite5 min readguides

Why Keep These Handy

Most developers don't write regex often enough to memorize the patterns. You reach for regex every few weeks: a validation rule, a log parser, a find-and- replace that's too complex for the editor. Having common patterns ready to copy and adapt saves the 20-minute detour of looking up lookaheads and character classes.

Test every pattern in the Regex Tester before using it in production. Paste the pattern, paste sample input, and verify the matches. Every pattern below works in JavaScript, Python, and most PCRE-compatible engines.

Email Validation

A practical (not RFC-5322-compliant) pattern that catches the vast majority of valid email addresses without exotic false negatives:

\b[A-Za-z0-9._%+-]+@[A-Za-z0-9.-]+\.[A-Za-z]{2,}\b

Matches: user@example.com, first.last@sub.domain.co.uk Does not match: user@, @example.com, user@.com

Breakdown:

  • [A-Za-z0-9._%+-]+: one or more characters from the local part character set
  • @: literal at sign
  • [A-Za-z0-9.-]+: domain name (letters, digits, dots, hyphens)
  • \.: literal dot before TLD
  • [A-Za-z]{2,}: TLD with at least 2 letters
  • \b: word boundary at the end

Email validation via regex is imperfect by design. The only way to validate an email address completely is to send a message to it. Regex catches obvious typos and format errors at input time.

A stricter version that requires a more conventional format:

^[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,}$

The ^ and $ anchors require the entire string to be the email address. No surrounding text.

URL Extraction and Validation

Full URL validation with protocol, domain, path, and query:

https?:\/\/(www\.)?[-a-zA-Z0-9@:%._\+~#=]{1,256}\.[a-zA-Z0-9()]{1,6}\b([-a-zA-Z0-9()@:%_\+.~#?&//=]*)

Matches: https://example.com, http://sub.domain.co.uk/path?q=1

A simpler version for extracting URLs from text:

https?://[^\s]+

Matches any non-whitespace sequence starting with http:// or https://. This is adequate for log parsing and content extraction where precision is less important than recall.

To extract the domain from a URL:

https?://(?:www\.)?([^/\s]+)

The capturing group ([^/\s]+) grabs everything after the optional www. and before the first slash or whitespace.

US Phone Numbers

Handles common formats: (555) 123-4567, 555-123-4567, 555.123.4567, 5551234567:

\(?\d{3}\)?[-.\s]?\d{3}[-.\s]?\d{4}

Breakdown:

  • \(?: optional opening parenthesis
  • \d{3}: three digits (area code)
  • \)?: optional closing parenthesis
  • [-.\s]?: optional separator (hyphen, dot, or space)
  • \d{3}: three digits (exchange)
  • [-.\s]?: optional separator
  • \d{4}: four digits (subscriber number)

To also capture each part with groups:

\(?(\d{3})\)?[-.\s]?(\d{3})[-.\s]?(\d{4})

Replace with ($1) $2-$3 to normalize any format to (555) 123-4567.

International numbers require a different approach. The pattern above is US/NANP specific. For international, check the country code first, typically \+\d{1,3} followed by the local number.

Date Formats

ISO date (YYYY-MM-DD):

\d{4}-\d{2}-\d{2}

This matches any 4-digit, 2-digit, 2-digit pattern separated by hyphens. It matches 2026-02-30 (invalid date) and 9999-99-99 (nonsense). For basic sanity checks, validate the ranges:

(19|20)\d\d-(0[1-9]|1[0-2])-(0[1-9]|[12]\d|3[01])

Matches years 1900-2099, months 01-12, days 01-31. It still matches 2026-02-30 because it doesn't validate days per month. Full date validation needs a date parser, not regex.

US date (MM/DD/YYYY):

(0[1-9]|1[0-2])\/(0[1-9]|[12]\d|3[01])\/\d{4}

Matches: 08/05/2026, 12/31/2025. Does not match: 13/01/2026 (month 13 is invalid).

IP Address (IPv4)

Basic version matching any pattern of four octets:

\b(?:\d{1,3}\.){3}\d{1,3}\b

Matches: 192.168.1.1, 10.0.0.255, 999.999.999.999 (invalid IP)

A stricter version that validates the range 0-255 per octet:

\b((25[0-5]|2[0-4]\d|[01]?\d\d?)\.){3}(25[0-5]|2[0-4]\d|[01]?\d\d?)\b

Breakdown of the octet pattern (25[0-5]|2[0-4]\d|[01]?\d\d?):

  • 25[0-5]: matches 250-255
  • 2[0-4]\d: matches 200-249
  • [01]?\d\d?: matches 0-199 (optional leading 0 or 1, then digits)

Password Strength Patterns

At least 8 characters, one uppercase, one lowercase, one digit:

(?=.*[a-z])(?=.*[A-Z])(?=.*\d).{8,}

How it works: each (?=...) is a positive lookahead that checks a condition without consuming input. All three must pass before .{8,} matches the actual password.

At least 12 characters, one uppercase, one lowercase, one digit, one special:

(?=.*[a-z])(?=.*[A-Z])(?=.*\d)(?=.*[!@#$%^&*()_+\-=\[\]{}|;:',.<>?]).{12,}

The special character class [!@#$%^&*()_+\-=\[\]{}|;:',.<>?] covers common symbols. Adjust it to match your password policy.

A minimum-length-only pattern (no character class requirements):

.{8,}

Hex Color Codes

^#?([a-fA-F0-9]{6}|[a-fA-F0-9]{3})$

Matches: #1a2b3c, 1a2b3c, #abc, abc

The # is optional. Three-digit shorthand (#abc) expands to #aabbcc. Six-digit full form (#1a2b3c) matches exactly. The $ anchor prevents partial matches like #abcdefg.

Extracting Content Between Tags

HTML/XML tags (use an actual parser for production, regex for ad-hoc extraction):

<([^>]+)>(.*?)<\/\1>

Breakdown:

  • <([^>]+)>: opening tag, captures tag name in group 1
  • (.*?): content between tags (lazy, captured in group 2)
  • <\/\1>: closing tag, backreference to the same tag name from group 1

The lazy quantifier .*? stops at the first closing tag. The backreference \1 requires the closing tag to match the opening tag name.

Find and Replace with Groups

Capture parts of a match with parentheses and reference them in the replacement with $1, $2, etc.:

Pattern:    (\d{4})-(\d{2})-(\d{2})
Replacement: $2/$3/$1
Input:      2026-08-05
Output:     08/05/2026

This is how you reformat dates, phone numbers, and any structured text. Each parenthesized group captures one piece. The replacement string reorders them.

More examples:

# Extract domain from email
Pattern:    .+@(.+)
Replacement: $1
Input:      user@example.com
Output:     example.com

# Mask credit card (keep last 4)
Pattern:    (\d{4})[-\s]?\d{4}[-\s]?\d{4}[-\s]?(\d{4})
Replacement: $1-****-****-$2
Input:      1234-5678-9012-3456
Output:     1234-****-****-3456

Patterns for Log Parsing

Extract timestamp, level, and message from a log line:

^(\d{4}-\d{2}-\d{2} \d{2}:\d{2}:\d{2})\s+(INFO|WARN|ERROR)\s+(.+)$

Apache/Nginx common log format:

^(\S+)\s+\S+\s+\S+\s+\[([^\]]+)\]\s+"([^"]*)"\s+(\d{3})\s+(\d+)

Group 1: IP, Group 2: timestamp, Group 3: request, Group 4: status, Group 5: size.

Try it yourself: open the Regex Tester. Copy any pattern from this article and test it against sample input. Modify the pattern incrementally . add a quantifier, change a character class . and observe how the matches change in real time. Try the find-and-replace feature with the date format pattern to convert ISO dates to US format.

Related Reading