How to display sub documents from mongodb to next js application - javascript

I am trying to display sub documents which is orderSchema.
github repo link - https://github.com/Sarab71/Git-optics
Please check out my repo link pages/user/[id]
import mongoose from 'mongoose'
const orderSchema = new mongoose.Schema({
rsph: { type: Number },
rcyl: { type: Number },
raxis: { type: Number },
lsph: { type: Number },
lcyl: { type: Number },
laxis: { type: Number },
add: { type: Number },
frame: { type: String },
lens: { type: String }
}, {
timestamps: true
});
const userSchema = new mongoose.Schema({
name: { type: String, required: true },
phone: { type: Number, required: true },
address: { type: String, required: true },
orders: [orderSchema]
}, {
timestamps: true
});
export default mongoose.models.User || mongoose.model('User', userSchema)
getServerSideProps function I have tried alot of things still I am not able to get orderSchema and Display it.
export async function getServerSideProps({ params: { id } }) {
const res = await fetch(`${baseUrl}/api/user/${id}`)
const data = await res.json()
return {
props: { user: data }
}
}

Related

how to wait for variable update for new calculation in javascript

Hey I'm trying to build dashboard for calculate my medicine supplier total outstanding using nextjs.
*below *is my **createPurchase **api.
`
import PurchaseOrder from '../../models/PurchaseOrder'
import Supplier from '../../models/Supplier'
import connectDB from '../../middleware/mongoose';
import Medicine from '../../models/Medicine';
const handler = async (req, res) => {
if (req.method === 'POST') {
const medicines = [];
let totalOrderAmount = 0;
let totalPaybleGst = 0;
req.body.medicines.forEach(async medicine => {
let medicineOne = await Medicine.findById(medicine.medicine)
let newQuantity = parseInt(medicineOne.quantity) + parseInt(medicine.quantity)
const filter = { _id: medicine.medicine };
const update = { quantity: newQuantity };
await Medicine.findByIdAndUpdate(filter, update);
let newmedi = {
name: medicine.name,
company: medicine.company,
medicine: medicineOne,
quantity: newQuantity,
pack_detail: medicine.pack_detail,
category: medicine.category,
batch: medicine.batch,
mrp: medicine.mrp,
rate: medicine.rate,
gst: medicine.gst,
totalAmount: medicine.totalAmount,
expiryDate: medicine.expiryDate
}
totalOrderAmount += medicine.totalAmount;
totalPaybleGst += medicine.gst * medicine.rate * medicine.quantity * 0.01;
medicines.push(newmedi);
})
const paidAmount = req.body.paidAmount
const supplierBeforeUpdate = await Supplier.findById(req.body.supplier);
const newOustanding = supplierBeforeUpdate.totalOutstanding + totalPaybleGst + totalOrderAmount - paidAmount;
const filter = { _id: req.body.supplier };
const update = { totalOutstanding: newOustanding };
await Supplier.findOneAndUpdate(filter, update);
const supplierAffterUpdate = await Supplier.findById(req.body.supplier);
const purchaseOrder = await PurchaseOrder.create({
supplier: supplierAffterUpdate,
createdBy: req.body.createdBy,
medicines: medicines,
paybleGst: totalPaybleGst,
totalAmount: totalOrderAmount,
grandTotal: totalPaybleGst + totalOrderAmount,
paidAmount: paidAmount
})
res.status(200).json({ success: true, purchaseOrder: purchaseOrder })
}
else {
res.status(400).json({ error: "This method is not allowed" })
}
}
export default connectDB(handler);
`
this is my purchaseOrder Schema
`
const mongoose = require('mongoose');
const { Schema, model, models } = mongoose;
const medicinePurchaseSchema = new Schema({
name: { type: String, required: true },
company: { type: String, required: true },
medicine: {
type: mongoose.Schema.Types.ObjectId,
required: true,
ref: 'Medicine'
},
quantity: { type: Number, required: true },
pack_detail: { type: String, required: true },
batch: { type: String, required: true },
mrp: { type: Number, required: true },
rate: { type: Number, required: true },
gst: { type: Number, required: true },
totalAmount: { type: Number, required: true },
expiryDate: { type: Date, required: true }
});
const purchaseOrderSchema = new Schema({
supplier: { type: Object, required: true},
createdBy: { type: String, required: true },
medicines: [medicinePurchaseSchema],
paybleGst: { type: Number, required: true },
totalAmount: { type: Number, required: true },
paidAmount: { type: Number, required: true },
grandTotal: { type: Number, required: true }
}, { timestamps: true })
const PurchaseOrder = models.PurchaseOrder || model('PurchaseOrder', purchaseOrderSchema);
export default PurchaseOrder;
`
`
const mongoose = require('mongoose');
const { Schema, model, models } = mongoose;
const medicineSchema = new Schema({
name: { type: String, required: true },
company: {type: String, required: true},
pack_detail: {type: Number, required: true},
quantity: { type: Number, required: true },
category: { type: String, required: true },
status: { type: String, required: true }
}, { timestamps: true });
const Medicine = models.Medicine || model('Medicine', medicineSchema);
export default Medicine;
`
this is my Medicine schema
but problem is I got **totalOrderAmount **and **totalPayableGst **is **0 **in newOutstanding calculation, i think my newOutstanding calculation line is executing before updating my these variable in medicines.each function.
How can I fix this, im trying since 2 days but i didn't get any solution.
anyone have any solution.
That forEach method call will execute synchronously and doesn't await any promises. The callbacks do have await, but those affect only the async function they occur in, not the forEach method.
Instead of using forEach, use map, so that you get back the array of promises (as the async callbacks return promises). To make sure those promises resolve to something useful, have those callbacks return the newmedi. With Promise.all you can then know when all those promises resolved, and get all the medicine values to store in the medicines array, and only continue with the rest of the function when that is done:
// Not forEach, but map, and await all returned promises
const medicines = await Promise.all(req.body.medicines.map(async medicine => {
/* ...rest of your callback code... */
return newmedi; // Don't push, but return it
}));

Failed to delete the a comment on post?

I'm trying to delete a comment on a post, but I'm unable to find the comment. When I'm console.log(post.comments) it shows me all the comments but still, I can't find the comment. The error was Comment not found which I wrote to find that comment is still there or not. But the comment was there I matched the id with it. Help me I'm new to NodeJs. Help me to fix this
*As a frontend I'm using react and redux I think the problem is in the backend, I've also tested with the postman. Can't delete the comment from postman.
here is the comment route and controller
router.route('/:id/comment/:comment_id').delete(protect, deleteComment);
export const deleteComment = asyncHandler(async (req, res) => {
const post = await Post.findById(req.params.id);
const comment = post.comments.find(
(comment) => comment._id === req.params.comment_id
);
if (!comment) {
res.status(404);
throw new Error('Comment not found');
}
//Check User
if (comment.user.toString() === req.user._id.toString()) {
post.comments = post.comments.filter(
({ id }) => id !== req.params.comment_id
);
await post.save();
return res.json(post.comments);
} else {
res.status(401);
throw new Error('User not authorized');
}
});
here is the post model
import mongoose from 'mongoose';
const postSchema = mongoose.Schema(
{
user: {
type: mongoose.Schema.Types.ObjectId,
ref: 'User',
required: [true, 'Please Author is required'],
},
title: {
type: String,
required: true,
},
desc: {
type: String,
required: true,
},
img: {
type: String,
},
isLiked: {
type: Boolean,
default: false,
},
isDisLiked: {
type: Boolean,
default: false,
},
likes: [
{
type: mongoose.Schema.Types.ObjectId,
ref: 'User',
},
],
disLikes: [
{
type: mongoose.Schema.Types.ObjectId,
ref: 'User',
},
],
comments: [
{
user: {
type: mongoose.Schema.Types.ObjectId,
ref: 'User',
},
text: {
type: String,
required: true,
},
name: {
type: String,
},
pic: {
type: String,
},
date: {
type: Date,
default: Date.now,
},
},
],
categories: {
type: Array,
},
},
{
timestamps: { createdAt: 'created_at', updatedAt: 'modified_at' },
}
);
const Post = mongoose.model('Post', postSchema);
export default Post;
When you access to the _id you are accessing the instance of the ObjectId
You should try to compare with the id, that is a string representation of the _id
const comment = post.comments.find(
(comment) => comment.id === req.params.comment_id
);

How to save Data In MongoDB ? Not all the Fields at one single time

I Have created a Schema to store user Details and Some information regarding it's test.
const mongoose = require("mongoose");
const schema = mongoose.Schema;
const userSchema = new schema({
name: { type: String },
gender: { type: String },
stream: { type: String },
email: {
type: String,
required: true,
unique: true,
match: /[a-z0-9!#$%&'*+/=?^_`{|}~-]+(?:\.[a-z0-9!#$%&'*+/=?^_`{|}~-]+)*#(?:[a-z0-9](?:[a-z0-9-]*[a-z0-9])?\.)+[a-z0-9](?:[a-z0-9-]*[a-z0-9])?/,
},
verified: { type: Boolean, default: false },
password: { type: String, required: true },
// For premium Calculations
test: {
type1Count: { type: Number, default: 0 },
type2Count: { type: Number, default: 0 },
type3Count: { type: Number, default: 0 },
},
testCompleted: [
{
testId: { type: String },
testDate: { type: Number },
testTypeNumber: { type: Number },
testTypeName: { type: Number },
testDurationInMinutes: {type: Number},
listOfQuestionId: [{ type: String }],
listOfCorrectAnswer: [{ type: Number }],
listOfAnswerByUser: [{ type: Number }],
totalNumberOfQuestion: { type: Number },
numberOfAttemptedQuestion: { type: Number },
numberOfUnattemptedQuestion: { type: Number },
numberOfCorrectAnswer: { type: Number },
numberOfWrongAnswer: { type: Number },
marksObtained: {type: Number},
isTestCompleted : {type: Boolean, default: false}
},
]
});
module.exports = mongoose.model("User", userSchema);
Now, I am not save all the data at a single time,
first, I will save only it's registration part like Name, Email, password.
code to register user...
const newUser = new User({
name,
email,
password,
});
const salt = await bcrypt.genSalt(10);
newUser.password = await bcrypt.hash(password, salt);
await newUser.save();
Now there is a user created in my database.
now I want to save this data ...
// some logics are there, but the data is fine ..
var paper = {
testId: Object.keys(user.testCompleted).length +1, // I choose Normal serialise Number starting from 1
testDate: Date.now(),
testTypeNumber: type,
testTypeName: testList[type - 1]["testName"],
testDurationInMinutes: testList[type - 1]["testDurationInMinutes"],
weightageOfQuestion: list[type - 1],
totalNumberOfQuestion: list[type - 1]["physics"] + list[type - 1]["chemistry"] + list[type - 1]["biology"],
listOfQuestionId: arrayOfQuestion,
listOfCorrectAnswer: arrayOfAnswer,
};
Now I have created a user earlier
and In the later stage, I have to save paper data in the testCompleted [] setion, which is a array of objects
and In the later stage i have to store this data .. in the same testCompleted [] setion,
const data = {
totalNumberOfQuestion: totalNumberOfQuestion,
numberOfAttemptedQuestion: attempt,
numberOfUnattemptedQuestion: totalNumberOfQuestion - attempt,
numberOfCorrectAnswer: attempt - wrong,
numberOfWrongAnswer: wrong,
marksObtained: marks,
isTestCompleted: true
}
Please help me, how to save data partially in mongodb at any points ?
2 ways for updating array inside documents:
Find the document then use push() for adding into array then call .save().
const userToUpdate = await User.find({_id:userId})
userToUpdate.testCompleted.push(data)
userToUpdate.save()
Using findOneAndUpdate() or update() and $push
User.update(
{ _id: userId },
{ $push: { testCompleted: data } },
done
);
Reference: using_nodejs_and_mongoose_to_update_array

My ObjectType is returning an empty object [duplicate]

This question already has answers here:
How to deal with cyclic dependencies in Node.js
(16 answers)
Closed 3 years ago.
So i have two objecttypes and i'm trying to include them to make relationships, one of them works and one of them just returns an empty object and i can't figure out why.
this one works, it console logs the ranktype and works fine
const Rank = require('../model/RankModel')
const { RankType } = require('./rank')
console.log(RankType)
/**
* Defines Branch Type
*/
const BranchType = new GraphQLObjectType({
name: "Branch",
fields: {
id: { type: GraphQLID },
name: { type: GraphQLString },
color: { type: GraphQLString },
ranks: {
type: GraphQLList(RankType),
resolve: async (branch) => {
return await Rank.find({branch: branch.id})
}
}
}
})
module.exports.BranchType = BranchType
this is the one thats breaking
const Rank = require('../model/RankModel')
const Branch = require('../model/BranchModel')
const { BranchType } = require('./branch')
console.log(BranchType)
/**
* Defines Rank Type
*/
const RankType = new GraphQLObjectType({
name: "Rank",
fields: {
id: { type: GraphQLID },
name: { type: GraphQLString },
shortHand: { type: GraphQLString },
branch: {
type: BranchType,
resolve: async (rank) => {
return await Branch.findById(rank.branch)
}
}
}
})
module.exports.RankType = RankType
this givs me an error of "message": "The type of Rank.branch must be Output Type but got: undefined."
Models/Relations:
BranchModel:
const mongoose = require('mongoose');
const Schema = mongoose.Schema;
let branchSchema = new Schema({
name: {
type: String,
required: true,
unique: true
},
color: {
type: String,
required: true,
unique: true
},
ranks: [{
type: Schema.Types.ObjectId,
ref: 'Rank'
}]
});
module.exports = mongoose.model('Branch', branchSchema)
RankModel
const mongoose = require('mongoose')
const Schema = mongoose.Schema
let rankSchema = new Schema({
name: {
type: String,
required: true,
unique: true
},
shortHand: {
type: String,
required: true,
unique: true
},
branch: {
type: Schema.Types.ObjectId,
ref: 'Branch'
}
});
module.exports = mongoose.model('Rank', rankSchema);
Answer!!!!!!
/**
* Defines Rank Type
*/
const RankType = new GraphQLObjectType({
name: "Rank",
fields: () => ({
id: { type: GraphQLID },
name: { type: GraphQLString },
shortHand: { type: GraphQLString },
branch: {
type: require('./branch').BranchType,
resolve: async (rank) => {
console.log(rank.branch)
return await Branch.findById(rank.branch)
}
}
})
})
module.exports.RankType = RankType
Looks to me like you need to destructure BranchType like you did when requiring RankType, based what I can see from your module.exports
change
const BranchType = require('./branch')
to
const { BranchType } = require('./branch')

How to save data in mongoDB and Schema is like bellow

Here is my schema by using mongoose npm package.
var StatusSchema = new mongoose.Schema({
empName: {
projectName: { type: String },
clientName: { type: String },
statusLastWeek: { type: String },
statusThisweek: { type: String },
planNextWeek: { type: String }
}
});
Here is my nodejs code to update the data
var Status = mongoose.model('Status', StatusSchema);
module.exports = Status;
Description: Want save data in MongoDB, data schema is like above mentioned,
save saving data is sored loke as bellow.
Inside Mongo DB :
{ "_id" : ObjectId("5d92f4aba4695e2dd90ab438"), "__v" : 0 }
{ "_id" : ObjectId("5d92f4b4a4695e2dd90ab439"), "__v" : 0 }
Expected collection in MongoDB :
Dave Smith {
projectName: BLE Mesh,
clientName: Tera,
statusLastWeek: BLE Scan,
statusThisweek: BLE List View,
planNextWeek: Mqtt config
}
Here you can see my NodeJS code :
router.post ('/update', (req,res,next)=>{
userStatus = new wkStatus(req.body)
userStatus.save()
.then(status => {
res.redirect('/success');
console.log ("Status saved in DB")
})
.catch(err => console.log(err))
// return next;
});
//You can use ODM like mongoose and define a schema with mongoose.Schema. You can just
// see mongoose module document from npm. Use .save() for save an object in DB.
// Example :
// schema as admin
const mongoose = require('mongoose');
mongoose.Promise = global.Promise;
const Schema = mongoose.Schema;
const bcrypt = require('bcrypt-nodejs');
const sha256 = require('sha256')
const adminSchema = new Schema({
fullName: { type: String, required: true },
userName: { type: String },
noc: { type: String, required: true },
mobileNumber: { type: String, required: true },
email: { type: String },
chacommAddress: {
contactPerson: { type: String },
country: { type: String },
address: { type: String },
city: { type: String },
pinCode: { type: String },
state: { type: String },
stateCode: { type: String },
},
address: {
country: { type: String },
city: { type: String },
pinCode: { type: String },
state: { type: String },
stateCode: { type: String },
address: { type: String },
CIN: { type: String },
GSTIN: { type: String }
},
password: { type: String, required: true },
userType: { type: Number, required: true },
createdAt: { type: Date, required: true },
uploadFile: { type: String, required: true },
bankdetails: {
bankName: { type: String },
accountNo: { type: String },
ifscCode: { type: String },
accountType: { type: String },
accountName: { type: String },
cancelledChequeCopy: { type: String }
},
isActive: { type: Boolean },
invoiceString:{type:String},
invoiceValue:{type:Number},
accountantName :{type:String} ,
accountantDesignation : {type:String},
referredBy:{type:String}
});
adminSchema.methods.comparePassword = function (password) {
let password_hash = sha256(password);
return bcrypt.compareSync(password_hash, this.password);
}
adminSchema.pre('save', function (next) {
if (!this.isModified('password'))
return next();
let password_hash = sha256(this.password);
bcrypt.hash(password_hash, null, null, (err, hash) => {
if (err)
return next(err);
this.password = hash;
next();
});
});
//export schema
// module.exports = mongoose.model('Admin', adminSchema)
// for save:
const admin = require('admin')
var obj= new admin({
// values as per model defined
})
obj.save()
const wkStatus = new wkStatus({
_id: new mongoose.Types.ObjectId(),
projectName: req.body.projectName,
clientName: req.body.clientName,
statusThisweek: req.statusThisweek,
statusLastWeek: req.statusLastWeek,
planNextWeek: req.planNextWeek
})
Status
.save()
.then(result => {
res.status(201).json({
message: "Data Created Successfully",
})
console.log(result) // show the response
})
.catch(err => {
res.status(500).json({error:err})
})
Try this way hope it will work. If need more you can message me
The schema what you are trying to create itself is wrong.
empName: {
projectName: { type: String },
clientName: { type: String },
statusLastWeek: { type: String },
statusThisweek: { type: String },
planNextWeek: { type: String }
}
The above schema can create objects like below: "empName" cannot be dynamic.
empName: {
projectName: BLE Mesh,
clientName: Tera,
statusLastWeek: BLE Scan,
statusThisweek: BLE List View,
planNextWeek: Mqtt config
}
If you want to store like what you have shown, where empName dynamically then you should make empName as Map
See https://mongoosejs.com/docs/schematypes.html#maps

Categories