I have created a login button that is supposed to take the Array stored in the browser local storage, read each item and check if the username and password written in the input boxes are inside the Array).
The Array is successfuly taken from storage, but when the code is supposed to read it and compare the items to the input for some reason it always says the input isn't in the Array. How could I fix that? Code follows:
const loginForm = document.getElementById("loginForm");
const loginButton = document.getElementById("loginButton");
const loginError = document.getElementById("loginError");
const registerForm = document.getElementById("registerForm");
const registerButton = document.getElementById( "registerButton");
const registerError = document.getElementById("registerError");
/*HERE IS THE PROBLEMATIC LOGIN BUTTON*/
loginButton.addEventListener("click", (e)=> {
e.preventDefault();
const username = loginForm.username.value;
const password = loginForm.password.value;
const user ={ username, password};
let checkUser =[];
checkUser = JSON.parse(localStorage.getItem("registred users"));
let checkUserInfo = checkUser.includes(user, 0);
if( checkUserInfo == true){
alert("Login sucessful!");
location.reload();
} else {
loginError.style.opacity = 2;
}
})
registerButton.addEventListener("click", (e)=> {
e.preventDefault();
const registerUsername = registerForm.registerUsername.value;
const registerPassword = registerForm.registerPassword.value;
const confirmPassword = registerForm.confirmPassword.value;
const registerEmail = registerForm.registerEmail.value;
const userData = {registerUsername, registerPassword};
let registredUserData = [];
if(registerPassword.length > 8 && registerPassword.match(/[a-z]+/) && registerPassword.match(/[A-Z]+/) && registerPassword.match(/[0-9]+/) && registerPassword.match(/[$##&!]+/) && registerPassword === confirmPassword && registerEmail.match(/[#/]+/ ) ){
registredUserData = JSON.parse(localStorage.getItem("registred users"));
registredUserData.push(userData);
localStorage.setItem("registred users",JSON.stringify(registredUserData));
location.reload();
} else {
registerError.style.opacity = 2;
}
})
You are comparing two objects for equality. Even though you use includes, it still checks if the value you put in is equal to an element in the array.
If you need to check for both username and password, loop through the array with some and see if the properties of one of the objects are equal to the provided input.
let checkUserInfo = checkUser.some(u => u.username === user.username && u.password === user.password);
Also keep in mind that this type of client side authentication is dummy auth for demonstration purposes only; it will not function as real authentication for any service.
You shouldn't use the includes to search for a similar object in an array of objects. You have to search one by one. You should use a filter type method like find() or some().
Your code would be something like:
/*HERE IS THE PROBLEMATIC LOGIN BUTTON*/
loginButton.addEventListener("click", (e)=> {
e.preventDefault();
const username = loginForm.username.value;
const password = loginForm.password.value;
const user ={ username, password};
let checkUser =[];
checkUser = JSON.parse(localStorage.getItem("registred users"));
let checkUserInfo = checkUser.some(item => item.username === user.username && item.password === user.password);
if( checkUserInfo == true){
alert("Login sucessful!");
location.reload();
} else {
loginError.style.opacity = 2;
}
})
Obs.: This is a extremely bad way to store password data. You should use some library that uses hash like bcryptjs.
Related
I am using local storage to store username and password
I am getting null on active user after this line of code, I dont know why
console.log("I am the Active user: " + activeUser);
const menuChannelIcon = $(".menu-channel-icon");
const bellIcon = $(".bell-btn");
const uploadButtonIcon = $(".upload-btn");
const signInMainPageIcon = $(".signInMainPage");
const signUpMainPageIcon = $(".signUpMainPage");
const signOutMainPageIcon = $(".signOutMainPage");
const videoSectionMainPage = $(".video-section");
const signin = () => {
console.log("signin button clicked")
if (localStorage.getItem("formData")) {
// as long as you are getting items from the local storage... do..
JSON.parse(localStorage.getItem("formData")).forEach((data) => {
let x = $("#signEmail").val();
let z = $("#signinPassword").val();
if (data.email == x && data.pwd == z) {
isLogged = true;
activeUser = localStorage.getItem(email);
console.log("I am the Active user: " + activeUser);
menuChannelIcon.show();
bellIcon.show();
uploadButtonIcon.show();
signInMainPageIcon.hide();
signUpMainPageIcon.hide();
signOutMainPageIcon.show();
singIn_formContainer.hide();
videoSectionMainPage.show();
console.log("You are LOGGED");
}
});
}
};
Edit: email and pwd are set during signup
Answer posted by Barmar in the comments:
localStorage.getItem("email")
Alternative answer:
Shouldn't the active user be x when the email and password match something from formData? Why are you getting the active user from local storage?
I have two arrays in JavaScript. One contains usernames and one contains passwords. I want to create a loop that checks what position (i) the username is in - in the 'approvedUsernames' array - that was inputted by the user, and takes that same 'i' value in the 'approvedPasswords' array and picks the value that was found. then compare the two. If they match, a successful login happens, if not it is unsuccessful
Please see existing Arrays and the code i have already written below
any help greatly appreciated
i hope this was clear enough i had trouble wording it :)
James
EDIT: I KNOW THIS IS A VERY INSECURE WAY TO STORE PASSWORDS IT IS JUST TEMPORARY TO TEST THE LOGIN ALGORITHM. THE FINAL VERSION WILL DEFINITELY BE USING PHP+SQL DATABASE
Arrays:
approvedLogins = ['JamesLiverton', 'SamW'] approvedPasswords = ['password', 'coding']
Code:
function login(){
var username = document.getElementById('usernameField').value
var password = document.getElementById('passwordField').value
for (i = 0; i < approvedLogins.length; i++) {
if (username == approvedLogins[i].username && password == approvedPasswords[i].password) {
alert('Login Sucessful')
return
}
else {
alert('Login Unsucessful')
return
}
}
}
First, if you're planning on doing this, I have a feeling that you don't know much about security. I suggest you look into third party authentication (which, if you're asking this kind of question, might be out of your skill level, but still). At the very least, consider encrypting your user's password, with a salt (look up what a salt is).
With that said, you can do this.
function login() {
const username = document.getElementById('usernameField').value
const password = document.getElementById('passwordField').value
alert(isValidLogin(username, password) ? 'Login successful' : 'Login failed')
}
// create a separate function for checking validity, so it's easier
// to refactor/reimplement later, if need be.
function isValidLogin(username, password) {
const usernameArray = ['name1', 'name2', ... 'nameN']
const passwordArray = ['pw1', 'pw2', ... 'pwN']
const usernameIndex = usernameArray.findIndex(item => item === username)
return usernameIndex !== -1 && passwordArray[usernameIndex] === password
}
let approvedLogins = ['JamesLiverton', 'SamW']
let approvedPasswords = ['password', 'coding']
function login(){
var username = document.getElementById('usernameField').value
var password = document.getElementById('passwordField').value
let index = approvedLogins.indexOf(username)
if (password === approvedPasswords[index]) {
alert('Login Sucessful')
} else {
alert('Login Unsucessful')
}
}
<input type="text" id="usernameField" placeholder="username" /><input type="text" id="passwordField" placeholder="password" />
<button onclick="login()">login</button>
Check this example:
var approvedLogins = ['JamesLiverton', 'SamW'];
var approvedPasswords = ['password', 'coding'];
function login(username) {
if (approvedLogins.includes(username)) {
var matchedPassword = approvedPasswords[approvedLogins.indexOf(username)];
console.log(matchedPassword);
} else {
console.log("Username not found in array!");
}
}
It checks if the Username provided in the login() parameter, is found in the array. If it's inside the array, then it gets the password relative to the position of the username within that array. For example, "SamW" would be "coding".
I hope this helps.
I have been working on a project where we can store login info so that once a user registers, the data gets saved in the localStorage object. I have mentioned some javascript code to show that:
var user = document.getElementById("user");
var pass = document.getElementById("pass");
var email = document.getElementById("email");
var user2 = document.getElementById("user2");
var pass2 = document.getElementById("pass2");
function register() {
localStorage.setItem("username", user.value);
localStorage.setItem("password", pass.value);
localStorage.setItem("email", email.value);
document.getElementById("id01").innerHTML = "Registration successful";
}
function login() {
var checkuser = localStorage.getItem("username");
var checkpass = localStorage.getItem("password");
if (checkuser === user2.value && checkpass === pass2.value) {
document.getElementById("demo").innerHTML = "You are now logged in.";
} else {
document.getElementById("demo").innerHTML = "Incorrect username and password";
}
}
In the javascript code mentioned above, i have used the localStorage object to store the values. I have stored the username in a user property, the password in a pass property and the email in an email property.
My question is: Is there any way where we can store the username, password and the email in one property(user property)?
Yes, you can do this by putting all the features you want in one object.
Example here
var user = document.getElementById("user");
var pass = document.getElementById("pass");
var email = document.getElementById("email");
var user2 = document.getElementById("user2");
var pass2 = document.getElementById("pass2");
var user = {
email:email,
pass:pass,
//.. other properties
}
then you can set like this
localStorage.setItam("USEROBJ",JSON.stringify(user));
When you want to call this you should use like
var user = JSON.parse(localStorage.getItam("USEROBJ"));
By the way you can read this
Storing Objects in HTML5 localStorage more detail about you question
You can store JSON as a string in localStorage property and then parse it
function setUser() {
localStorage.setItem('user', JSON.stringify(user));
}
function getUser() {
user = JSON.parse(localStorage.getItem('user'))
}
I have this function that is supposed to get referral codes from users. User gives a code and the referral code checked if it exists in the database then evaluated if
it does not match the current user, so that one should not refer himself and
it is a match with one of the codes in the database
This code however just does not find a match even if the code given is in the database. If the referral code matches the one of the current user, it works correctly and points that out i.e one cannot refer themselves.
But if the referral code is a match to that of another user which is how a referral system should work, it still says no match.
How can I remove this error
export const getID = functions.https.onCall(async(data, context) => {
const db = admin.firestore();
const usersSnapshot = await db.collection("user").get();
const allUIDs = usersSnapshot.docs.map(doc => doc.data().userID);
const userID = context.auth.uid;
const providedID = "cNx7IuY6rZlR9mYSfb1hY7ROFY2";
//db.collection("user").doc(providedID).collection("referrals").doc(userID);
await check();
function check() {
let result;
allUIDs.forEach(idFromDb => {
if (providedID === idFromDb && (idFromDb === userID)) {
result = "ownmatch";
} else if (providedID === idFromDb && (idFromDb !== userID)) {
result = "match";
} else {
result = "nomatch";
}
});
return result;
}
if (check() === "match") {
return {
message: `Match Found`,
};
} else if (check() === "ownmatch") {
return {
message: `Sorry, you can't use your own invite code`,
};
} else {
return {
message: `No User with that ID`
};
}
});
(This is not an answer, but a simple refactoring.)
This is what your code is currently doing (roughly, I didn't run it):
const resultMsgs = {
nomatch: 'No User With That ID',
ownmatch: 'Sorry, you can\'t use your own invite code',
match: 'Match Found',
}
function check(uids, providedId, userId) {
let result
uids.forEach(idFromDb => {
if (providedId !== idFromDb) {
result = 'nomatch'
return
}
if (userID === idFromDb) {
result = 'ownmatch'
return
}
result = 'match'
})
return result
}
export const getID = functions
.https
.onCall(async (data, context) => {
const userId = context.auth.uid
const providedId = 'cNx7IuY6rZlR9mYSfb1hY7ROFY2'
const db = admin.firestore()
const user = await db.collection('user').get()
const uids = user.docs.map(doc => doc.data().userId)
const checkResult = check(uids, providedId, userId)
return { message: resultMsgs[checkResult] }
})
(I removed the seemingly-spurious db collection operation.)
Your forEach is iterating over all of the uuids, but result will be set to whatever the last comparison was. Perhaps this is correct, but:
If you're looking for any match, this is not what you want.
If you're looking for all matches, this is not what you want.
If you're looking to match the last UUID, it's what you want, but an odd way to go about it.
So:
If you want any matches, use... ahem any form of an any function.
If you want all matches, use any form of an all function.
If you want the first match, then just check the first element.
If you want the complete set of comparisons then you'll need to use map instead of forEach, and handle each result appropriately, whatever that means in your case.
In any event, I'd recommend breaking up your code more cleanly. It'll be much easier to reason about, and fix.
I'm quite new to JS and am trying to check if a user or any value exists in a JavaScript object in real time, the goal is to implement this in Firebase in order to prevent user registration if that username has already been taken but I am doing it locally first because Im learning. This is what I have so far.
let input = document.getElementById('input')
let btn = document.getElementById('btn')
btn.disabled = false
let users = [
{
uname: "mark"
},
{
uname: "sarah"
},
{
...others uname
}
]
input.addEventListener('input', () => {
input.value = input.value.replace(regex, "")
check(input.value)
})
function check(val) {
users.forEach((item) => {
let uname = item.uname
if (uname.indexOf(val) > -1 && uname === val) {
console.log('That user name has been taken')
btn.disabled = true
} else {
console.log('Ok')
btn.disabled = false
}
})
}
The problem with that is when I typed in the input element Im getting both the if and else triggered and while (val) matches some key/value pairs the others won't and then I am able to use whatever username Im typing which is not what I want.
How can I solved this? Thanks.
You aren't checking to see if the username has been found.
function isUsernameAvailable (val) {
for (var i = 0; i < users.length; i++) {
var uname = users[i].name;
if (uname === val) {
console.log('That user name has been taken')
btn.disabled = true
return false; // the username is taken, we can stop checking
}
}
console.log('Ok')
btn.disabled = false
return true;
}
Also, forEach doesn't let you exit the loop early and you don't need to check every user after you found a match (if you find a match).