I have implemented Facebook login using passport in my application.
app.get('/index', ensureAuthenticated, function(req, res){
res.render('/', {});
});
function ensureAuthenticated(req, res, next) {
if (req.isAuthenticated()) { return next(); }
res.redirect('/')
}
In the front end I am using backbone for single page application, without a hash in url.
Backbone.history.start({ pushState: true });
When I enter /index in the url, it's redirecting to login page (which is perfect). But, when I enter /#index, indexView is loading.
What is the proper way to handle such conditions? I want to avoid having the user access any of my view, with or without hash in url, if they are not logged in.
Related
I need to redirect to login page if there any network issue or service down happen. I done a code which is redirect to login page. The problem is it redirect only the body. The layout is still there I want to show complete login page. Meaning I need to remove the layout. I have tried using window.location.href however I would like to use res.redirect('/');
> var isAuthenticated = function (req, res, next) {
var now = moment();
// logger.error("Tracing here", {"name":"routeshandler.js", "operation" : "isAuthenticated" });
// if user is authenticated in the session, call the next() to call the next request handler
// Passport adds this method to request object. A middleware is allowed to add properties to
// request and response objects
if (req.isAuthenticated()) {
if (req.user && global.users[req.user.userid]) {
global.users[req.user.userid].lastactive = now;
}
return next();
}
req.logout();
// if the user is not authenticated then redirect him to the login page
res.redirect('/');
res.end();
}
But it is load only the body. the layout is still there. How can I reload the complete page?
I quite don't understand the difference between these two:
app.get('*', function(req, res, next) {
next();
//ROUTE 1
});
app.get('*', function(req, res) {
res.redirect('/some');
//ROUTE 2
});
app.get('/some', function(req, res) {
res.send("success");
//ROUTE 3
});
When I try making request to ROUTE 1, I get response success but ROUTE 2 doesn't show this response. Why is that?
What I want to do is:
Every request should pass from ROUTE 1 and the control should be handled to a SPECIFIC route, which I would write in it ROUTE if-else statement (not like next(), which sends control to next MATCHING route).
For example:
app.get('*', function(req, res, next) {
if(x==y){
//call SPECIFIC route 3
} else {
// call SPECIFIC route 4 (another route)
//ROUTE 1
});
I tried to do it with redirect but it's not working.
Thank you.
EDIT:
Routes would be: /checkIfSession exists. I would use express-session to check if user's username exists or not in session.
If exists, I want to send control to if otherwise else.
Assume the requests are:
http://198.168.43.200:3000/checkIfSession
http://198.168.43.200:3000/some
(I will call only 1st request).
EDIT 2: I tried following but I don't get any response when I request:
app.use(function (req, res, next) {
if(2==2){
res.redirect("/session");
} else {
res.end("else");
}
});
app.get("/session", function(req, res){
res.write("session");
res.end();
});
app.get("/some", function(req, res){
res.write("some");
res.end();
});
Request: /some
I suppose if you want your routes to go through some kind of authentication first you can use middleware in your routes.
Below is sample code:
app.get('/some', checkSession, function(req, res) {
res.send("success");
});
// this is the middleware function
function checkSession(req, res, next) {
// do your checking here
if (x===y) {
next();
//continue users access to protected API
}
else {
res.redirect('/');
// redirect user to the default login page
}
}
In this above example there are 2 Cases
Case1:
x === y as from your given example I'am assuming users is logged in, so when the user is accessing /some section of your website he will receive Success from the server.
This is the use of your next() function i.e. it continues the execution of that api or sends the data whatever the user is requesting. Something similar to continue in your programming.
Case2:
x!==y now this will be the case where user is not authenticated or logged in and user is still trying to access the /some section of your website. In this case user will be redirected to login page of whatever you have designed for your website for him/her to re-enter his/her credentials.
Here your redirect function redirects the user without sending any data. Something similar to the break.
I'm using express framework , Lets say I have this line in the API :
router.delete('/user',(req, res) => { //deleting...}
Now I want that only an Admin will be able to access this line.
In the rest of the code there are lines that only user can access like :
router.put('/post')
And lines only admin can access like:
router.put('/killDB)
what is the best way (tokens, sessions or something like that) that will be able to help me differenitate between the two?
Use password to authenticate users and then check if the user is an admin. And then simply add password logic to your route. Below I will provide my code where I just check if user is logged in (it was enough for me)
router.get('/delete', isLoggedIn, function (req, res) {
Page.collection.drop();
var page = new Page();
page.save(function (err) {
if(err) throw err;
res.redirect('/admin');
});
});
// render login form
router.get('/login', function (req, res) {
res.render('login',{ message: req.flash('error'), layout: null});
});
// process the login form
router.post('/login', passport.authenticate('local-login', {
successRedirect : '/admin', // redirect to the secure profile section
failureRedirect : '/login', // redirect back to the signup page if there is an error
failureFlash : true // allow flash messages
}));
router.get('/logout', function(req, res) {
req.logout();
res.redirect('/');
});
function isLoggedIn(req, res, next) {
// if user is authenticated in the session, carry on
if (req.isAuthenticated())
return next();
// if they aren't redirect them to the home page
res.redirect('/');
}
You can use the connect-roles package to authorize your users, and then route them to those URL's which they are allowed to access.
You can also opt for passport.js, however it is more or like a authentication package where as the connect-roles just aims at to provide only the "authorization" part. And this package works well with Express.
Once you implement this package, you can use the "role" attribute to check the user's authorization level and allow them to perform their respective actions.
For eg.,
if (req.user.role === 'admin') {
router.put('/killDB)
}
You can check out the package here: https://www.npmjs.com/package/connect-roles
Hope this helps!
On the front page of my app, the user can register an account and then login. It is expressed as a login and register button on the front page which then show the appropriate form when either are clicked.
I would like to replace the two buttons with a log out button if the user is already logged in but I need to inform the client of that first.
In my index.js, I am serving static html like so
app.use(express.static('public'));
I thought I could then do the following
app.get('/', function(req, res) {
// inform the client if req.user isn't null
});
but the callback is never called
I have found a solution.
In my index.js, I have this
app.get('/isloggedin', function(req, res) {
res.json({ loggedin: (req.user != null) });
});
And then I can just send a get request for /isloggedin and handle the result
$.get('/isloggedin', {}, function(data) {
if (!data.loggedin) {
// remove logged-in only elements
} else {
// remove logged-out only elements
}
});
Umm! i guess there would be a login/register form so there has to be two routes one with .get() and second one with .post():
app.get('/', function(req, res) {
// This is for navigation to the home page
}).post('/', function(req, res){
// inform the client here about the req.body.user
});
and i guess you have set up this:
app.use(bodyParser.urlencoded({extended:true})); // for "formurlencoded"
app.use(bodyParser.json()); // for "application/json"
if not then you have to load this module require('body-parser') first and require it only if you are using express 4.
I copy pasted the app passport-local on my app,
The fun is I can log in users, but I can't make them logout,
app.get('/logout', function(req, res){
req.logout();
res.redirect('/');
});
this is not doing nothing, nothing on the logfiles, and I I have its a link to /logout
this is the main route examples
app.get('/page1', function(req, res){
res.render('page1', {user: req.user});
});
app.get('*', function(req,res){
res.render('root', {user: req.user});
});
Why the logout its not working ????
Apparently this is a known problem:
Why is PassportJS in Node not removing session on logout
The thread mentioned above suggests to use req.session.destroy() instead.
It would be nice to have some feedback from the Passport team directly.
This is still an issue.
What I did was to use req.session.destroy(function (err) {}); on the server side and on the client side, whenever they logout:
const logout = () => {
const url = '/users/logout'
fetch(url)
setTimeout(function () {
location.reload(); }, 500);
That way, when refreshing the page, the user is without session. Just make sure you are redirecting to the correct page if no one is authenticated.
Not the best approach, perhaps, but it works.