I'm using Express to make the api and I'm using angular to send the POST request, for some reason the request do not send and i have no idea why.
server
app.post('/users/register', (req, res) => {
const { first_name, last_name, email, password, city, street } = req.body
pool.query('INSERT INTO users SET ? ', {first_name,last_name,email,password,city,street }, (err, data) => {
if(err) {
console.log(err);
} else {
console.log(data);
res.status(200).send(data)
}
})
})
service
insertUsers(registerFrom) {
return this.http.post('http://localhost:3000/users/register', registerFrom)
}
component TS
submitFrom(registerForm) {
console.log(registerForm);
this.appControl.insertUsers(registerForm)
.subscribe(data => {
console.log(data);
})
}
Component html
<form #registerFrom="ngForm" (ngSubmit)="submitFrom(registerFrom.value)" class="form-container sign-up-container">
<div class="thisForm">
<h1>Create Account</h1>
<div >
<input type="checkbox" id="admin" name="admin" value="Admin">
<label for="admin"> Admin?</label>
</div>
<div class="social-container">
<span>or use your account</span>
</div>
<input ngModel name="name" type="text" placeholder="First name" />
<input ngModel name="lastName" type="text" placeholder="Last name" />
<input ngModel name="email" type="email" placeholder="Email" />
<input ngModel name="password" type="password" placeholder="Password" />
<div class="adress">
<input name="city" ngModel type="text" placeholder="City">
<input name="street" ngModel type="text" placeholder="Street">
</div>
<button type="submit" value="Submit">Sign Up</button>
</div>
</form>
in server use array instead of Object
pool.query('INSERT INTO users SET ? ', [first_name,last_name,email,password,city,street, (err, data) => {}
Try the query:
pool.query('INSERT INTO users ( first_name, last_name, email, password, city, street ) VALUES (?,?,?,?,?,?)', [first_name, last_name, email, password, city, street]), function (error, results) {
if (error) throw error;
// ...
});
and check out the docs about escaping query values https://www.npmjs.com/package/mysql#escaping-query-values
In order to avoid SQL Injection attacks, you should always escape any
user provided data before using it inside a SQL query
Related
I'm trying to pass an array to MongoDB using express post request.
app.post('/createGroup', (req, res) => {
const { title, description, tenants } = req.body;
const group = {
title: title,
description: description,
tenants: tenants,
};
console.log(tenants);
const newGroup = new Group(group);
newGroup.save();
res.redirect('/'); });
Everything works just fine till here. if I log console.log(tenants) returns and array of ids
[ 'd8ef412c-7947-4500-8e7f-73157e30961e', 'a515dfa8-a272-4d95-87d2-a1a4f22175b5' ]
But the tenants are not passed to MongoDB.
Instead, I get
_id: 623639bde8f1bdfc6eab462e
title: "Nitro"
description: "Its a Group"
tenants: Array
created_at: 2022-03-19T20:14:53.268+00:00
__v: 0
Here is my Schema,
const GroupSchema = new mongoose.Schema({
title: String,
description: String,
tenants: [{type: String}],
created_at: {
type: Date,
default: Date.now
}
});
The HTML form is here.
<form class="create-group" action="/createGroup" method="POST">
<div class="form-group">
<label for="title">Group Title</label>
<input type="text" class="form-control" id="title" name="title" placeholder="Group Title / Name">
</div>
<div class="form-group">
<label for="description">Group Description</label>
<textarea class="form-control" id="description" name="description" rows="3"
placeholder="Group Description"></textarea>
</div>
<div>
<fieldset>
<legend>
Tenants
</legend>
<% tenants.forEach(function(tenant) { %>
<div class="form-check">
<input class="form-check-input" type="checkbox" value="<%= tenant.tenantId %>" name="tenants[]">
<label class="form-check-label" for="<%= tenant.tenantId %>">
<%= tenant.tenantName %>
</label>
</div>
<% }) %>
</fieldset>
</div>
<div class="form-group">
<button type="submit" class="btn btn-primary">Create Group</button>
</div>
</form>
I believe the issue is in your schema, you should be defining tenants array property like this
tenants: [String]
or you can do
tenants: { type: [String] }
I have three input to obtain three different values. Im using express.js , node.js, mongodb and ejs templates.
<form action="/save-profile/<%= user.id %>/<%= user.name %>/<%= user.lastname %>/<%= user.description %>" method="POST">
<div class="input-group mb-3">
<span class="input-group-text" id="basic-addon1">Name</span><%= user.username %>
<input type="text" class="form-control" placeholder="'John'" aria-label="Username" name="username">
<span class="input-group-text">lastName</span><%= user.lastname %>
<input type="text" class="form-control" placeholder="" aria-label="Server" name="lastname">
</div>
<div class="input-group">
<span class="input-group-text">Description:</span>
<textarea class="form-control" aria-label="With textarea" placeholder="" name="description"><%= user.description %></textarea>
</div>
</p><br>
<button class="btn btn-primary mb-10 btn-lg">Save</button>
</div>
</div>
In js file:
router.post('/save-profile', async (req, res) => {
const profile_id = await User.findById({ _id: req.body.id })
const updatedName = await User.findOneAndUpdate({ username: req.body.username})
const updatedlastname = await User.findOneAndUpdate({ apellido: req.body.lastname })
const updatedDescription = await User.findOneAndUpdate({ description: req.body.description })
console.log(profile_id,updatedName,updatedApellido,updatedDescription)
res.redirect('/profile')})
I tried to do it with a get but it didn't work
Firstly, action attribute in the form tag accepts the path where you are handling the form data. You only need to pass the user.id, there's no need to pass the other fields for this use-case.
<form action="/save-profile/<%= user.id %>" method="POST">
...
</form>
Secondly, in your route handler, the database record can be updated using only a single findOneAndUpdate call. You don't need to call it multiple times for every field if you're only going to update a single record.
The path written in action attribute will appear as /save-profile/1, for instance, in your route handler. Value preceding /save-profile/ i.e. 1 can be accessed by modifying the path in route handler as /save-profile/:id and in the callback you can get it by req.params.id
Finally you have this.
router.post('/save-profile/:id', async (req, res) => {
const response = await User.findOneAndUpdate(
{ _id: req.params.id },
{
username: req.body.username,
apellido: req.body.lastname,
description: req.body.description
},
{ new: true }
)
// Do something with response
res.redirect('/profile')
})
I'm new to mongoose/mongo and express so I'm not quiet sure how to go about this. So basically I'm trying to use checkboxes to sort of "filter" results in my database.
Here's an example of something in my db:
{ "location" : "PHARMACY",
"region" : "SOCAL",
"system" : "WITS",
"contact" : "SMITH",
"membership" : "TIER1" }
So far I've only figured out how to hard code it like this, where I do Environment.find({region: "SOCAL"}) and it spits out all the db entries that contain SOCAL as a region:
var express = require("express"),
app = express(),
mongoose = require("mongoose"),
bodyParser = require("body-parser");
mongoose.connect("mongodb://localhost/epims", {
useNewUrlParser: true,
useUnifiedTopology: true
});
app.use(bodyParser.urlencoded({ extended: true }));
app.set("view engine", "ejs");
//schema setup
var environmentSchema = new mongoose.Schema({
name: String,
region: String,
system: String,
contact: String,
membership: String,
});
var Environment = mongoose.model("Environment", environmentSchema);
app.get("/environments/show", function(req, res) {
//find environment with selected parameters
Environment.find({region: "SOCAL"}, function(err, foundEnvironment) {
if (err) {
console.log(err);
} else {
//render show template with that env
res.render("show", { environment: foundEnvironment });
}
});
});
How do I make it so this search through the database changes based on what selections are made?
Here is my select form if anybody needs to see that as well
<form action="/environments" method="GET">
<legend>Locations</legend>
<input type="checkbox" name="location" value="PHARMACY">
<label for="PHARMACY">PHARMACY</label>
<input type="checkbox" name="location" value="OFFICE">
<label for="OFFICE">OFFICE</label>
<input type="checkbox" name="location" value="STORE">
<label for="STORE">STORE</label>
<legend>Regions</legend>
<input type="checkbox" name="region" value="SOCAL">
<label for="SOCAL">SOCAL</label>
<input type="checkbox" name="region" value="NORCAL">
<label for="NORCAL">NORCAL</label>
<input type="checkbox" name="region" value="WA">
<label for="WA">WA</label>
...
Submit
</form>
You can pass the search parameters via the search query:
/environments/show?location=OFFICE&location=STORE®ion=SOCAL®ion=NORCAL
The GET request produce this database query:
{
region: { '$in': [ 'SOCAL', 'NORCAL' ] },
location: { '$in': [ 'OFFICE', 'STORE' ] }
}
app.get("/environments/show", function (req, res) {
let region = [req.query.region || []].flat();
let location = [req.query.location || []].flat();
let query = {
region: {
"$in": region
},
location: {
"$in": location
}
};
Environment.find(query, function (err, foundEnvironment) {
if (err) {
console.log(err);
} else {
//render show template with that env
res.render("show", { environment: foundEnvironment });
}
});
});
<form action="/environments/show" method="GET">
<legend>Locations</legend>
<input type="checkbox" name="location" value="PHARMACY">
<label for="PHARMACY">PHARMACY</label>
<input type="checkbox" name="location" value="OFFICE">
<label for="OFFICE">OFFICE</label>
<input type="checkbox" name="location" value="STORE">
<label for="STORE">STORE</label>
<legend>Regions</legend>
<input type="checkbox" name="region" value="SOCAL">
<label for="SOCAL">SOCAL</label>
<input type="checkbox" name="region" value="NORCAL">
<label for="NORCAL">NORCAL</label>
<input type="checkbox" name="region" value="WA">
<label for="WA">WA</label>
...
<button type="submit">Submit</button>
</form>
On firebase, using vue.js, when registering and trying to add more info about the user to the database I am running into a really frustrating error when the app tries to write the newUser email to Firebase. The app simply breaks when I the email is part of an object.
I am using the createUserWithEmailAndPassword(this.email, this.password) method to authorise and register a user (on the user list) and then calling a function to register the same user on the database.
this is the error i am getting:
As you can see the console is outputting a string joaoalvesmarrucho#gmail.com while complaining it's not a string. :/
I have converted the email to a string with no success.
HTML TEMPLATE:
<form v-on:submit.prevent>
<div class="control">
<input class="input" v-model="newUser.name" type="text" placeholder="Your Display Name">
</div>
<div class="control">
<input class="input" v-model="newUser.email" id="email" type="email" placeholder="joew#bloggs.com" >
</div>
<div class="control">
<input id="password" v-model="newUser.password" class="input" type="password" placeholder="Password">
</div>
<div class="control">
<input id="confirm_password" class="input" type="password" placeholder="Retype your password" v-on:keyup="checkRetypePassword">
</div><span id='message'></span>
<button type="submit" class="button is-primary" v-on:click="signUp">Register</button><span> or </span><button type="submit" class="button is-primary" v-on:click="googleSignUp">Register with Google</button>
</form>
SCRIPT:
export default {
data: function() {
return {
users: usersRef,
// username: this.$store.getters.getUser.displayName,
newUser: {
name: '',
email: '' ,
password: '',
uid: '',
}
};
},
methods: {
signUp: function() {
var jsonEmail = JSON.stringify(this.newUser.email);
var email = jsonEmail.replace(/\"/g, "");
console.log(email);
firebaseApp.auth().createUserWithEmailAndPassword(this.email, this.password).then(function(user) {
logUser(user); // callback push user to database
console.log(email);
}, function(error) {
alert(error.message + error.code);
});
function logUser(user) {
usersRef.push(this.newUser);
this.name = '';
this.email = ''; // ERROR: "email" must be a valid string
this.uid = firebaseApp.auth().currentUser.uid;
}
Could you please give me a hint?
Got it working simply by getting the value from the email field. Hope this is useful to somebody in the future:
HTML
<form v-on:submit.prevent>
<div class="control">
<input class="input" v-model="user.name" type="text" placeholder="Your Display Name">
</div>
<div class="control">
<input class="input" v-model="user.email" id="email" type="email" placeholder="joew#bloggs.com" >
</div>
<div class="control">
<input id="password" v-model="user.password" class="input" type="password" placeholder="Password">
</div>
<div class="control">
<input id="confirm_password" class="input" type="password" placeholder="Retype your password" v-on:keyup="checkRetypePassword">
</div><span id='message'></span>
<button type="submit" class="button is-primary" v-on:click="signUp">Register</button><span> or </span><button type="submit" class="button is-primary" v-on:click="googleSignUp">Register with Google</button>
</form>
SCRIPT:
export default {
data: function() {
return {
users: usersRef,
user: {
name: '',
email: '',
},
users: [{
name: 'John Doe',
email: 'john.doe#gmail.com',
uid: "should be actual User UID",
}],
};
},
methods: {
signUp: function() {
firebaseApp.auth().createUserWithEmailAndPassword(email.value, password.value).then(function(user) {
}, function(error) {
alert(error.message + error.code);
});
I am trying to implement a simple edit feature in my app. In my profile.handlebars file, I have an edit button. When clicked, I'd like the user's information to appear in the text input fields on the form in order to allow the user to edit their existing information.
Right now, they would have to input all of their information over again (and every field in the form would need to be filled out due to validation that I have implemented), click Submit, and their profile can be updated. Is this possible without using a framework (like Angular)? For example, in LinkedIn, a user can hover over a section of their profile causing the edit buttons to highlight, then click a single edit button, and they're instantly in editing mode. That might be too advanced for my purposes right now, but eventually, I'd love to have functionality like that.
I have a post request in my routes file to handle a user posting information to their profile:
router.post('/add', function(req, res) {
req.checkBody({
'city': {
errorMessage: 'Please enter your city'
},
'state': {
errorMessage: 'Please enter your state',
notEmpty: true
},
'zip': {
errorMessage: 'Please enter your zip code',
notEmpty: true
},
'about': {
errorMessage: 'Please briefly describe yourself',
notEmpty: true
}
});
console.log("req.user " + req.user);
var errors = req.validationErrors();
if (errors) {
res.render('profile', {
errors: errors
});
} else {
var user_info = new User_Info({
city: req.body.city,
state: req.body.state,
zip: req.body.zip,
about: req.body.about,
user_name: req.user.username
});
user_info.save(function(err, user_info) {
if (err) throw err;
});
res.redirect('profile/' + req.user.username)
}
})
Then, I have my profile.handlebars file:
{{#if errors}}
Uh oh! Something went wrong. Please review the below errors, and try again.<br><br>
<ul>
{{# each errors }}
<li style="color: red">{{this.msg}}</li>
{{/each}}
</ul>
{{else}}
<h3 align="center">Profile ({{user_name.name}})</h3>
<div class="row">
<div class="col-md-4 col-md-offset-4">
<div class="thumbnail" style="border-radius: 12px">
<div class="caption">
<p>City: {{# each information }} {{this.city}} {{/each}}</p>
<p>State: {{# each information }} {{this.state}} {{/each}}</p>
<p>Zip: {{# each information }} {{this.zip}} {{/each}}</p>
<p>About: {{# each information }} {{this.about}} {{/each}}</p>
<div class="btn-group">
<button type="Edit" class="btn btn-danger dropdown-toggle deleteLocation" data-id="{{this.id}}">Edit</button>
</div>
</div>
</div>
</div>
</div>
<br>
<center>
<form method="POST" action="/users/add">
<input type="text" name="city" placeholder="City" style="text-align: left">
<br><br>
<input type="text" name="state" placeholder="State" style="text-align: left">
<br><br>
<input type="text" name="zip" placeholder="Zip" style="text-align: left">
<br><br>
<textarea name="about" placeholder="About You" style="text-align: left; resize: both;" rows="5" cols="50"></textarea>
<br><br>
<div class="btn-group">
<button type="submit" class="btn btn-success dropdown-toggle" aria-haspopup="true" aria-expanded="false">Submit</button>
</div>
<br><br>
</form>
</center>
{{/if}}
Please let me know if you need additional info to help me solve this issue. Thanks!
you can use this code for node for editing the parameters , city,state,zip and about.
router.post('/add', function (req, res) {
var users = req.Collection;
var city = req.body.city;
var state = req.body.state;
var zip = req.body.zip;
var about = req.body.about;
var user_id = req.body.user_id;
if (city && state && ) {
users.findOneAndUpdate({_id: user_id}, {$set: {city: city, state: state, zip: zip, about:about}}, function (err, user) {
if (err) {
res.json({status: 0, message: err});
}
if (!user) {
res.json({status: 0, msg: "not found"});
} else {
res.json({status: 1, city: city, state: state, zip: zip, about:about, message: " edit success"});
}
})
} else {
res.json({status: 0, msg: "Invalid Fields"});
}
});