URL Slug Regex
Validates a URL-friendly slug made of lowercase letters and digits, with single hyphens allowed only between word groups (no leading, trailing, or doubled hyphens).
Regex Pattern
^[a-z0-9]+(?:-[a-z0-9]+)*$Pattern Breakdown
Hover over a token to see what it does.
| Token | Meaning |
|---|---|
| ^ | Anchors the match to the start of the string |
| [a-z0-9]+ | One or more lowercase letters or digits forming the first word |
| (?: | Start of a non-capturing group for repeated hyphen-separated words |
| -[a-z0-9]+ | A literal hyphen followed by one or more lowercase letters/digits |
| )* | Closes the group and allows it to repeat zero or more times |
| $ | Anchors the match to the end of the string |
Detailed Explanation
What it does
This pattern matches strings that follow the classic 'slug' convention used in blog and product URLs: lowercase alphanumeric words joined by single hyphens, such as my-blog-post-123. It rejects uppercase letters, spaces, underscores, and malformed hyphen placement.
Why it works
The pattern requires an initial run of lowercase letters/digits, then allows the non-capturing group (?:-[a-z0-9]+)* to repeat for each additional hyphen-joined word. Because each repetition of the group demands a hyphen immediately followed by at least one alphanumeric character, two consecutive hyphens or a hyphen at the start/end of the string can never satisfy the pattern, and the ^/$ anchors ensure the whole string is checked.
Common use cases
- Validating slugs before saving them to a database or using them in a route
- Auto-generating and then verifying SEO-friendly URLs from article titles
- Enforcing consistent slug formatting in a CMS or static site generator
- Sanitizing user-submitted permalink overrides
Edge cases
- A single word with no hyphens, like hello, is valid since the repeating group is optional
- Purely numeric slugs like 2026-07-10 are valid because digits are allowed alongside letters
- Double hyphens (hello--world) are correctly rejected because the group requires an alphanumeric character right after each hyphen
- Leading or trailing hyphens (-hello, hello-) are rejected since the string must start and end with an alphanumeric character
Limitations
- Does not transliterate or normalize accented/Unicode characters — that must happen before validation
- Does not enforce a maximum length, so extremely long slugs will still pass
- Cannot detect semantically reserved slugs (e.g. 'admin' or 'api') — that needs an application-level check
Interactive Tester
Edit the pattern or text below — matching runs live in your browser.
Test Cases
Editable — add your own inputs to see if they pass.
| Input | Expected | Result | |
|---|---|---|---|
| Pass | |||
| Pass | |||
| Pass | |||
| Pass | |||
| Pass | |||
| Pass | |||
| Pass | |||
| Pass |
Language Variants
Production-ready examples in 12 languages.
const slugRegex = /^[a-z0-9]+(?:-[a-z0-9]+)*$/;
console.log(slugRegex.test('my-blog-post-123')); // trueCommon Mistakes
Using [a-z0-9-]+ without structure, which allows leading, trailing, and doubled hyphens like --hello--
Fix: Use the (?:-[a-z0-9]+)* structure so every hyphen is guaranteed to be followed by an alphanumeric character
Forgetting to lowercase and trim the source string before generating a slug
Fix: Normalize the input (toLowerCase, trim, replace spaces with hyphens) before running it through the validation regex
Not stripping accented characters, producing slugs like 'caf-au-lait' that lose information
Fix: Transliterate Unicode characters (e.g. e with an accent becomes e) before slugifying
Performance Notes
- The pattern has no ambiguous overlap between the initial class and the repeated group, so it runs in linear time with no catastrophic backtracking risk
- Anchors (^ and $) let the engine reject invalid strings immediately without scanning the whole input for a partial match
- For slugifying large batches of titles, generate the slug first (lowercase, replace spaces) and use this regex only as a final validation gate
Browser Compatibility
| Engine | Supported | Notes |
|---|---|---|
| Chrome | Yes | — |
| Firefox | Yes | — |
| Safari | Yes | — |
| Edge | Yes | — |
| Node.js | Yes | — |
Work with this pattern
Take this expression further — test it against your own data, adapt it in the builder, or read up on the syntax behind it.
Regex Tester
Test a regular expression against sample text and see every match highlighted live.
Regex Generator
Build a pattern by clicking blocks — no syntax memorisation required.
Regular Expressions Guide
What regex is, how the syntax works, and the mistakes that trip people up.
Regex Cheat Sheet
Every token, quantifier, and assertion on one printable page.
Python Regex Guide
The re module end to end — search, match, findall, groups, and substitution.
Regex Pattern Library
100+ ready-to-use patterns for email, URLs, dates, IPs, and more.