how to store signup data into redis with node.js - javascript

i want to store signup data it contains name and email and password.
i will store this data in mongodb like this
db.save({"name":"xxxx","email":"xxxxx","password":'xxxxxxxx'},function(err,result){});
when user login ,they surely give their email id or username with password so i will find this user exist in db or not by using like this
db.find({'email:'xxxxxxx','password':'xxxxxxxxx'},function(err,result){});
i have tried to do same in redis,by like this
db.hmset('key' name xxxxx email xxxx pass xxxxxx,function(){});
it is stored but how can i check email id usename already exist becz user will give email and password only.if i know key then only i can find that data.even if i know key i can get only data i could not be found data already exist ot not like mongodb
how can i solve this?

You could store your users both in a Set and a Hash for details.
You can then check in the Set if a user exists with: http://redis.io/commands/sismember

I think you should break things down into chunks instead of trying to do everything with one query. So, for example, to add a new user, first check if the user exists:
(My example assumes a Mongoose User Model has been defined)
User.findOne({$or : [{'email': req.body.email}, {'username': req.body.username}],
function(err, result) {
if (err) {next(err);}
if (result) {
// you found an existing user
res.send(309, {'message':'Error: User exists'});
} else {
// no user found
var user = new User({
'email': req.body.email,
'username': req.body.username,
'password': req.body.password,
'and-so-on': req.body.moredata
});
user.save(function(err){
if (err) {next(err);}
res.send(200, {'message':'User Registered Successfully'});
});
}
Honestly though, I wouldn't recommend writing a user authentication system from scratch, because it is pretty limiting in todays world of auth methods. I personally use Passport, because it gives you the ability to use multiple auth systems with your app, including Facebook, Twitter, and so on and so forth.

Related

confirming if an email already exists in a MongoDB database

I wrote this code to check if an email already exists in the database:
async store (req,res) {
const email = req.body.email;
let user = await User.findOne ({ email: email });
if (user) {
console.log('Already exist.')
};
(...)
}
But it's not working: I can store the info in the User collection but it's email is not verified.
I'm using Mongoose.
What I'm doing wrong?
You need to use exec() at the end to actually run the query:
let user = await User.findOne({ email: email }).exec();
Also, since you're using await, make sure the containing function is marked async.
I am limited in the information I can give you because you just say "It's not working". That doesn't tell me anything. Do you run it and nothing happens? Does it give you an error? People on this site don't like to hear the words: "it's not working".
You haven't described your use case, but if you're looking to avoid email collisions, using mongoose, when you define the object's schema, you can use the unique: true option. It will then reject any new or updated User that submits an already stored email.

Questions about how passport.js works. Specifically about user.id

I have no id field in my model ,doc, or record or whatever you want to call it. So how come done(null, user.id) works. I have an _id but no id. It looks like a passport object is being added to my session with the _id of the user in the DB, but how did it get the _id is it done automatically? in the docs it says
In this example, only the user ID is serialized to the session
how did it get the id and how did it get the user?
similar example in my code:
passport.serializeUser(function(user, done){
done(null, user.id)
});
passport.deserializeUser(function(id, done){
User.findById(id, function(err, user){
done(err, user);
})
});
What are the steps that it takes to get the user id?
I also have
passport.use("login", new LocalStrategy(function(username, password, done){
User.findOne({username : username}, function(err, user){
if(err){return done(err)}
if(!user){
return done(null, false, {message : "no User has that name"})
}
.......
Does the fact that I use passport.use() somehow connect the user in the DB to the passport methods.
Edit lets say I want to transfer the doc (user) via passports on the name field should I use user.name?
Also I'm not really sure about how serializing works
So how come done(null, user.id) works. I have an _id but no id.
You're using Mongoose, which adds a so-called virtual getter called id to documents, that returns the _id property. So in your case, both user.id and user._id will work (and will return the same).
Does the fact that I use passport.use() somehow connect the user in the DB to the passport methods.
Yes and no. The strategy that you pass to passport.use() implements the authentication process. You have to implement how the entered user information is validated against your database. In the example code, a call to User.findOne() is made, and the result of that call is checked against the supplied information ("Is username a valid username? If so, is password the password that belongs to this user?").
If the username and password match, the done callback is called with the user document as an argument. This document is what Passport will pass around to various other parts, for instance, to passport.serializeUser() (see below).
Also I'm not really sure about how serializing works.
Serializing is used to store information about the user in a "session object". This object should be able to uniquely identify the user. And since user.id (or user._id) is unique to a user, it's a good property to use.
That's where passport.serializeUser() comes in: it gets passed the user document, and it should provide Passport (by calling the callback function) a uniquely identifying piece of information about that user. Hence done(null, user.id).
The session object itself is also uniquely identified by a "session key". This key is stored in a HTTP cookie and sent to the browser when a user logged in successfully. When the browser opens another page on your website, it sends along that cookie, and using the session key in the cookie, the session object is retrieved from the "session store".
The session object contains the unique user id, but not the rest of the user information. So that's where passport.deserializeUser() comes in: it gets passed the id, and performs a database lookup to retrieve the full user document belonging to that id. This is what Passport will make available as req.user in your route handlers.
If all these steps are executed successfully (which isn't always the case, because cookies can expire, users can get deleted, etc), it will mean that Passport was able to positively identify the user, and they don't have to log in again. At least not until the session expires.

Quickblox: Change password of other user in Javascript

I'm doing a javascript app with Quickblox and I'm having one problem. I want to have a recover user password function and I have thought that an special user could change another one password. For that I'm using this:
var params = {password: newPassword, old_password: oldPassword };
QB.users.update(userId, params, function (error, response) {
//...
});
The function only works if I use the same userId of the user connected. I know that there is a forgot password function that is sending mails in Quickblox, however, I would like to not send any mail. What I can do? How can I use QB.users.update properly?
Lot of thanks in advance and best regards
You can't change a password of another users, only yours.
You can try to use admin account's credentials to change other user's password

How can I impersonate another user with Passport.js in Node?

Using Passport.js in Node, is there a way for me to allow one user to impersonate another? eg. as an Administrator in the application, I want to be able to log in as another user, without knowing their password.
Most simply, I would be satisfied if I could change the serialized user data (user ID) so when deserializeUser is called it will just assume the identity of the alternate user. I've tried replacing the value at req._passport.session.user and the value at req.session.passport.user but the net effect is just that my session seems to become invalid and Passport logs me out.
Passport provides a req.logIn method in case you want to do the authentication manually. You can use it to login any user even regardless of authentication.
Here's how you can use it. Have the Admin login normally, who'll have an isAdmin flag set.
Then place a middleware before passport.authenticate in your login route. This will login the new user based only on their username, if the currently logged in user isAdmin.
app.post('/login',
function forceLogin(req, res, next) {
if (!req.user.isAdmin) return next(); // skip if not admin
User.findOne({
username: req.body.username // < entered username
}, function(err, user) {
// no checking for password
req.logIn(user);
res.redirect('/users/' + user.username);
});
},
passport.authenticate('local'),
function(req, res) {
res.redirect('/users/' + req.user.username);
}
);
I have another way to impersonate, because:
I didn't want to mess with internals of authentication/passport like
session storage / logIn / etc. You must understand them really well
and also they are prone to change so I'd say it's not an option for
me.
Also, I'd like to still be able to tell if action is made from
superuser (impersonated) or normal user (not impersonated).
What I do is:
Have a route for user with superadmin role to impersonate, like /superadmin/impersonate?username=normaluser1 which sets req.user.impersonated.userid = normaluser1.userid
Then I have a middleware, which checks if user is superadmin and is impersonated:
if (req.user.isAdmin && req.user.impersonated) {
req.user.userid = req.user.impersonated.userid;
}
Also, I have found this to be a good article about user impersonation. Similar to my approach, and good for inspiration for building something similar.
The answer to your question is basically: no. The reason is this: the sessions library that is being used 99% of the time is signing the cookies, so if you tamper with the data the web server will reject it.
The way around this is to write your own passport authentication strategy that obviously doesn't do this, but I'm assuming you're talking about working with the built-in strategies here.

NodeJS Sessions

Hy and thanks in advance, So im working on a project, where part of the requirements, is to have a field where the user can insert is e-email, and then receive a custom url on his e-mail account, from there he can access the site. This is like the example of a "password-reset", where a custom url is generated and sent to u with a time-stamp validation. Im very new to nodejs, and my question here is if anyone has some type of guidlines to start doing this. My idea was to generate a sessionID, then generate a custom url, send the email, and then the users goes to the webpage. Im using express, and the whole site is already assembled, its just this feature tha is killing me! :(
I'm not sure what you need, but here is what I'd suggest (spoke about this on Reddit earlier).
// If you want the user to **have** to be a custom URL
req.param('userId', function(req, res, next) {
db.getUser(userId, function(e, usr) {
if (e) throw new Error(e);
req.user = usr;
});
});
req.all("*", function(req, res, next) {
if (!req.user) return res.redirect('/login');
});
// Rest of routes
req.get()
req.post()
That being said, you normally shouldn't have user login this way. Normally you would set the user in the session and validate it that way. Here's a good article on setting up sessions in Express.
If you do it this way, you would do something like this:
req.all("*", function(req, res, next) {
var userId = req.session('userid');
if (!userId) res.redirect('/login');
db.getUser(userId, function(e, usr) {
if (e) throw new Error(e);
if (!usr) return res.redirect('/login');
// Now the user is accessbile through its session
req.session.user = usr;
});
});
// Rest of routes
req.get()
req.post()
Password resetting requires what's called a nonce. This will be a small object in your DB that has a created date. You email them a link to your site that uses that nonce.
Whenever the route is hit that uses the password reset nonce, you look it up in the DB, verify it's new enough (within X hours or days), then give them access to the route that resets their password.
Your project requirements are pretty vague, so I'm not exactly sure what you need.
As of my understanding you want how to implement password reset functionality using expressjs.
Here are steps
1.
for forgot password
create an API
app.post('/forgotpassword',function(req,res){
var email = req.body.email;
// validation
// your custom url creation logic here
// someurl/:resetpasswordtoken
// store this in user data
// for this I'll suggest to use any unique string creation logic*
}
to show reset password page
app.get('/someurl/:resetpasswordtoken, function(req,res) {
//check token exist
// render the page for reset like current passwor,new password
}
Action for reset password
app.post('/someurl/:resetpasswordtoken , function(req,res){
var currentPwd = //get current pwd
var newPwd = //get new pwd
//check token
//then reset password for user
}

Categories

Resources