I want to validate that the user has letters and numbers
Example:
"pedro123" -> true
"peter" -> false
I have this:
function isUserNameValid(username) {
const res = /(?!.*[\.\-\_]{2,})^[a-zA-Z0-9]{3,24}$/.exec(username);
const valid = !!res;
return valid;
}
You were already there. Use .test instead of .exec
So:
function isUserNameValid(username) {
return /(?!.*[\.\-\_]{2,})^[a-zA-Z0-9]{3,24}$/.test(username);
}
By the way, this also states that username must be between 3 and 24 characters long.
You can use several regexps:
function isUserNameValid(username) {
const hasLetter = /[a-zA-Z]/.test(username);
const hasNumber = /[0-9]/.test(username);
const isValid = hasLetter && hasNumber;
return isValid;
}
console.log(isUserNameValid("pedro123"))
console.log(isUserNameValid("peter"))
Try:
const isUserNameValid = function (userName) {
let regExp = /^(?=.*[a-zA-Z])(?=.*[0-9])/;
return regExp.test(userName);
};
Related
Question: I am trying to validate email endings in an array
let input = 'test#gmail.com' // This is grabbed dynamically but for sake of explanation this works the same
let validEndings = ['#gmail.com', '#mail.com', '#aol.com'] //and so on
if(input.endsWith(validEndings)){
console.log('valid')
}else{
console.log('invalid')
}
I can get this to work when validEndings is just a singular string e.g let validEndings = '#gmail.com'
but not when its in an array comparing multiple things
You can solve the problem with regex. Example:
const input = 'test#gmail.com';
const validEndingsRegex = /#gmail.com$|#mail.com$|#aol.com$/g;
const found = input.match(validEndingsRegex);
if (found !== null) {
console.log('valid')
} else {
console.log('invalid')
}
You can achieve this by using Array.some() method which tests whether at least one element in the array passes the test implemented by the provided function. It returns true if, in the array, it finds an element for which the provided function returns true; otherwise it returns false.
Live Demo :
let input = 'test#gmail.com';
let validEndings = ['#gmail.com', '#mail.com', '#aol.com'];
const res = validEndings.some(endingStr => input.endsWith(endingStr));
console.log(res);
Say, I have a string to be replaced:
let searches = ['gone', 'go', 'run']
let s = 'go went gone-go'
const lookup = {
'go': '(go)',
'gone': '[gone]',
}
for (let key of searches) {
s = s.replaceAll(key, lookup[key])
}
console.log(s)
And I get (go) went [(go)ne]-(go).
Assume s can be any string with some words from lookup keys, and lookup values won't necessarily have consistent patterns. searches is the variable from outside inputs.
If I change orders in searches to, for example, ['go', 'gone', 'run'], result becomes (go) went (go)ne-(go).
The result I'm expecting is (go) went [gone]-(go), so that longer ones are replaced first, and won't be replaced by later matches.
I did come up with a solution that replacing values from lookup to uuid first, iterating from longer keys to shorter ones, then replace uuid back with corresponding values. Of course, this is rather stupid and inefficient:
let searches = ['go', 'gone', 'run']
let s = 'go went gone-go'
const lookup = {
'go': '(go)',
'gone': '[gone]',
}
const uuid = () => Date.now().toString(36) + Math.random().toString(36).substring(2) // pseudo uuid for quick demo. src: https://stackoverflow.com/a/44078785/17954892
let uuidKeys = {}
Object.keys(lookup).forEach(k => uuidKeys[k] = uuid()) // uuidKeys = {'go': 'random1', 'gone': 'random2'}
let uuids = Object.values(uuidKeys) // uuids = ['random1', 'random2']
let uuidValues = {}
Object.keys(lookup).forEach((k, i) => uuidValues[uuids[i]] = lookup[k]) // uuidValues = {'random1': '(go)', 'random2': '[gone]'}
searches.sort((a, b) => b.length -a.length) // searches = ['gone', 'run', 'go']
for (let key of searches) {
s = s.replaceAll(key, uuidKeys[key]) // s = 'random1 went random2-random1'
}
for (let key of searches.map(i => uuidKeys[i])) {
s = s.replaceAll(key, uuidValues[key]) // s = '(go) went [gone]-(go)'
}
console.log(s)
I then thought about loop-split the string by searches, then replace and record the index that's processed, and finally join the list back to string. However, I cannot find a nice way to implement it without expensive Array methods (flat, splice, etc.) in for-loops.
Is there an elegant/efficient way to achieve the result?
You can do this by using a regular expression with the g flag with replace, passing a callback function as the replacement; the function then picks the appropriate replacement based on what matched.
For instance:
let searches = ["gone", "go", "run"];
let s = "go went gone-go";
const lookup = {
"go": "(go)",
"gone": "[gone]",
};
let rex = new RegExp(searches.map(escapeRegex).join("|"), "g");
s = s.replace(rex, match => lookup[match]);
console.log(s);
...where escapeRegex escapes any charactesr in the search strings that have special meaning in regular expressions; see this question's answers for possible implementations.
Live Example:
function escapeRegex(string) {
return string.replace(/[-\/\\^$*+?.()|[\]{}]/g, '\\$&');
}
let searches = ["gone", "go", "run"];
let s = "go went gone-go";
const lookup = {
"go": "(go)",
"gone": "[gone]",
};
let rex = new RegExp(searches.map(escapeRegex).join("|"), "g");
s = s.replace(rex, match => lookup[match]);
console.log(s); // "(go) went [gone]-(go)"
Note: The order of the strings in the searches array matters. If you put "go" before "gone", it'll match first:
function escapeRegex(string) {
return string.replace(/[-\/\\^$*+?.()|[\]{}]/g, '\\$&');
}
let searches = ["go", "gone", "run"];
// Note −−−−−−−−^
let s = "go went gone-go";
const lookup = {
"go": "(go)",
"gone": "[gone]",
};
let rex = new RegExp(searches.map(escapeRegex).join("|"), "g");
s = s.replace(rex, match => lookup[match]);
console.log(s); // "(go) went (go)ne-(go)"
If you always want the longest one to have the highest precedence, and you can't control the contents of the input array, you could sort it prior to using it:
function escapeRegex(string) {
return string.replace(/[-\/\\^$*+?.()|[\]{}]/g, '\\$&');
}
let searches = ["go", "gone", "run"];
// Note −−−−−−−−^
let s = "go went gone-go";
const lookup = {
"go": "(go)",
"gone": "[gone]",
};
let rex = new RegExp(
searches.sort((a, b) => b.length - a.length)
.map(escapeRegex)
.join("|"),
"g"
);
s = s.replace(rex, match => lookup[match]);
console.log(s); // "(go) went [gone]-(go)"
I'm passing an object using the jQuery $.post method. When it's loaded using the $.get method, I need that the message field of the object is parsed correctly. I was able to remove the equal "=" sign and the "&" sign, but if it's a long message it will contain the plus "+" sign and the commas are not displayed correctly. Here is the console output i get:
{user: "demo", message: "Lorem+ipsum+dolor+sit+amet%2C+consectetur+adipisci…+qui+officia+deserunt+mollit+anim+id+est+laborum."}
message: "Lorem+ipsum+dolor+sit+amet%2C+consectetur+adipiscing+elit%2C+sed+do+eiusmod+tempor+incididunt+ut+labore+et+dolore+magna+aliqua.+Ut+enim+ad+minim+veniam%2C+quis+nostrud+exercitation+ullamco+laboris+nisi+ut+aliquip+ex+ea+commodo+consequat.+Duis+aute+irure+dolor+in+reprehenderit+in+voluptate+velit+esse+cillum+dolore+eu+fugiat+nulla+pariatur.+Excepteur+sint+occaecat+cupidatat+non+proident%2C+sunt+in+culpa+qui+officia+deserunt+mollit+anim+id+est+laborum."
user: "demo"
__proto__: Object
The commas are replaced by the %2C character and the spaces are replaced from the plus sign.
How to obtain the text without this signs?
here is a function I write for this scope, but it's not working at all.
function parseData(data){
var params = {}
params.data = data.split("&");
params.result = {};
for(var i = 0; i < params.data.length; i++) {
var item = params.data[i].split("=");
params.result[item[0]] = item[1];
}
return params.result;
}
Use this one :
function parseData(data){
return decodeURIComponent((data + '').replace(/\+/g, '%20'));
}
Use this function hope it will work for you :
export function parseData(data) {
url = decodeURI(url);
if (typeof url === 'string') {
let params = url.split('?');
let eachParamsArr = params[1].split('&');
let obj = {};
if (eachParamsArr && eachParamsArr.length) {
eachParamsArr.map(param => {
let keyValuePair = param.split('=')
let key = keyValuePair[0];
let value = keyValuePair[1];
obj[key] = value;
})
}
return obj;
}
}
When I run this code:
var foundUrlString = savedPage.match( /og:url.*="(http.*\.com)/i );
var foundUrl = foundUrlString[1];
I get an error if there are no matches on the page:
Result of expression 'foundUrlString' [null] is not an object
How can I get "false" when there are no matches instead of this error?
Going off of what you have, you could add a "truthy" check on the second line:
var foundUrlString = savedPage.match( /og:url.*="(http.*\.com)/i );
var foundUrl = !!foundUrlString && foundUrlString[1];
That will leave foundUrl either as a matched string or false.
Check null to print false or true.
var savedPage = '';
var foundUrlString = savedPage.match( /og:url.*="(http.*\.com)/i );
var foundUrl = foundUrlString == null ? false : true;
console.log(foundUrl );
Here is an example with try and catch which may help you:
function regex(savedPage) {
try {
var foundUrlString = savedPage.match(/og:url.*="(http.*\.com)/i);
return foundUrlString[1];
} catch (error) {
return false;
}
}
var savedPage1 = '<link property="og:url" content="http://test.com/test">';
console.log('savedPage1',regex(savedPage1));
var savedPage2 = '<link content="http://test.com/test">';
console.log('savedPage2',regex(savedPage2));
You need to understand what's the purpose of String.prototype.match. The function match will return an array with the whole set of matched groups in your regexp. So, if you want to validate a string, the best way is using the function RegExp.prototype.test.
Use the function RegExp.prototype.test from regexp:
let savedPage = "EleFromStack";
console.log(/og:url.*="(http.*\.com)/i.test(savedPage));
I need your your help,
For some strange reason, when my var str is set to "OTHER-REQUEST-ASFA" the matched key comes back as "ASF" as opposed to "ASFA"
How can I get the returned output key of "ASFA" when my str is "OTHER-REQUEST-ASFA"
function test() {
var str = "OTHER-REQUEST-ASFA"
var filenames = {
"OTHER-REQUEST-ASF": "ASF",
"OTHER-REQUEST-ASFA": "ASFA",
"OTHER-REQUEST-ASFB": "ASFB",
"OTHER-REQUEST-ASFC": "ASFC",
"OTHER-REQUEST-ASFE": "ASFE"
}
for (var key in filenames) {
if (str.indexOf(key) != -1) { alert(filenames[key]) }
}
}
You could switch from
str.indexOf(key)
to
key.indexOf(str)
function test() {
var str = "OTHER-REQUEST-ASFA",
filenames = {
"OTHER-REQUEST-ASF": "ASF",
"OTHER-REQUEST-ASFA": "ASFA",
"OTHER-REQUEST-ASFB": "ASFB",
"OTHER-REQUEST-ASFC": "ASFC",
"OTHER-REQUEST-ASFE": "ASFE"
},
key;
for (key in filenames) {
if (key.indexOf(str) != -1) {
console.log(filenames[key]);
}
}
}
test();
To answer why it's not working as you want...
You've got:
str.indexOf(key)
This checks for the first instance of key in str.
So in your loop, key first equals OTHER-REQUEST-ASF which is part of OTHER-REQUEST-ASFA, so the condition is true.
However, to do what you want to do, if you know the pattern is always going to be OTHER-REQUEST-XYZ, the easiest way is to use split():
str.split('-')[2]
will always return the last section after the last -
cause "OTHER-REQUEST-ASFA".indexOf("OTHER-REQUEST-ASF") will not return -1, so it will show "ASF"
You can also use static method Object.keys() to abtain array of keys
var test = () =>{
var str = "OTHER-REQUEST-ASFA"
var filenames = {
"OTHER-REQUEST-ASF": "ASF",
"OTHER-REQUEST-ASFA": "ASFA",
"OTHER-REQUEST-ASFB": "ASFB",
"OTHER-REQUEST-ASFC": "ASFC",
"OTHER-REQUEST-ASFE": "ASFE"
}
Object.keys(filenames).forEach(x => {
if ( x.indexOf(str) !== -1)
console.log(filenames[str]);
});
}
test();