I am following a MEVN stack tutorial: https://appdividend.com/2018/11/21/mevn-stack-tutorial-with-example-from-scratch/#8_Setup_and_connect_MongoDB_database
In section 10 he shows how to create routes for adding, deleting, updating and reading data in a mongoDB database using mongoose.
This is part of that code:
// post.model.js
const express = require('express');
const postRoutes = express.Router();
// Require Post model in our routes module
let Post = require('./post.model');
// Defined store route
postRoutes.route('/add').post(function (req, res) {
let post = new Post(req.body);
post.save()
.then(() => {
res.status(200).json({'business': 'business in added successfully'});
})
.catch(() => {
res.status(400).send("unable to save to database");
});
});
Is there a specific reason he has put {'business': 'business in added successfully'} in the JSON for the 200 response? or can that just be anything? Also i'm not entirely sure what i would put in it for my specific scenario where i am trying to add, delete, update and read data about users in a 'users' collection.
It can be anything, just to information that received request is successful and created the records. He added some response to that request.
Related
I have created an app that has a cart that sends data to the backend, now when I restore I want to preserve the data and display the same data as before.
I have used the PUT method instead of POST and when I send and get data from Firebase, data is preserved on reload and the data from the database is visible, but if I use my own backend in Node.js, I am not able to get the data on reload. This is where I am fetching data from the backend.
export const fetchCartData=()=>{
return async(dispatch)=>{
const getData= async() =>{
const response = await fetch('https://localhost:5000/');
if(!response.ok){
throw new Error('Something went wrong');
}
const info=await response.json();
return info;
};
try{
const data= await getData();
console.log("Here is data from Firebase", data);
dispatch(order_action.replaceCart({
items:data.items || [],
totalQuantity:data.totalQuantity || 0
}));
}catch(error){
dispatch(show_action.showNotification({
status:"failed",
title:"Error...",
message:"Some error occurred."
}));
}
}
}
Tha backend Code is:
const express=require("express");
const bodyParser=require('body-parser');
const cors=require('cors');
const app=express();
app.use(cors());
app.use(bodyParser.json());
app.put("/",function (req,res) {
const data={
items:req.body.items,
totalQuantity:req.body.totalQuantity
}
console.log(data);
console.log("END");
res.send({data});
})
app.get("/",function (req,res) {
console.log(req.body);
const data={
items:req.body.items,
totalQuantity:req.body.totalQuantity
}
res.send({data})
})
app.listen(5000,function () {
console.log("Running on 5000");
})
You can use localStorage on the browser i.e at the client-side. Whenever there is any change in the cart do these steps:
Send data to the backend API using the PUT method and store it in DB or cache(based on the website and users you are dealing with).
Once you get the response from API, update your localStorage data.
localStorage.set('cart', JSON.stringify(dataFromAPI));
Now, on every reload you will always be getting the last updated cart data.
when I send and get data from Firebase, data is preserved on reload
and the data from the database is visible
Just for your knowledge, firebase is a database and when you save data, it is persistent. Now, on reload you must be calling the firebase DB to get the data back that's why you see the data on the client otherwise it is impossible to get data without caching or saving it locally.
You can store/contain the data in a JSON file and reuse the data.
If the data is a stream of data, then you do only need some latest records; you can perform some JavaScript array operations to perform a First-In-First-Out operations by containing up to like 50 or 100 objects/records in the JSON file, so you can later retrieve/reuse.
const fs = require("fs");
const path = require("path");
const data = fs.readFileSync(path.resolve(__dirname,"filename.json");
const data = JSON.parse(data);
data.contentArray.push(req.body); //or any other data
const data = JSON.stringify(data);
fs.writeFileSync(path.resolve(__dirname,"filename.json",data,"utf-8");
/*
filename.json sample
{
"contentArray":[
{
"key":"value"
},
{
"key":"value"
}
]
}
*/
You can find ways to literally store/contain the data in a '.json' file or '.csv' file. I would recommend storing the data in a JSON file, which is way easier.
I wrote two node js applications, they are fetching data properly but they are not taking post values 1st applications is this TinderClone this is just an api with no frontend i am posting data from postman and it is returning auto generated id but not the data i am posting,
Other application i cloned from github, it has proper frontend with working CRUD, but when i tried to post values from postman it wont take any values it will just add record in database with null values, so is there anything wrong im doing on postman? cause it is still working if i post data with the form on its frontend the application url is MernCRUD
Postman Screenshots:
posting data,
fetching data
Code:
//Cards Schema (Cards.js)
import mongoose from 'mongoose'
const cardSchema = mongoose.Schema({
name: String,
imgUrl: String
})
export default mongoose.model('cards', cardSchema)
//Posting Data (Server.js)
app.post('/tinder/cards', (req, res) => {
const dbCard = req.body;
Cards.create(dbCard, (err, data) => {
if(err){
res.status(500).send(err)
}
else{
res.status(201).send(data)
}
})
})
//Fetching Data
app.get('/tinder/cards', (req, res) => {
Cards.find((err, data) => {
if(err){
res.status(500).send(error);
}
else{
res.status(200).send(data);
}
});
});
in postman you don't have to add content type manually . You should select json from the drop down and it will add content type by default. **
Now you have text in your raw dropdown change to json .
**
I followed a tutorial for making an api with express and postgres. I can get all my data in json form no problem. But I have no idea how to use the data in the frontend of a site.
These are what I have in 2 different files that are linked.
index.js:
const db = require('../queries')
router.get('/classes/:id', db.getClassById)
router.get('/classes/:id/edit', db.getClassById, (req, res) => {
res.render('dashboard/editClass')
})
queries.js:
const getClassById = (req, res) => {
const id = parseInt(req.params.id)
pool.query('SELECT * FROM classes WHERE state = 1 AND classId = $1', [id], (err, results) => {
if(err){
throw err
}
res.status(200).json(results.rows)
})
}
module.exports = {
getClassById
}
The getClassById query is called by the express middleware and automatically sends the json data to the page, which will not allow the res.render('dashboard/editClass') to work.
So how would I call this query so that I can fill in a form with the data from the query so a user can see the existing data and make any changes they want?
Thanks to Mark and Marc who commented, I realized I needed to fetch the data from my own api when rendering the front end pages. I am now using axios to get this done in node and so far it is doing exactly what I was looking for.
I am using Node.js + Express for backend and MongoDB for database. My problem is that when I write data to the database, the subdocuments remain empty, i.e. I am not able to write data into the subdocuments.
Response
Fields employeeInformation up to cancellationReason are all subdocuments. When I do a console.log of req.body, I can see that my fields are populated with the correct values, but in MongoDB and in the response, there is no data. I can also write fine using Postman.
Here is my app.post code:
// POST
app.post('/create-incident', (req, res) => {
let incidentNumber = functions.createIncidentNumber();
let status = 'New';
const incidentHeader = new IncidentHeader({
incidentNumber: incidentNumber,
status: status,
employeeInformation: req.body.employeeInformation,
incidentDetail: req.body.incidentDetail,
spi: req.body.spi,
investigationDetail: req.body.investigationDetail,
recommendation: req.body.recommendation,
dataPrivacyDetail: req.body.dataPrivacyDetail,
infrastructureDetail: req.body.infrastructureDetail,
dataElement: req.body.dataElement,
processIncident: req.body.processIncident,
legislation: req.body.legislation,
dataPrivacyEducation: req.body.dataPrivacyEducation,
rca: req.body.rca,
approval: req.body.approval,
auditTrail: req.body.auditTrail,
cancellationReason: req.body.cancellationReason
});
console.log(`req.body: ${JSON.stringify(req.body)}`);
incidentHeader
.save()
.then(IncidentHeader => {
res.status(200).send(JSON.stringify(IncidentHeader));
console.log('Saved to IncidentHeader.');
})
.catch(e => {
return res.status(400).send(e);
console.log('Unable to save to IncidentHeader.');
});
});
What could I be doing wrong here?
Here is the link to my GitHub project should you wish to inspect the code further. Thank you in advance.
GitHub Repo
I've been researching this issue for several hours now and found something odd. Using ExpressJS, Firebase, and React for a small app, and need to call the Firebase Database via the Express Backend, and I also need to make post requests to store data in the database via the Express Backend.
Functionality: I make a post request to the backend to add data to the database. Since Firebase is real time db, the data will immediately reflect on the page.
Problem: The issue is, when I make a post call to the backend and that completes, the page refreshes but the data doesn't show because of this
ERROR: [ERR_HTTP_HEADERS_SENT]: Cannot set headers after they are sent to the client
/**
* Add new note to Firebase
* Real-Time Database
*/
app.post('/addNote', (req, res)=> {
var title = req.body.note.title;
var body = req.body.note.body;
var userId= req.body.note.uid;
db.notes.push({
title: title,
body: body,
uid: userId
})
res.send("Success")
})
app.get('/all', (req, res, next)=> {
db.notes.on('value', snapshot => {
return res.send(snapshot.val());
})
})
Possible Solution: I've found that using the code below, I can make a post request, manually refresh the page, and the data will reflect with no header error. I'm trying to code the proper functionality but can't seem to figure out where the code is sending multiple responses with the db.notes.on because I'm only sending res.send one time. The clear difference is (.on listens and updates immediately, while .once requires manual refresh)
/**
* Add new note to Firebase
* Real-Time Database
*/
app.post('/addNote', (req, res)=> {
var title = req.body.note.title;
var body = req.body.note.body;
var userId= req.body.note.uid;
db.notes.push({
title: title,
body: body,
uid: userId
})
res.send("Success")
})
app.get('/all', (req, res, next)=> {
db.notes.once('value', snapshot => {
return res.send(snapshot.val());
})
})
An on("value" listener to Firebase will fire:
straight away with the current value of the data,
and will then later also fire when the data changes.
Since you're sending the data in the response to the client in #1, the response will be closed/finished by the time #2 happens.
By using a once("value" listener this problem doesn't happen, since once() removes the listener after #1.