Regex for a string with at least a letter and no repeating dash I had a problem a few days back and had to find a regex that matches a string that:


Contains only letters in the alphabet [a-z0-9-] so lowercase latin letters, numbers 0 to 9, and the dash character
Must contains at least a letter [a-z]
Must not contains repeating dashes. abc-def-gh is ok but not abc--def
The size of the string must be between 1 and 10 characters


I came up with:

^(?=[a-z0-9-]*[a-z][a-z0-9-]*)(?:[a-z0-9]|[-](?![-])){1,10}$


A little explanation:


(?=[a-z0-9-]*[a-z][a-z0-9-]*) lookahead to find if the string contains at least a letter
(?:[a-z0-9]|[-](?![-])){1,10} A non capturing group (not really important to capture or not I believe) with two parts, that must be between 1 and 10 chars


[a-z0-9] any letter in the alphabet I want
[-](?![-] a dash then a negative lookahead to see if there is no dash following



Here is a list of strings that should not match:

#should not match
-
1
1-
-1
aaaaaaaaaaaaaaaaa
11111
2a2--af
a2a--22


And a list of string that should match:

#should match
a
a-
-a
a-2
a2a
2a2-
a2a-2a2
a-b-c-d
a123213232
123213213a
a12321322a


HERE you can find an online regex tester to play with it.

All improvements, remarks, feedbacks is welcome. My guts is telling me the lookahead can be improved but I did not find how. Also, I'm not even sure the lookahead is needed at all. I'm eager to improve my regex skill so if you have any alternative method also I'd be really glad to know.
The lookahead (?=[a-z0-9-]*[a-z][a-z0-9-]*) can be reduce to:

(?=.*[a-z])


because the allowed characters are defined after in the non capturing group.

The dash [-] doesn't need to be inside a character class, - is enough

Then, the whole regex becomes:

^(?=.*[a-z])(?:[a-z0-9]|-(?!-)){1,10}$