Node Express can't figure out how to update user details - node.js

Okay so once the user logs in, i am storing their details in req.user. The user should then be able to edit their details (fistname, lastname, email) in a form rendered with the /profile route as seen below:
app.get('/profile', checkAuthenticated, (req, res) => {
res.render('profile.ejs', req.user);
})
Here is the form:
<form class="form__inputs" action="/update-profile" method="post">
<div class="form__input">
<input id="firstname" name="firstname" type="text" value="<%=firstname%>" required />
<label for="firstname">Firstname</label>
</div>
<div class="form__input">
<input id="lastname" name="lastname" type="text" value="<%=lastname%>" required />
<label for="lastname">Lastname</label>
</div>
<div class="form__input form__email">
<input id="email" name="email" type="email" value="<%=email%>" required />
<label for="email">Email</label>
</div>
<button class="form__button" type="submit">Update</button>
</form>
After submitting the form the i want the user to be redirected to the /update-profile route, where i can perform an update to the database (MySQL).
app.put('/update-profile', (req, res) => {
console.log(req.params)
console.log(req.body)
res.redirect('/')
})
However I'm recieving a "Cannot POST /update-profile" error.
I was just going to use the user_id stored in req.user, and new user data (firstname, lastname, email) stored in req.body.params to update the database, but i've clearly gotten a bit mixed up with my routes.
Any help would be greatly appreciated, thanks so much for your time!

It seems you are listening to a PUT request in your express app, but sending a POST.
app.post('/update-profile', (req, res) => {
console.log(req.params)
console.log(req.body)
res.redirect('/')
});
If you change your code to this, it should work.

Related

Express.js "TypeError: Cannot read properties of undefined" in req.body

`
router.post("/login", (req, res) => {
console.log(req.body.username)
console.log(req.body.password)
res.redirect("/")
})
<body>
<form action="/register" method="post">
<label for="username">
</label>
<input type="text" name="username" placeholder="Username" id="username" required>
<label for="password">
<i class="fas fa-lock"></i>
</label>
<input type="password" name="password" placeholder="Password" id="password" required>
<input type="submit" value="Login">
</form>
</body>
`
I just started learning express but already have a problem and I can't find any fixes. Somehow the req.body variable is undefined in the post. This is going to be a login system. (Sorry for my bad english)
I first tried to do it like here on github: https://github.com/WebDevSimplified/express-crash-course but i still had the "TypeError: Cannot read properties of undefined" error in my console. So I was looking for something else and found this: https://codeshack.io/basic-login-system-nodejs-express-mysql/
My code is based on the codeshack example but I'm still getting the error.
If you want to access body of post request, we need to use express middleware which will parse the body of request and it will attached it under req.body object.
In order to do it we can use express.urlencoded() middleware.
for more information link
router.post("/login",express.urlencoded({ extended: true }) , (req, res) => {
console.log(req.body.username)
console.log(req.body.password)
res.redirect("/")
})
Add middleware before your handlers
app.use(bodyParser.urlencoded({ extended: false }))

Nodejs req.query.token undefined from url

Good day,
Can anyone help me with this question, I send email to user with link which have token and email in it:
<p>To reset your password, please click the link link</p>
So with following code I'm trying to set new password for user:
router.post('/reset-password', authController.resetPassword);
exports.resetPassword = async (req, res, next) => {
let token = req.query.token;
let email = req.query.email;
console.log(token);
console.log(email);
...
Page form:
<form action="/auth/reset-password" method="POST">
<div class="form-group">
<input type="password1" id="newPassword" name="password" class="form-control" placeholder="Naujas slaptažodis" required>
</div>
<div class="form-group">
<input type="password2" id="newPasswordConfirm" name="passwordConfirm" class="form-control" placeholder="Pakartoti nauja slaptažodį" required>
</div>
<button type="submit" name="submit" class="btn btn-theme btn-block btn-form">Patvirtinti</button>
</form>
So my problem is that req.query.token return for me undefined.
Probably problem is that when user press submit, it send to new link (http://localhost:5000/auth/reset-password) which don't have token and email in new url.
How should I transfer it from my email url to new url, or maybe there is something else what I can do?
Thank you
I managed today to fix it, so if any one have familiar problem do as robertklep told me.

POST request from handlebars form gives 404

I have the following form in my handlebars code:
{{#if contact}}
<form method="POST" action="/contacts/{{contact._id}}">
<input type="text" name="name">
<input type="text" name="phone">
<button>Update Contact</button>
</form>
{{else}}
When the user clicks the button, my browser is redirected to 'localhost:3000/contacts/34634234'
and I get a 404 error.
I checked, and 34634234 is a valid ID.
In my Node routes, I have
router.post('contacts/:id', function(req, res) {
res.render('index');
});
I know res.render('index') works because I've used it in other parts of my code.
However,
Not sure if is because of this, but...
You're missing type="submit" on the button element.
{{#if contact}}
<form method="POST" action="/contacts/{{contact._id}}">
<input type="text" name="name">
<input type="text" name="phone">
<button type="submit">Update Contact</button>
</form>
{{else}}
And you're missing a slash / at the beginning of your route.
router.post('/contacts/:id', function(req, res) {
res.render('index');
});

How to write Mongo query to find data between dates

I want to get data of owner ID which lies between two dates using datePicker.
HTML
<form method="post">
<div class="col-lg-5 col-md-5">
<label>From</label>
<input type="date" class="form-control" ng-model="date.from" name="datefrom" />
</div>
<div class="col-lg-5 col-md-5">
<label>To</label>
<input type="date" class="form-control" ng-model="date.to" name="dateto" /> </div>
<div class="col-lg-2 col-md-2">
<button class="btn btn-primary " ng-click="getleaddate()">Go</button>
</div>
</form>
Node API
apiRoutes.post('/getleaddate', function(req, res){
var token=getToken(req.headers);
var owner=jwt.decode(token, config.secret);
Lead.find({ownerId:owner._id},date:{$gte :new Date(req.body.datefrom), $lte:new Date(req.body.dateto)},function(err, data){
if(err){res.json(err)}
else{
res.json(data);
console.log(data)
}
});
});
Above API is not working because req.body.datefrom and req.body.dateto is undefined
I don't know how to fix it.
please check the function for ng-click="getleaddate()"
Check the network tab on the request and request body sent .
it is working fine for me :
FormData:
datefrom:2017-01-11
dateto:2017-01-04
router.post('/test', function(req, res) {
console.log(req.body);
console.log(req.body.datefrom);
});
Console Output:
{ datefrom: '2017-01-11', dateto: '2017-01-04' }

Shortcut to adding req values to a response for rendering in Express View

I'm using Node/Express (most recent production versions)
I have a form where I collect new account info. The user can add a username, etc.
In the view handler, I check a mongodb database to see if the username is unique. If it is not, I generate a message and reload the original view. Since the original request was a post, all of the data the user posted is in req.body. I would like to add the data the user submitted on the response. I could do it by specifically adding each value to the response. But isn't there an easier way to add all the request data back to the response? And is there a way to render that in the view (i'm using ejs) I tried res.send(JSON) coupled with ejs variables. Doing so generates errors saying the variables aren't available.
Here's my function (ignore the users.createUser(req) - it's not finished yet):
createAccount: function(req, res, next){
users.createUser(req);
res.render('create_account', {
layout: 'secure_layout',
title: 'Create Account',
givenName: req.body.givenName,
username: req.body.username,
familyName: req.body.familyName
});
},
And here's my view:
<form action="/createAccount" method="post">
<div>
<label>First Name:</label>
<input type="text" name="givenName" value="<%= givenName %>"/><br/>
</div>
<div>
<label>Last Name:</label>
<input type="text" name="familyName" value="<%= familyName %>"/><br/>
</div>
<div>
<label>Username:</label>
<input type="text" name="username" value="<%= username %>"/><br/>
</div>
<div>
<label>Password:</label>
<input type="password" name="password"/>
</div>
<div>
<input type="submit" value="Submit"/>
</div>
</form>
It seems overly complex to have to add each of the values. I tried {body: req.body} but values were never added to the view.
I'm not quite sure what you're after, but if you want to render an ejs view with data that was on the request body, you would do something along these lines:
app.post('/foo', function(req, res, next) {
res.render('view', {body: req.body});
});
view.ejs:
<ul>
<% for(var key in body) { %>
<li><%= key %>: <%= body[key] %></li>
<% } %>
</ul>

Resources