Express.js session undefined. Redis - node.js

Trying to get sessions set up with Redis. I have my Redis DB in a dokku container, linked to my app (also in a dokku container). I keep getting a session undefined.I've stripped things back to the bare minimum, also checked the order in which things are run. I still get an undefined.
I've read here 'session' is undefined when using express / redis for session store and Express js session undefined to no avail.
I shouldn't need to use cookie-parser, as expression-session has cookie stuff in it, and the docs say cookie-parser can cause problems with expression-session.
var express = require('express');
var session = require('express-session');
var redisStore = require('connect-redis')(session);
var bodyParser = require('body-parser');
var app = express();
app.set('port', (process.env.PORT || 5000));
var redisURL = 'redis://xxxxx:1234567#bar-redis-foo:6379';
var store = new redisStore({ url: redisURL });
app.use(session({
secret: 'ssshhhhh',
store: store,
saveUninitialized: true,
resave: true
}));
app.use(express.static(__dirname + '/public'));
app.use(bodyParser.json()); // to support JSON-encoded bodies
app.use(bodyParser.urlencoded({ // to support URL-encoded bodies
extended: true
}));
app.get('/', function(req, res, next) {
console.log(req.session); // Logs Undefined
res.send('Hello');
});

Check your redis connection and run again. Sample code is following line.
"use strict";
const express = require("express");
const bodyParser = require("body-parser");
const session = require("express-session");
const RedisStore = require("connect-redis")(session);
const app = express();
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({extended: false}));
app.use(session({
secret: "$kx(Fj$uB!Ug!#jCkguFmc6f7t<c-e$9",
resave: false,
saveUninitialized: true,
store: new RedisStore({
url: "redis://:********#pub-redis-12766.eu-central-1-1.1.ec2.redislabs.com:12766",
ttl: 5 * 60 // 5 minute (Session store time)
})
}));
app.use(function (request, response, next) {
let path = request.originalUrl;
if (request.session.user) {
request.session.reload(function (err) { //session expire time regenerate
if (!err) {
next();
} else {
response.redirect('/login');
}
});
} else {
if (path == '/login') {
next();
} else {
response.redirect('/login');
}
}
});
app.get('/', function(request, response) {
if (request.session.user) {
response.send(request.session.user);
} else {
response.redirect("/login");
}
});
app.get('/login', function(request, response) {
if (request.session.user) {
response.redirect("/");
} else {
request.session.user = {username: "halil"}; //custom key {user} and custom data {username: "halil"}
}
response.send('Login');
});
app.get('/logout', function(request, response) {
if (request.session.user) {
request.session.destroy();
response.redirect("/login");
} else {
response.redirect("/login");
}
});
app.listen(app.get('port'), function () {
console.log('App is working on port: ' + app.get('port'));
});

Related

Express-session. Session not persisting

Session data is not persisting for multiple calls. It is going through localhost. I have tried making the cookie not secure. Every call has the value of 1 and it never changes. Using latest versions of all packages. Please help me
// JS
$.ajax({
type: "GET",
url: "http://localhost:8080/test/",
success: (result) => { console.log(result); }
});
// NODE
var express = require("express");
var path = require('path');
var cors = require('cors');
var hash = require('object-hash');
var session = require('express-session');
var app = express();
app.use(express.json());
app.use(cors());
app.use(express.urlencoded({extended: true}));
app.use(session({
resave: false,
saveUninitialized: true,
secret: 'keepThemSweatyKidsAway',
cookie: {
secure: false
}
}));
app.use((req, res, next) => {
if (!req.session.views) {
req.session.views = 0;
}
req.session.views = req.session.views + 1;
next();
});
app.get('/test/', function (req, res, next) {
console.log(req.session);
res.send('you viewed this page ' + req.session.views + ' times');
});
app.listen(PORT, () => {
console.log("Server listening on: https://sweaty-kids.herokuapp.com:%s", PORT);
});

Protection csrf Nodejs Form

I have a little probleme with my Nodejs application. I want protect my forms with csrf token, but it's not work. I have an error like
ForbiddenError: invalid csrf token
POST http://localhost:3000/addfile 403 (Forbidden)
I want to create csrf token for all requests. I can create csrf token, but if I use the methods like : POST/PUT or DELETE it's not work.
I don't understand why I have this error. Thanks for yours answers.
app.js
var express = require("express");
var bodyParser = require("body-parser");
var mongoose = require('mongoose');
var fs = require('fs');
var path = require('path');
var logger = require('morgan');
var expressValidator = require('express-validator');
var csrf = require('csurf');
var session = require('express-session');
var passport = require('passport');
var PORT = 3000;
var config = require('./config/database');
var app = express();
// Connexion to MongoDb
mongoose.connect(config.database, function(err) {
if(err){
console.log(err);
}
else{
console.log("Connected to MongoDb");
}
});
// Middleware
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({extended: false}));
app.use(expressValidator());
app.set('views',path.join(__dirname, ''));
app.set('view engine','pug');
app.use(express.static(path.join(__dirname, '')));
app.disable('x-powered-by');
app.use(session({
name: 'SESS_ID',
secret: config.secret,
resave: true,
saveUninitialized: true,
cookie: {
secure: false,
httpOnly: true,
maxAge: 5*60*1000 } //15minutes*60sec*1000ms
//cookie: {secure: false} //https = true, http=false
}));
app.use(csrf());
app.use(passport.initialize());
app.use(passport.session());
require('./config/passport')(passport);
app.use(function(req, res, next) {
res.locals._csrf = req.csrfToken();
next();
});
app.use('/', require('./routes/fileRoutes'));
app.use('/', require('./routes/authRoutes'));
app.listen(PORT,function(){
console.log("Server started at the port " + PORT);
});
routes/fileRoutes.js
app.get('/',function(req,res){
File.find(function(err, files){
res.render('views/layout',{files:files});
});
});
app.post('/addfile',upload,function(req,res){
if (req.fileValidationError) {
return res.end("Error PDF");
} else {
for (var i = 0; i < req.files.length; i++)
{
var files = new File ();
files.fieldname= req.files[i].fieldname;
files.originalname= req.files[i].originalname;
files.encoding= req.files[i].encodin;
files.path= req.files[i].path;
files.save(function(err, data){
});
}
res.redirect('/');
}
});
layout.pug
form#uploadForm(enctype='multipart/form-data', action='/addfile', method='post')
input(type='hidden', name='_csrf', value=_csrf)
input(type='file', name='userPhoto', multiple='')
input(type='submit', value='Upload Image', name='submit')
input#random(type='text', name='random')
I see you have:
input(type='hidden', name='_csrf', value=_csrf)
What is the value for if you console.log(_csrf)? I also noticed you didn't put that one in quotes.

Express session is undefined when accessing from different route?

Im trying to implement infinite scroll. In my first route I load 5 elements from the data base and store the id of the last seen item. To load more data getNextHomeContent is called, but for some reason req.session.lastseen is undefined.
server.js
var express = require('express');
var session = require('express-session');
var app = express();
var mongoose = require('mongoose');
var logger = require('morgan');
var bodyParser = require('body-parser');
var cors = require('cors');
//imports database configuration
var databaseConfig = require('./config/database');
//defines route file to use
var router = require('./app/routes');
//connect to datbase
mongoose.connect(databaseConfig.url);
app.listen(process.env.PORT || 8080);
console.log("App listening on port 8080");
app.use(bodyParser.urlencoded({ extended: false })); // Parses urlencoded bodies
app.use(bodyParser.json()); // Send JSON responses
app.use(logger('dev')); // Log requests to API using morgan
app.use(cors());
app.use(session({
resave: true,
saveUninitialized: true,
secret: 'keyboard cat',
cookie: {
maxAge: 60000,
secure: false
}
}));
router(app);
And here is my controller for my routes in homeCtrl.js
exports.getHomeContent = function(req, res, next) {
req.session.lastseen = null;
homeContent.find({})
.sort({
"_id": -1
})
.limit(5)
.exec(function(err, content) {
if (err) {
res.send(err);
}
var last = content.slice(-1);
req.session.lastseen = last[0]._id;
console.log("lastseen first is " + req.session.lastseen);
res.json(content);
});
}
exports.getNextHomeContent = function(req, res, next) {
console.log("lastseen is " + req.session.lastseen);
homeContent.find({
"_id": { "$lt": req.session.lastseen }
})
.sort({
"_id": -1
})
.limit(5)
.exec(function(err, content) {
if (err) { res.send(err); }
console.log("WTF:" + content.slice(-1));
var lastitem = content.slice(-1);
req.session.lastseen = lastitem[0]._id;
res.json(content);
});
}
When get Home content runs, req.session.lastname is set to the ID of the last item. However req.session.lastitem becomes undefined when getNextHomeContent() runs. Can anyone help me with this?
Thanks!!

expressjs and socket.io session issues

I'm using express and socket.io and I want to share the express session between the two, with each one being on a different Node instance (localhost:3000 and localhost:8000). So far, express will create the session and the cookie created, however socket.io only picks up the 'io' cookie, not the express cookie. Can anyone show mw here my error is? I'm using express 4.x and socket.io 1.x.
Express config (localhost:3000):
var cookieParser = require('cookie-parser')
, session = require('express-session')
, bodyParser = require('body-parser')
, express = require('express')
, redis = require('redis')
, RedisStore = require('connect-redis')(session);
module.exports = function (app, passport) {
app.use(express.static('./static'))
app.use(cookieParser("thisismynewsecret"));
app.use(session({
//passport: passport,
name: 'sid',
//key: 'express.sid',
secret: 'thisismynewsecret',
saveUinitialized: true,
resave: true,
store: new RedisStore({ client: redis.createClient() }),
cookie: {
httpOnly: true,
path: '/',
secure: false
}
}));
app.use(passport.initialize());
app.use(passport.session());
// all environments
app.set('port', process.env.PORT || 3000)
app.set('views', './views')
app.set('view engine', 'jade')
app.use(bodyParser.json());
app.use(bodyParser.urlencoded());
app.use(require('method-override')());
app.use( require('express-subdomain-handler')({ baseUrl: 'localhost', prefix: 'myprefix', logger: true }) );
}
});
socket.io (localhost:8000):
var fs = require('fs');
var session = require('express-session');
var cookie = require('cookie');
var cookieParser = require('cookie-parser');
var sessionStore = require('connect-redis')(session);
var server = require('http').Server(function(req, res) {
fs.readFile(__dirname + '/views/JAMinit.html', function(error, content) {
if (error) {
res.writeHead(500);
res.end();
}
else {
res.writeHead(200, { 'Content-Type': 'text/html' });
res.end(content, 'utf-8');
}
});
}).listen(8000);
var io = require('socket.io')(server);
io.use(function(socket, next) {
var data = socket.handshake || socket.request;
if (data.headers.cookie) {
data.cookie = cookie.parse(cookieParser.signedCookie(data.headers.cookie, 'thisismynewsecret'));
console.log(data.cookie);
console.log('data.cookies ( %s )', JSON.stringify(data.cookie));
if (data.cookie.sid) {
data.sid = data.headers.cookie.sid;
sessionStore.get(data.headers.cookie.sid, function(err, session) {
data.session = session;
});
}
}
next();
});
Check out express.io, it combines express and socket.io and has automatic session support.

NodeJS + ExpressJS + RedisStore Session is undefined

I've gone through many questions with the same issue, but none of the various solutions have helped. I'm using Redis to store session in a clustered NodeJS+ExpressJS application, but the session is always undefined. Here's my Express setup:
var express = require('express'),
RedisStore = require('connect-redis')(express),
Config = require('./config/config'),
cluster = require("cluster"),
QueryManager = require('./service/query_manager'),
app = express();
// --- Index --- //
function renderSplash(req, res) {
res.render(...);
}
function renderIndex(req, res) {
res.render(...);
}
app.get('/', function(req, res) {
if(req.session.user === null) {
renderSplash(req, res);
} else {
renderIndex(req, res);
}
});
// --- Configuration ---//
//EJS
app.engine('.html', require('ejs').__express);
app.set('view engine', 'html');
app.set('views', __dirname + '/public');
app.configure(function() {
//Session
app.use(express.cookieParser());
app.use(express.session({
store: new RedisStore({
host: Config.redis.host,
port: Config.redis.port
}),
secret: 'Its a secret.',
cookie: { secure: true }
}));
app.use(validateRequest); //Ensures we're at www. to hit the LB
app.use(express.static(__dirname+'/public'));
app.use(express.compress);
app.use(app.router);
});
Even without using the Redis store, I'm getting the following error:
TypeError: Cannot read property 'user' of undefined
You'll have to instantiate the sessions before the routes.
var express = require('express'),
RedisStore = require('connect-redis')(express),
Config = require('./config/config'),
cluster = require("cluster"),
QueryManager = require('./service/query_manager'),
app = express();
app.use(express.cookieParser());
app.use(express.session({
store: new RedisStore({
host: Config.redis.host,
port: Config.redis.port
}),
secret: 'Its a secret.',
cookie: { secure: true }
}));
// --- Index --- //
function renderSplash(req, res) {
res.render(...);
}
function renderIndex(req, res) {
res.render(...);
}
app.get('/', function(req, res) {
if(req.session.user === null) {
renderSplash(req, res);
} else {
renderIndex(req, res);
}
});

Resources