How can I pass id to the router delete method? - node.js

I have a list of data shown with a delete button as below.
<ul class="quotes">
<% for(var i=0; i<quotes.length; i++) {%>
<li class="quote" data-id= "<%= quotes[i]._id %>">
<span><%= quotes[i].name %></span> -
<span><b><%= quotes[i].price %></b></span>
<button class="delete-todo">×</button>
</li>
<% } %>
</ul>
From jQuery I am passing the id to be deleted as follow:
$('.delete-todo').on('click', function(e){
e.preventDefault();
var id = $(this).parent().data('id');
$.post('/products',{'id':id},function(data){
},'json');
});
I have a product.router.js as follows:
router.delete(':/id', product_controller.product_delete);
I am confused about how to call this delete of router and pass the id to this router method.

In NodeJS
router.delete('/products/:id', product_controller.product_delete);
and you will get in params( req.params.id) in product_controller.product_delete function
and in JQuery
$('.delete-todo').on('click', function(e){
e.preventDefault();
var id = $(this).parent().data('id');
$.ajax({
url: '/products/'+ id,
type: 'DELETE',
success: function(data) {
// your success response data here in data variable
console.log('result ', data);
}
});
});

Check this
Express JS
router.delete('/:id', product_controller.product_delete);
// If you are using router in `app.use('products', router)`
OR
router.delete('products/:id', product_controller.product_delete);
Ajax Call
$.ajax({
url: '/products/'+ id,
type: 'DELETE',
success: callback
});

Related

AJAX call is broken, NodeJS, Express, Handlebars

I've been working on this for a couple of days. I'm certain its something really stupid, but I'm at the end of my sanity.
The public files are set up properly.
Error Message:
Uncaught ReferenceError: togDefine is not defined
Front End HTML:
<li class="list-group-item list-group-item-dark">
<div class="row">
<div class="col-md-4"><strong>Heating:</strong> {{#if heating}} {{this.heating}} {{else}} N/A {{/if}}</div>
<div class="col-md-4"><strong>Cooling:</strong> {{#if cooling}} {{this.cooling}} {{else}} N/A {{/if}}</div>
<div class="col-md-4">
<input type="checkbox" id="pvt{{this.id}}" checked="{{this.private}}" onchange="togDefine({{this.id}}, {{this.private}});" data-toggle="toggle" data-on="Private" data-off="Public" data-onstyle="success" data-offstyle="danger" />
</div>
</div>
AJAX Call:
$(function() {
// Private-Public toggle
let togDefine = (id, pvt) => {
$.ajax({
type: "POST",
url: "/api/pvtToggle",
data: {
id: id,
newState: (pvt === 'true') ? false : true
},
success: function(text) {
if (text === 'ok') {
pvtSuccess(id, pvt);
} else {
console.log('updatePvt failed');
}
}
});
};
let pvtSuccess = (id, pvt) => {
$('#pvt' + id).attr('checked', (pvt === 'true') ? 'false' : 'true');
};
});
Back End:
//TOGGLE Private vs Public PROPERTY
app.put('/api/pvtToggle/', isAuthenticated, function(request, response) {
db.Prop.update({
private: request.params.newState
}, {
where: {
id: request.params.id
}
}).then(data => {
response.send('ok');
}).catch(error => {
console.log(error);
});
});
Please help me figure out why the request isn't working properly. :D
Your function togDefine() is defined inside this block:
$(function() { /* in here */ })
Therefore, that function name is only available inside that block and is not available to your HTML. Since just defining a function doesn't actually execute anything, there is really no reason to define a function inside of that kind of block unless you ONLY want the symbol available inside that block.
Since you explicitly don't want that here, just move the definition of togDefine() outside that block.

Object not found, using parse nodejs

I'm new using parse and I'm trying to get the objects from my database and displaying them with ejs using a for loop in my webpage. I'm using back4app as my database.
Here's what I'm doing:
const Car = Parse.Object.extend('Vehicle');
const query = new Parse.Query(Car);
app.get('/', function(req, res){
const VehicleInfo = [
{
VehicleName: query.get('Name'),
Description: query.get('Description'),
Price: query.get('Price'),
Rating: query.get('Rating'),
Route: query.get('Route'),
PassengerAmount: query.get('PassengerAmount')
}
]
try{
res.render('index', {
title: 'mainPage',
VehicleData: VehicleInfo
});
}catch(error){
throw error.message;
}
});
I query this and all 5 of my vehicles are displayed in the console.log but when trying to do the same in my .ejs file this shows up and only one div displays
enter image description here
Here's how I'm using the for loop
<% for (var CarInfo of VehicleData) { %>
<div class="row">
<div class="col-lg-4 col-md-6">
<!-- Car Item-->
<div class="rn-car-item">
<div class="rn-car-item-review">
<div class="fas fa-star"></div> <%= CarInfo.Rating %>
</div>
<div class="rn-car-item-thumb">
<a href="/car-single">
<img class="img-fluid" src="/images/car-1.jpg" alt="Black Sedan" srcset="/images/car-1.jpg 1x, /images/car-1#2x.jpg 2x"/>
</a>
</div>
<div class="rn-car-item-info">
<h3>
<%= CarInfo.VehicleName %>
</h3>
<p>Descripcion: <%= CarInfo.Description %></p>
<div class="rn-car-list-n-price">
<ul>
<li>Ruta: <%= CarInfo.Route %></li>
<li>Cantidad de Pasajeros: <%= CarInfo.PassengerAmount %></li>
</ul>
<div class="rn-car-price-wrap">
<a class="rn-car-price" href="/car-single">
<span class="rn-car-price-from">Desde</span>
<span class="rn-car-price-format">
<span class="rn-car-price-amount">$<%= CarInfo.Price %></span>
<span class="rn-car-price-per">/day</span>
</span>
</a>
</div>
</div>
</div>
</div>
<!-- End Car Item-->
</div>
</div>
<% } %>
I'm sure your code doesn't work like this, also not in the console. You need to run find or first in order to fetch objects.
The other problem is that your Promise hasn't been resolved and doesn't contain the result when you pass it on to the .ejs file. It works in the console because the result in the console will be updated once the Promise is resolved.
You need to do
const VehicleInfo = [];
const query = new Parse.Query(Car);
query.find().then(result => {
result.forEach(vehicle => {
VehicleInfo.push({
VehicleName: result.get('Name'),
Description: result.get('Description'),
Price: result.get('Price'),
Rating: result.get('Rating'),
Route: result.get('Route'),
PassengerAmount: query.get('PassengerAmount')
});
});
}).catch(error => {
console.error('error fetching objects', error);
});
Alternatively you can await the result for cleaner code:
app.get('/', async function(req, res) {
const VehicleInfo = [];
const query = new Parse.Query(Car);
try {
const result = await query.find();
result.forEach(vehicle => {
VehicleInfo.push({
VehicleName: result.get('Name'),
Description: result.get('Description'),
Price: result.get('Price'),
Rating: result.get('Rating'),
Route: result.get('Route'),
PassengerAmount: query.get('PassengerAmount')
});
});
} catch (error) {
console.error('error fetching objects', error);
}
});
Here's more about Promises in JavaScript

Unable to fetch array into an EJS file

I want to display an appropriate error message that I am pushing in an array 'errorsList' and sending it to ideas/add.ejs as the context. In the EJS, i am iterating over errorsList and fetching the elements. The webpage displays an error saying errrorsList is not defined.
I have tried to pass the JSON directly instead of putting it into some variable just to check, still in that case it gives me an error as errorsList is not defined
App.js
// Process form
let errorsList = [];
if(!request.body.title) {
errorsList.push({ text: 'Please add a title' });
}
if(!request.body.details) {
errorsList.push({ text: 'Please add something' });
}
console.log('Errors List: ', errorsList);
if(errorsList.length > 0) {
const context = {
errorsList: errorsList,
title: request.body.title,
details: request.body.detail,
pageTitle: 'Ideas'
}
response.render('ideas/add', context);
}
else {
const context = {
pageTitle: 'Ideas'
};
response.render('ideas/ideas', context)
}
});```
add.ejs
<div class="container">
<% errorsList.forEach((error) => { %>
<div class="alert alert-danger">
<%= error.text %>
</div>
<% }) %>
Here i get the error as errorsList is not defined

How do I have a variable available to display on my success page, after adding items to a database via a /POST route?

I would like to display the doc.id variable of a successful /POST of data to a route, on the success page that the user will be redirected to afterward. I'm trying to work out how to carry the variable teamId through to the Handlebar template page success.hbs
I've tried making it a variable, and setting up a Handlebar helper to display it, but nothing is working.
/POST route redirecting to success.hbs:
app.post('/create', (req, res) => {
var players = [];
var playerObj = {};
for (let i = 1; i < 21; i++) {
var playerObj = { playerName: req.body[`player${i}Name`], playerNumber: req.body[`player${i}Number`], playerPosition: req.body[`player${i}Position`] };
if (req.body["player" + i + "Name"] === '') {
console.log("Empty player name detected, disregarding");
} else {
players.push(playerObj);
}
}
var newTeam = new Team({
// WEB SETUP BELOW
"team.teamRoster.teamCoach": req.body.coachName,
"team.shortTeamName": req.body.teamShortName,
"team.teamName": req.body.teamName,
"team.teamRoster.players": players
});
newTeam.save().then((doc) => {
var teamId = doc.id;
console.log(teamId);
res.render('success.hbs');
console.log("Team Added");
}, (e) => {
res.status(400).send(e);
});
});
/views/success.hbs
<div class="container-fluid" id="body">
<div class="container" id="page-header">
<h1><span id="headline">Team Added Succesfully</span></h1>
<hr>
<h3><span id="subheadline">Input the following address as a JSON Data Source within vMix.</span></h3>
<span id="content">
<div class="row">
<div class="container col-md-12">
{{{teamId}}}
</div>
</div>
</span>
</div>
<hr>
</div>
I'd like a Handlebar helper to get the doc.id value of the /POST request, and store it as teamId to display on the success page. It's finding nothing at the moment.
Any help is appreciated.
Node.js can pass variables to the handlebars-view like this:
newTeam.save().then((doc) => {
var teamId = doc.id;
console.log(teamId);
res.render('success.hbs', {
teamId
});
console.log("Team Added");
}, (e) => {
res.status(400).send(e);
});

sails.js view does not load

I made a controller which get data from a rest api and
serializes them to .xls file.
In my web view I have a button with "Create xls data" which call my controller.
Then my controller sierialises and reload this view with the xls download link and a "Download data" button.
My view import_export_data_page.ejs:
At start button "Create xls data" is displayed.
<%
if(typeof link == 'undefined'){
%>
<button type="button" class="btn btn-primary" id="button_get_xls_file">Create xls data</button>
<%
}else {
%>
<button type="button" class="btn btn-primary"></button>
<%
}
%>
<script type="text/javascript">
$('#button_get_xls_file').click(function(){
var projectName = getCurrentServiceName(currentService);
$.get( "/api/export_xls_data", { url : currentService, projectname : projectName} ).done(function( data ) {
});
});
</script>
In my controller :
exportXLS : function(req,res)
{
var request = require('request');
var categories;
//get informations
request(url + "/places", function (error, response, body) {
categories = JSON.parse(body);
/*
* Parsing tacks 3 seconds max
*/
//if file exists delete and create file
fs.exists(fileName, function (exists) {
if(exists){
fs.unlinkSync(fileName);
}
fs.writeFile(fileName, xls, 'binary',function(err){
if(err){
console.log(err);
res.status(500);
return res.send("");
}else{
var downloadLink = req.headers.host+'/xls/'+currentProject.split(' ').join('')+'_data.xls';
console.log(downloadLink);
return res.view('import_export_data_page',{link : downloadLink});
});
});
}
}
My file is created. My link works but my view is not reloaded.
Your view is not reloaded because your making an AJAX call. There is nothing in your code to tell the page to reload the view.
I think you want to change this:
$.get( "/api/export_xls_data", { url : currentService, projectname : projectName} ).done(function( data ) {});
to:
window.location.href = '/api/export_xls_data?url=' + currentService + '&projectname=' + projectName

Resources