How to improve this Regular expression validation? - javascript

I tried to write a form validation for description textarea> of the users about their owns like he/she education or experience.
I wrote this Regex for this textarea, but I have a problem if user use above comma it's not allowed, for example if user written "House's", it's not allowing to write this comma '.
PWhich symbols may needed or predicate while users describe owns?
I used this Regex:
$descriptionValidation = "/^[a-zA-Z0-9\.\-\,\"\(\) ]+[a-zA-Z0-9\.\-\,\"\(\) ]*$/";

To match a whole string and require that the string only consist of alphanumeric characters and: dots, commas, single-quotes (also called apostrophes, but not "above commas"), double-quotes, left parentheses, right parentheses, spaces, and hyphens, use the following expression.
The ^ and $ metacharacters ensure that the characters span the entire length of the string. + means one or more of the any of the characters in the list. The "list" is technically called a "character class". a-z is the full range of letters and \d is the full range of numbers. - does have special meaning inside of a character class but only if it has a non-ranged expression on both sides of it. If you wish to prevent mistakes with hyphens inside of a character class, you can add a backslash to escape it or you can write the hyphen at the start or end of the character class OR you can write it next to a character range.
/^[a-z\d.,'"() -]+$/i
When declaring this pattern in php using single quotes, you will need to escape the single-quote in the character class.
$descriptionValidation = '/^[a-z\d.,\'"() -]+$/i';

Related

RegEx does not match my example

This RegEx could not find example string.
RegEx:
^ALTER\\sTABLE\\sADMIN_\\sADD CONSTRAINT \\s(.*)\\sPRIMARY KEY \\s(\(.*\))\\.([a-zA-Z0-9_]+)
Example:
ALTER TABLE ADMIN_ ADD CONSTRAINT PK_ADMIN_ PRIMARY KEY (RECNOADM);
I am new to regex and tried to complete my RegEx at REGEX101.COM but with no success. What am I missing?
Djorjde
^\s*ALTER\s+TABLE\s+ADMIN_\s+ADD\s+CONSTRAINT\s+(.+)\s+PRIMARY\s+KEY\s*\((.+)\)\s*;\s*$
This expression will match the SQL statement you used as an example, capturing PK_ADMIN_ in the first group and RECNOADM in the second.
My suggestion is to use always \s+ to match the spaces (\s* when they are optional, like the leading or trailing spaces), unless they have to be exactly a single space.
So let's break the regex down:
^ Marks the beginning of the line. You don't want the line to match if there's anything else before.
\s* Optional leading spaces.
ALTER\s+TABLE\s+ADMIN_\s+ADD\s+CONSTRAINT This will match ALTER TABLE ADMIN_ ADD CONSTRAINT, regardless of the spacing used.
\s+(.+)\s+ Then, the next space-bound word(s)** will be captured into the first group. You're accepting any character here! Maybe you could want to restrict that to \w+ or the like. Unless you accept an empty group, use the + closure (i.e., one or more), not the * one (i.e., zero or more)
PRIMARY\s+KEY Matches the sequence PRIMARY KEY, again, regardless of the spacing.
\s*\((.+)\) This will capture anything inside the parentheses as the PK in the second capture group.
\s* Means that it can be optionally preceded by an arbitrary number of spaces (although they are optional. They are in SQL if I recall correctly)
\(...\) You have to escape the parentheses because they are characters to match, no special characters of the regex.
(.+) Here you capture (between unescaped parentheses) everything between the (escaped) parentheses into a capture group. The second one in this case.
\s*;\s* The sentence has to end with a semicolon, optionally preceded and/or succeeded by any spaces.
$ Marks the end of the line.
In case you want to accept more than one sentence in the same line, you'd remove the ^ and $ zero-width delimiters.
About the escaping, the easiest way here is to simply double every backslash in the expression you built in the editor: ^\\s*ALTER\\s+TABLE\\s+ADMIN_\\s+ADD\\s+CONSTRAINT\\s+(.+)\\s+PRIMARY\\s+KEY\\s*\\((.+)\\)\\s*;\\s*$ However, there are context and/or languages where a more complex escaping may be needed (e.g., the Linux shell)
** Note that in 4, the inner expression .+ will take as many characters as possible, as long as the remaining parts also match the string. This is because the closures are by default greedy, meaning that the engine will try to match the longest string possible. That means that, for instance, this entry will match: ALTER TABLE ADMIN_ ADD CONSTRAINT PK_ADMIN_ OR *WHATEVER* YOU "WANT" TO PUT HERE! PRIMARY KEY (RECNOADM);, capturing PK_ADMIN_ OR *WHATEVER* YOU "WANT" TO PUT HERE! in the first group. Hence the importance of restricting the set of accepted characters ;)
Have you tried the following?
^ALTER\sTABLE\sADMIN_\sADD\sCONSTRAINT\s((.*))\sPRIMARY\sKEY\s\((.*)\);
I am wrapping two separate blocks through () in order to identify from the Regex the values inserted if you need to access them too.
In your regex there are few issues with white spaces (mixing up white spaces with \s and the white space should be \s not \s)
In JavaScript you only need to escape backslashes that are part of escape sequences when you're composing a regexp from a string, e.g.:
var r = new RegExp('\\d');
console.log(r.test('2'));
But the additional \ is not part of the regexp and you don't need it when using the literal syntax (or regexp101):
var r = /\d/;
console.log(r.test('2'));

regular expression incorrectly matching % and $

I have a regular expression in JavaScript to allow numeric and (,.+() -) character in phone field
my regex is [0-9-,.+() ]
It works for numeric as well as above six characters but it also allows characters like % and $ which are not in above list.
Even though you don't have to, I always make it a point to escape metacharacters (easier to read and less pain):
[0-9\-,\.+\(\) ]
But this won't work like you expect it to because it will only match one valid character while allowing other invalid ones in the string. I imagine you want to match the entire string with at least one valid character:
^[0-9\-,\.\+\(\) ]+$
Your original regex is not actually matching %. What it is doing is matching valid characters, but the problem is that it only matches one of them. So if you had the string 435%, it matches the 4, and so the regex reports that it has a match.
If you try to match it against just one invalid character, it won't match. So your original regex doesn't match the string %:
> /[0-9\-,\.\+\(\) ]/.test("%")
false
> /[0-9\-,\.\+\(\) ]/.test("44%5")
true
> "444%6".match(/[0-9\-,\.+\(\) ]/)
["4"] //notice that the 4 was matched.
Going back to the point about escaping, I find that it is easier to escape it rather than worrying about the different rules where specific metacharacters are valid in a character class. For example, - is only valid in the following cases:
When used in an actual character class with proper-order such as [a-z] (but not [z-a])
When used as the first or last character, or by itself, so [-a], [a-], or [-].
When used after a range like [0-9-,] or [a-d-j] (but keep in mind that [9-,] is invalid and [a-d-j] does not match the letters e through f).
For these reasons, I escape metacharacters to make it clear that I want to match the actual character itself and to remove ambiguities.
You just need to anchor your regex:
^[0-9-,.+() ]+$
In character class special char doesn't need to be escaped, except ] and -.
But, these char are not escaped when:
] is alone in the char class []]
- is at the begining [-abc] or at the end [abc-] of the char class or after the last end range [a-c-x]
Escape characters with special meaning in your RegExp. If you're not sure and it isn't an alphabet character, it usually doesn't hurt to escape it, too.
If the whole string must match, include the start ^ and end $ of the string in your RegExp, too.
/^[\d\-,\.\+\(\) ]*$/

Regex to allow special characters

I need a regex that will allow alphabets, hyphen (-), quote ('), dot (.), comma(,) and space. this is what i have now
^[A-Za-z\s\-]$
Thanks
I removed \s from your regex since you said space, and not white space. Feel free to put it back by replacing the space at the end with \s Otherwise pretty simple:
^[A-Za-z\-'., ]+$
It matches start of the string. Any character in the set 1 or more times, and end of the string. You don't have to escape . in a set, in case you were wondering.
You probably tried new RegExp("^[A-Za-z\s\-\.\'\"\,]$"). Yet, you have a string literal there, and the backslashes just escape the following characters - necessary only for the delimiting quote (and for backslashes).
"^[A-Za-z\s\-\.\'\"\,]$" === "^[A-Za-zs-.'\",]$" === '^[A-Za-zs-.\'",]$'
Yet, the range s-. is invalid. So you would need to escape the backslash to pass a string with a backslash in the RegExp constructor:
new RegExp("^[A-Za-z\\s\\-\\.\\'\\\"\\,]$")
Instead, regex literals are easier to read and write as you do not need to string-escape regex escape characters. Also, they are parsed only once during script "compilation" - nothing needs to be executed each time you the line is evaluated. The RegExp constructor only needs to be used if you want to build regexes dynamically. So use
/^[A-Za-z\s\-\.\'\"\,]$/
and it will work. Also, you don't need to escape any of these chars in a character class - so it's just
/^[A-Za-z\s\-.'",]$/
You are pretty close, try the following:
^[A-Za-z\s\-'.,]+$
Note that I assumed that you want to match strings that contain one or more of any of these characters, so I added + after the character class which mean "repeat the previous element one or more times".
Note that this will currently also allow tabs and line breaks in addition to spaces because \s will match any whitespace character. If you only want to allow spaces, change it to ^[A-Za-z \-'.,]+$ (just replaced \s with a space).

Can it be done with regex?

Having the following regex: ([a-zA-Z0-9//._-]{3,12}[^//._-]) used like pattern="([a-zA-Z0-9/._-]{3,12}[^/._-])" to validate an HTML text input for username, I wonder if is there anyway of telling it to check that the string has only one of the following: ., -, _
By that I mean, that I'm in need of regex that would accomplish the following (if possible)
alex-how => Valid
alex-how. => Not valid, because finishing in .
alex.how => Valid
alex.how-ha => Not valid, contains already a .
alex-how_da => Not valid, contains already a -
The problem with my current regex, is that for some reason, accepts any character at the end of the string that is not ._-, and can't figure it out why.
The other problem, is that it doesn't check to see that it contains only of the allowed special characters.
Any ideas?
Try this one out:
^(?!(.*[.|_|-].*){2})(?!.*[.|_|-]$)[a-zA-Z0-9//._-]{3,12}$
Regexpal link. The regex above allow at max one of ., _ or -.
What you want is one or more strings containing all upper, lower and digit characters
followed by either one or none of the characters in "-", ".", or "_", followed by at least one character:
^[a-zA-Z0-9]+[-|_|\.]{0,1}[a-zA-Z0-9]+$
Hope this will work for you:-
It says starts with characters followed by (-,.,_) and followed and end with characters
^[\w\d]*[-_\.\w\d]*[\w\d]$
Seems to me you want:
^[A-Za-z0-9]+(?:[\._-][A-Za-z0-9]+)?$
Breaking it down:
^: beginning of line
[A-Za-z0-9]+: one or more alphanumeric characters
(?:[\._-][A-Za-z0-9]+)?: (optional, non-captured) one of your allowed special characters followed by one or more alphanumeric characters
$: end of line
It's unclear from your question if you wanted one of your special characters (., -, and _) to be optional or required (e.g., zero-or-one versus exactly-one). If you actually wanted to require one such special character, you would just get rid of the ? at the very end.
Here's a demonstration of this regular expression on your example inputs:
http://rubular.com/r/SQ4aKTIEF6
As for the length requirement (between 3 and 12 characters): This might be a cop-out, but personally I would argue that it would make more sense to validate this by just checking the length property directly in JavaScript, rather than over-complicating the regular expression.
^(?=[a-zA-Z0-9/._-]{3,12}$)[a-zA-Z0-9]+(?:[/._-][a-zA-Z0-9]+)?$
or, as a JavaScript regex literal:
/^(?=[a-zA-Z0-9\/._-]{3,12})[a-zA-Z0-9]+(?:[\/._-][a-zA-Z0-9]+)?$/
The lookahead, (?=[a-zA-Z0-9/._-]{3,12}$), does the overall-length validation.
Then [a-zA-Z0-9]+ ensures that the name starts with at least one non-separator character.
If there is a separator, (?:[/._-][a-zA-Z0-9]+)? ensures that there's at least one non-separator following it.
Note that / has no special meaning in a regex. You only have to escape it if you're using a regex literal (because / is the regex delimiter), and you escape it by prefixing with a backslash, not another forward-slash. And inside a character class, you don't need to escape the dot (.) to make it match a literal dot.
The dot in regex has a special meaning: "any character here".
If you mean a literal dot, you should escape it to tell the regex parser so.
Escape dot in a regex range

regular expression using javascript

I have a regular expression ^(?=.*?[A-Za-z])\S*$ which indicates that the input should contain alphabets and can contain special characters or digits along with the alphabets. But it is not allowing white spaces since i have used \S.
Can some one suggest me a reg exp which should contain alphabets and it can contain digits or special characters and white space but alphabets are must and the last character should not end with a white space
Quite simply:
^(?=.*?[A-Za-z]).*$
Note that in JavaScript . doesn't match new lines, and there is no dot-all flag (/s). You can use something like [\s\S] instead if that is an issue:
^(?=[\s\S]*?[A-Za-z])[\s\S]*$
Since you only have a single lookahead, you can simplify the pattern to:
^.*[A-Za-z].*$
Or, even simpler:
[A-Za-z]
[A-Za-z] will match if it finds a letter anywhere in the string, you don't really need to search the rest from start to end.
To also validate the last character isn't a whitespace, it is probably easiest to use the lookahead again (as it basically means AND in regular expressions:
^(?=.*?[A-Za-z]).*\S$

Categories

Resources