Node.js request.body undefined - node.js

This is my server.js file:
var express = require("express");
var bodyParser = require("body-parser");
var controllers = require('./controllers');
var app = express();
controllers.init(app);
app.set('view engine', 'vash');
app.use(bodyParser());
app.use(express.static(__dirname + "/public"));
app.listen(5000);
This is my index.js code in controllers folder:
(function(controllers){
var homeController = require('./homeController');
controllers.init = function(app){
homeController.init(app);
};
})(module.exports);
This is my homeController.js code:
(function(homeController){
homeController.init = function(app){
app.get('/', function(req, res){
res.render('index', {title: "The Board"});
});
app.post("/", function(req, res){
console.log(req.headers);
console.log(req.body);
});
};
})(module.exports);
And this is my HTML:
#html.extend('layout', function(model){
#html.block('body', function(model){
#if(model.error){
<p class="text-error">Error occurred: #model.error</p>
}
<div class="row">
<form action="/" method="post">Enter your name:
<input type="text" name="userName" placeholder="..." />
<br>
<button type="submit">Submit</button>
</form>
</div>
})
})
When I make the post action req.body is undefined. How can I solve this problem?

Move app.use(bodyParser()); before route declaration controllers.init(app);

Related

update routing not working in node with ejs templating (404 not found error)

editUser.js which is loading the data correctly, however when clicking on update I am getting (404 not found error), not able to understand why update route is not getting invoked. It is working for /, createUser, editUser/:id (for loading user data).
editUser.js
<div class="container">
All Users
<form class="col g-3 mt-3"" method="post" action="/update/<%= user.id %>">
<div class="col-md-6">
<label for="inputFirstName" class="form-label">First Name:</label>
<input type="text" class="form-control" value="<%= user.first_name %>" name="first_name" id="first_name">
</div>
<div class="col-md-6">
<label for="inputLastName" class="form-label">Last Name</label>
<input type="text" class="form-control" value=<%= user.last_name%> name="last_name" id="last_name">
</div>
<div class="col-md-6">
<label for="inputEmail" class="form-label">Email</label>
<input type="email" class="form-control" value=<%= user.email%> name="email" id="email">
</div>
<div class="col-md-6 mt-3">
<button type="submit" class="btn btn-primary">Update</button>
</div>
</form>
</div>
routes/index.js
var express = require('express');
var router = express.Router();
var {allUsers, createUser, saveUser, editUser, updateUser} = require('../controllers/userController')
/* GET users listing. */
//Commenting default function
router.get('/', allUsers)
router.get('/createUser', createUser)
router.post('/createUser', saveUser)
router.get('/editUser/:id', editUser)
router.post('/updateUser/:id', updateUser)
module.exports = router;
controllers/userController.js
const User = require('../models/userModel')
const updateUser = async (req, res) => {
console.log('Updating User')
const userId = req.params.id
const userData = req.body
const selector = {where: {id:userId}}
await User.update(userData, selector).catch(error => console.log(error))
res.redirect('/')
}
module.exports = { allUsers,createUser,saveUser,editUser,updateUser }
app.js
//Imports
var createError = require('http-errors');
var express = require('express');
var path = require('path');
var cookieParser = require('cookie-parser');
var logger = require('morgan');
var expressLayouts = require('express-ejs-layouts')
const routes = require('./routes');
//DOTENV for storing sensitive data
require('dotenv').config({path:'./bin/.env'})
var app = express();
// View engine setup
app.set('views', path.join(__dirname, 'views'));
app.set('view engine', 'ejs'); //Key, Value
app.set('layout','layouts/layout')
//Middleware between requet and response
app.use(logger('dev'));
app.use(express.json());
app.use(express.urlencoded({ extended: false }));
app.use(cookieParser());
app.use(express.static(path.join(__dirname, 'public')));
app.use(expressLayouts)
//Use Router
app.use('/',routes)
// catch 404 and forward to error handler
app.use(function(req, res, next) {
next(createError(404));
});
// error handler
//error handler first parameter is "err"
app.use(function(err, req, res, next) {
// set locals, only providing error in development
res.locals.message = err.message;
res.locals.error = req.app.get('env') === 'development' ? err : {};
// render the error page
res.status(err.status || 500);
res.render('error');
});
module.exports = app;
Form action should be action="/updateUser/<%= user.id %>

why do i always get redirected to "/" if i make GET request to "/sell" with http status code 302?

IF i am not logged in and make "GET" request to "/sell" i am redirected to "/user/login" which is working accordingly.But if i am logged in and i make GET request to "/sell" i am always redirected to
"/" i.e. homepage instead of "/sell" page.so what should i do to only access "/sell" page if i am logged in?.Here are the code snippets you may probably need. Please let me know if u need anything else. Thank you in advance.
/routes/sell.js
const express = require('express');
const router = express.Router();
var bodyParser = require('body-parser');
var urlencodedParser = bodyParser.urlencoded({extended:false});
const Product = require('../models/product');
router.get('/sell', isLoggedIn, (req, res, next) => {
res.render('sell',{title: 'Home|Sell', success: req.session.success, errors: req.session.errors, csrfToken: req.csrfToken()});
req.session.success = null;
req.session.errors = null;
})
router.post('/book_upload', isLoggedIn, (req, res, next) => {
req.check('name')
.isLength({min:3}).withMessage('Name must be of 3 characters long.')
.matches(/^[A-Za-z\s]+$/).withMessage('Name must be alphabetic.');
req.check('phone')
.isLength({min:10,max:10}).withMessage('Phone number must be of 10 digits.');
req.check('book_name')
.isLength({min:3}).withMessage('Book Name must be of 3 characters long.')
.matches(/^[A-Za-z\s]+$/).withMessage('Book Name must be alphabetic.');
req.check('book_price')
.isNumeric().withMessage('Price must be numeric.');
req.check('description')
.isLength({min:3}).withMessage('Description must be of 3 characters long.')
.matches(/^[<A-Za-z0-9></A-Za-z0-9>\s]+$/).withMessage('Please write appropriate description.')
req.check('faculty')
.isLength({min:3}).withMessage('Faculty must be of 3 characters long.')
.matches(/^[A-Za-z\s]+$/).withMessage('Faculty must be alphabetic.')
var errors = req.validationErrors();
if (errors){
req.session.errors = errors;
req.session.success = false;
} else {
req.session.success = true;
var item = {
name: req.body.name,
phone: req.body.phone,
book_name: req.body.phone,
book_price: req.body.price,
description: req.body.description,
faculty: req.body.faculty
};
var data = new Product(item);
data.save();
}
res.redirect('/sell');
})
function isLoggedIn (req, res, next){
if (req.isAuthenticated()){
return next();
}
req.flash('error', 'Please Login to Continue')
res.redirect('/user/login');
}
module.exports = router;
and app.js
var createError = require('http-errors');
var express = require('express');
var path = require('path');
var cookieParser = require('cookie-parser');
var logger = require('morgan');
var expressHbs = require('express-handlebars');
var mongoose = require('mongoose');
var session = require('express-session');
var passport = require('passport');
var flash = require('connect-flash');
var validator = require('express-validator');
// var MongoStore = require('connect-mongo')(session);
mongoose.connect('mongodb+srv://username:password#firstdatabase-ytrfr.mongodb.net/test?retryWrites=true&w=majority',{
useNewUrlParser: true,
useUnifiedTopology: true
})
.then(()=>console.log('Connected to the database'))
.catch(err=> console.log('could not connect.',err.message))
// passport
require('./config/passport');
var indexRouter = require('./routes/index');
var userRouter = require('./routes/user');
var sellRouter = require('./routes/sell');
var app = express();
// view engine setup
app.engine('.hbs', expressHbs({ defaultLayout: 'layout', extname: '.hbs'}))
app.set('view engine', '.hbs');
app.use(logger('dev'));
app.use(express.json());
app.use(express.urlencoded({ extended: false }));
app.use(cookieParser());
app.use(validator());
app.use(session({
secret: 'blahblah',
resave: false,
saveUninitialized: false,
}))
app.use(flash());
app.use(passport.initialize());
app.use(passport.session());
app.use(express.static(path.join(__dirname, 'public')));
app.use((req, res, next) => {
res.locals.login = req.isAuthenticated();
res.locals.session = req.session;
next();
})
app.use('/', indexRouter);
app.use('/', userRouter);
app.use('/', sellRouter);
// catch 404 and forward to error handler
app.use(function(req, res, next) {
next(createError(404));
});
// error handler
app.use(function(err, req, res, next) {
// set locals, only providing error in development
res.locals.message = err.message;
res.locals.error = req.app.get('env') === 'development' ? err : {};
// render the error page
res.status(err.status || 500);
res.render('error');
});
module.exports = app;
and sell.hbs
<section class="my_account_area pt--80 pb--55 bg--white">
<div class="container">
<div class="row">
<div class="col-lg-6 col-12">
<div class="my__account__wrapper">
{{# if success}}
<section class="success">
<h2>Form submitted!</h2>
</section>
{{else}}
{{# if errors}}
<div class="alert alert-danger">
<section class="errors">
<ul>
{{# each errors}}
<li>{{ this.msg }}</li>
{{/each}}
</ul>
</section>
</div>
{{/if}}
<h3 class="account__title">Fill Up the Information of Book</h3>
<form action="/book_upload" method="post">
<div class="account__form">
<div class="input__box">
<label>Your Name <span>*</span></label>
<input type="text" id="name" name="name">
</div>
<div class="input__box">
<label>Phone No. <span>*</span></label>
<input type="number" id="phone" name="phone">
</div>
<div class="input__box">
<label>Name of book <span>*</span></label>
<input type="text" id="book_name" name="book_name">
</div>
<div class="input__box">
<label>Price of Book<span>*</span></label>
<input type="number" id="book_price" name="book_price">
</div>
<div class="input__box">
<label>Description of Book<span>*</span></label>
<input type="text" id="description" name="description" placeholder="e.g. To study in 1st year 1st part">
</div>
<div class="input__box">
<label>Faculty<span>*</span></label>
<input type="text" id="faculty" name="faculty">
</div>
<input type="hidden" name="_csrf" value="{{ csrfToken }}">
<div class="form__btn">
<button type="submit">Upload</button>
</div>
</div>
</form>
</div>
{{/if}}
</div>
</div>
</div>
</section>
Middleware functions are executed sequentially, therefore the order of middleware inclusion is important.
Hence, change the order of
app.use('/', indexRouter);
app.use('/', userRouter);
app.use('/', sellRouter);
to
app.use('/', sellRouter);
app.use('/', indexRouter);
app.use('/', userRouter);
It will work.

Contact form not submitting information to Terminal

Im using express, node, bodyParser to pull information from a contact form and post it to the terminal. When I run the code and access my demo site through LocalHost:3000, upon submitting, my input items are not showing up in the terminal.
I've tried changing the form attributes action="send" action="/send" action="/"
const express = require('express');
const path = require('path');
const bodyParser = require('body-parser');
const exphbs = require('express-handlebars');
const nodemailer = require('nodemailer');
const app = express();
// View engine setup
app.engine('handlebars', exphbs());
app.set('view engine', 'handlebars');
// Static folder
app.use('/public', express.static(path.join(__dirname, 'public')));
/ Body Parser Middleware
app.use(bodyParser.urlencoded({ extended: false }));
app.use(bodyParser.json());
app.get('/', (req, res) => {
res.render('contact', { layout: false });
});
app.post('/send', (req, res) => {
console.log(res.body);
});
//Form HTML code
<form action="send" method="POST">
<input name="name" type="text" id="name" placeholder="NAME: First & Last">
<input name="email" type="text" id="email" placeholder="EMAIL:">
<textarea name="text" id="text" cols="30" rows="10" placeholder="QUESTION OR INQUIRY:"></textarea>
<br>
<button type="submit">Submit</button>
</form>
Have you tried console logging the req instead of the res for the app.post?
If you are doing console.log(req.body) then this should output a long json object. If this is not happening, then you are not hitting the url.
const express = require('express');
const path = require('path');
const bodyParser = require('body-parser');
const exphbs = require('express-handlebars');
const nodemailer = require('nodemailer');
const app = express();
// View engine setup
app.engine('handlebars', exphbs());
app.set('view engine', 'handlebars');
// Static folder
app.use('/public', express.static(path.join(__dirname, 'public')));
// Body Parser Middleware
app.use(bodyParser.urlencoded({extended:false}));
app.use(bodyParser.json());
app.get('/', (req, res) => {
res.render('contact', { layout: false });
});
app.post('/send', (req, res) => {
console.log(res.body);
});
The problem is in your html code. I have made some changes, Try this.
//Form HTML code
<form action="http://localhost:9000/send" method="POST">
<input name="name" type="text" id="name" placeholder="NAME: First & Last">
<input name="email" type="text" id="email" placeholder="EMAIL:">
<textarea name="text" id="text" cols="30" rows="10" placeholder="QUESTION OR INQUIRY:"></textarea>
<br>
<button type="submit">Submit</button>
</form>

how to pass variable from one ejs to another ejs in node js

I have two ejs in my views folder
I have created very simple ejs to see if I can send the variable from one ejs to another ejs.
a.ejs in veiws file
<form name="input" action="\home" method="post">
<input type='checkbox' checked>Cheese
<input type="submit" value="Submit" href="validation.ejs">
</form>
b.ejs has
<h1><% post my variable here%></h1>
in my node js this is what i did
const express = require('express');
const bodyParser = require('body-parser');
const app = express();
app.use(bodyParser.urlencoded({ extended: false }));
app.set('view engine', 'ejs');
app.get('/', (req, res) => {
res.render('index', { title: 'EJS Demo' });
});
app.post('/', (req, res) => {
const a = req.body.a;
res.get('index2',a);
});
app.listen(3000, () => {
console.log('Listening....');
});
i think the post has to do something in here...
I think you need to submit a value from form1 in page1 and pass that variable to page2
if thats the case you can do like this
const express = require('express');
const bodyParser = require('body-parser');
const app = express();
app.use(bodyParser.urlencoded({ extended: false }));
app.set('view engine', 'ejs');
// send the page1 to the user
app.get('/', (req, res) => {
res.render('page1', { title: 'EJS Demo' });
});
//capture the submit from the user and then send another page
//to the user
app.post('/submitForm', (req, res) => {
const a = req.body.valueFromA;
res.render('page2',a);
});
app.listen(3000, () => {
console.log('Listening....');
});
<form name="input" action="\home" method="post">
<input type='checkbox' checked>Cheese
<input type="submit" value="Submit" href="validation.ejs">
</form>
<!-- page1 form1 -->
<html>
<head>
<title> <& title &> </title>
</head>
<form action='/submitForm' method='post'>
<input type='text' value='' name='valueFromA' />
<input type='submit' />
</form>
</html>
<!-- page2 ejs -->
<html>
<body>
<p> <% value %> </p>
</body>
</html>
b.ejs has
<h1><% post my variable here%></h1>
in my node js this is what i did const

Cannot post to a server in express

I have an express app that takes basic user input data. All of my get routes work fine but when submit a post request to the server I get a 404 on the url I'm posting to even though I have this page in my views folder.
app.js:
var express = require('express');
var path = require('path');
var consolidate = require('consolidate');
var bodyParser = require('body-parser');
var database = require('./database/database');
var Patient = require('./models/models').Patient;
var morgan = require('morgan');
var routes = require('./routes');
var app = express();
app.engine('html', consolidate.nunjucks);
app.set('view engine', 'html');
app.set('views', './views');
app.use(morgan('dev'));
//app.use(app.router);
app.use(routes);
app.use(bodyParser.urlencoded({ extended: false }));
app.listen(3055);
module.exports = app;
routes/index.js:
const express = require('express');
var bodyParser = require('body-parser');
var Patient = require('../models/models').Patient;
const router = express.Router();
router.get('/', function(req, res, next){
res.render('index.html');
});
router.post('/addsubject', function(req, res, next){
Patient.create(req.body).then(function(patient){
res.redirect('/profile');
}).catch(function(err){
if(error.name === "SequelizeValidationError"){
} else {
return next(err);
}
}).catch(function(error){
res.send(500, error);
});
});
router.get('/profile', function(req, res, next){
res.render('./profile.html');
});
router.get('/addsubject', function(req, res, next){
// .... do something here ..
});
module.exports = router;
I have the <form action="/addsubject" method="post"> in my index.html file.
index.html:
<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8">
<title>dabl Demographic</title>
<body>
<h2>Add Subject</h2>
<form action="/addsubject" method="post">
<label for="fname">First Name: </label>
<input type="text" name="fname" id="fname">
<br>
<label for="sname">Second Name: </label>
<input type="text" name="sname" id="sname">
<br>
<label for="dob">dob: </label>
<input type="text" name="dob" id="dob">
<br>
<label for="laterality">Laterality: </label>
<input type="text" name="laterality" id="laterality">
<br>
<button>Submit</button>
</form>
</body>
</html>
You pass wrong function (error handling function) to the POST route.
Just remove first "err" param from the function like this:
router.post('/addsubject', function(req, res, next){
Use body-parser middleware before app.router
...
app.use(bodyParser.urlencoded({ extended: false }));
app.use(morgan('dev'));
//app.use(app.router);
app.use(routes);
...
Problem solved:
}).catch(function(err){
if(error.name === "SequelizeValidationError"){
next(err); //next(err); called inide this block no more 404 error
}
User input is now succesfully passed through the body-parser.

Resources