MongoDB Array not displaying - node.js

I want to query my MongoDB database to only fetch all the values in my array using my user_id
I have tried using the (schema.name), it not working out
// #route GET api/user/package
// #desc Get all package
// #access Private
router.get('/package',
passport.authenticate('jwt', { session: false }),
(req, res) => {
Shipments.find({_id : req.user._id},{paymentStatus: "incomplete"})
.then(shipments => res.status(200).json(shipments.packages))
.catch(err =>res.status(404).json({ nopackages: 'No package found for you now' }));
});
Here is my expected result
"packages": [
{
"date": "2019-09-23T12:52:14.226Z",
"_id": "5d88bffe2a6ed7b8d9873548",
"category": "hazard",
"quantity": "10",
"description": "a valueablegoods",
"length": 10,
"height": 20,
"width": 12,
"weight": 12
},
{
"date": "2019-09-23T12:52:58.129Z",
"_id": "5d88c02a2a6ed7b8d9873549",
"category": "hazard",
"quantity": "10",
"description": "a valueablegoods",
"length": 10,
"height": 20,
"width": 12,
"weight": 12
}
],
but postman didn't return any value but brings a status 200, but returns nobody

Try Shipments.findOne()
This happens because you are getting a single user detail.

All i did was change find to findOne. This solve the problem
router.get('/package',
passport.authenticate('jwt', { session: false }),
(req, res) => {
Shipments.findOne({ $and: [{ _id : req.user._id }, { paymentStatus: "incomplete" }] })
.then(shipments => res.status(200).json(shipments.packages))
.catch(err =>res.status(404).json({ nopackages: 'No package found for you now' }));
});
it may help u

Related

Remove object from nested array in MongoDB using NodeJS

I can see that this question should have been answered here, but the code simply doesn't work for me (I have tried multiple, similar variations).
Here is my data:
[{
"_id": {
"$oid": "628cadf43a2fd997be8ce242"
},
"dcm": 2,
"status": true,
"comments": [
{
"id": 289733,
"dcm": 2,
"status": true,
"clock": "158",
"user": "Nathan Field",
"dept": "IT",
"department": [],
"dueback": "",
"comment": "test 1"
},
{
"id": 289733,
"dcm": 2,
"status": true,
"clock": "158",
"user": "Nathan Field",
"dept": "IT",
"department": [],
"dueback": "",
"comment": "test 2"
}
],
"department": [],
"dueback": ""
}]
And here is my code
const deleteResult = await db.collection('status').updateOne(
{ "dcm": comments.dcm },
{ $pull: { "comments": { "id": comments.id } } },
{ upsert: false },
{ multi: true }
);
Absolutely nothing happens...
So the issue ended up being something to do with running multiple update operations within one function. I have a database connection function like this:
const withDB = async (operations, res) => {
try {
const client = await MongoClient.connect('mongodb://localhost:27017', { useNewUrlParser: true });
const db = client.db('collection');
await operations(db);
client.close();
} catch (error) {
res.status(500).json({ message: 'Error connecting to db', error });
}
}
And then I call this by using:
withDB(async (db) => {
await db.collection('status').updateMany(
{ "dcm": comments.dcm },
{ $pull: { "comments": { "id": comments.id } } },
{ multi: true }
);
});
The issue occurred it would seem because I had two of these update operations within one withDB function. I have multiple operations in other instances (update item, then fetch collection), but for some reason this caused an issue.
I created a separate call to the withDB function to perform the '$pull' (delete) request, and then updated the array with the new comments.
To check that there was nothing wrong with my actual query, I used Studio3T's IntelliShell feature. If I'd done that sooner I would saved myself a lot of time!

MongoDb find all objects that contain nested value

This is my user object sent as token in req:
{
"_id": "6212aba16653621e67393549c",
"name": "User",
"email": "user#gmail.com",
"__v": 0
}
This is my get function code:
const getSharedLists = asyncHandler(async (req, res) => {
const lists = await List.find({
sharedWith: { email: req.user.email },
});
res.status(200).json(lists);
});
This is what object looks like:
{
"_id": "621817233300dfff68e23710",
"user": "6212ab33383621e67393549c",
"listName": "test update",
"private": true,
"items": [
{
"itemName": "Bananas",
"quantity": 3,
"isBought": false,
"isle": "isle",
"_id": "621b043622147906eece2e72"
},
],
"sharedWith": [
{
"email": "user#gmail.com",
"_id": "621bdbf0791a322534284c49"
}
],
"createdAt": "2022-02-24T23:39:25.668Z",
"updatedAt": "2022-02-27T21:21:03.584Z",
"__v": 0,
},
I keep getting empty array back, even when hard code req.user.email as "user#gmail.com" for example. I need to find all lists on MongoDb that have my email in array of sharedWith.
Can somebody help please. Apparently I'm using List.find method wrong but can't seem to figure out the syntax.
You need (.) dot notation.
const lists = await List.find({
"sharedWith.email" : req.user.email
});
Sample Mongo Playground
Reference
Specify a Query Condition on a Field Embedded in an Array of Documents

How to pull out object heading from an array

I have a JSON response structure like this
{
"_id": "620e97d76ca392a43097cca6",
"user": "620295cbd67ece90802d2522",
"orderId": "EnrL7C",
"Items": [
{
"product": {
"name": "Fresh Salad",
"id": "61f2911723ff35136c98ad3e"
},
"quantity": 1,
"price": 1250,
"_id": "620e97d76ca392a43097cca7"
},
],
}
But i want the product not to be an object, so it should look like this
{
"_id": "620e97d76ca392a43097cca6",
"user": "620295cbd67ece90802d2522",
"orderId": "EnrL7C",
"Items": [
{
"name": "Fresh Salad",
"id": "61f2911723ff35136c98ad3e",
"quantity": 1,
"price": 1250,
"_id": "620e97d76ca392a43097cca7"
},
],
}
This is my code responsible for the response output
exports.getOrder = (req,res) => {
Order.findOne({orderId: 'EnrL7C'})
.populate("Items.product", "name")
.exec((error, order) => {
if(error) return res.status(400).json({ error });
if (order) {
return res.json(order);
}else{
return res.json(['No order found']);
}
});
Sometimes when I'm too lazy to look up all the mongoose documentation and figure out what version I'm on etc, I use the .lean() to just convert it to a normal JS object, which I'm way more comfortable with.
exports.getOrder = (req, res) => {
Order.findOne({ orderId: "EnrL7C" })
.lean() // add lean
.populate("Items.product", "name")
.exec((error, order) => {
if (error) return res.status(400).json({ error });
if (order) {
// fix the structure in javascript
order.Items = order.Items.map((item) => {
const flat = {
...item.product,
...item,
};
delete flat.product;
return flat;
});
return res.json(order);
} else {
return res.json(["No order found"]);
}
});
};
Let me know if that doesn't work, so I can update the answer.

Traversing array and changing object values

I'm trying to update the values ​​of my payments array objects
{
"balance": 109610,
"gifts": [],
"orders": [],
"payments": [{
"isPaid": 0,
"status": "Pending",
"address": "3KsdQbmADyz1KNN7qqX1yZcMXBbfFCm31r",
"date": 1624057559970
}, {
"isPaid": 0,
"status": "Pending",
"address": "3FYQK6YiAaL8fEbDWaXYw38CJN3K2y5dPD",
"date": 1624058531601
}],
"isVendedor": false,
"isAdmin": true,
"createdAt": {
"$date": "2021-06-17T21:10:15.020Z"
},
"username": "teste",
"email": "teste#teste.com",
"password": "$2a$10$qUNkorDuvbf.AYLTvjNc4ebKyNgLa7L9NoTBwAIV8.BfN51umaD9O",
"__v": 3
}
First, I look for the object of the user who made a request to my server
const userPayment = await User.find({"payments.address": notification.address}).exec();
Then I go through the user object and find it until I find the position where I find notification.address again
userPayment.forEach((AllPayments, index) => {
AllPayments.payments.forEach((payment, index) => {
if (payment.address == notification.address) {
if (payment.isPaid || payment.status != "Pending")
return res.json({
success: false,
error: "Payment Already Processed!",
});
const valueToDeposit = Math.round(notification.fiat_amount);
console.log(
userPayment[0].payments[index].isPaid,
userPayment[0].payments[index].status
);
// Set payments[index].isPaid = true
// Set payments[index].status = "Paid"
});
});
So I tried to make these 3 ways and none of them was successful.
userPayment[0].balance += valueToDeposit; // this works when save() is triggered
userPayment[0].payments[index].isPaid = 1; // this doesnt works when save() is triggered
userPayment[0].payments[index].status = "Paid"; // this doesnt works when save() is triggered
userPayment[0].updateOne({"payments.address": notification.address}, { $set: { "payments.$.isPaid": 1,"payments.$.status":"Paid" } },(err, result) => { console.log(err, result); }); this doesnt works
userPayment[0].save()

REST API using Nodejs Mongoose Express

{
"_id": "58be5a4a031372098578b1d6",
"name": "A",
"email": "abc#gmail.com",
"username": "A.a",
"password": "$2a$05$GAF1hP91EowKUTKr14ASL.MRd2lOjotfOgVlEghwnqctNcIe5seNW",
"latitude": 12,
"longitude": 72,
"profilePic": "images/A.png",
"__v": 9,
"isBuddyEnabled": true,
"friendRequests": [
{
"friendId": "58be7aa0c204cb134068975d",
"isAccepted": true
},
{
"friendId": "58bf8cb4c26d5811b188a600",
"isAccepted": false
}
],
"friends": [
"58be7aa0c204cb134068975d"
],
"networkContacts": [
{
"profession": "doctor"
}
],
"interests": [
"sports",
"music"
]
}
I have the above json for a single user , now i need the array of such json with all info whose friendRequest isAccepted is false which means these requests are pending for him,
for eg: when i hit api/requests/58be5a4a031372098578b1d6 => i have to get info of id 58bf8cb4c26d5811b188a600
till now i was able to retreive the ids whose request was not accepted via following query
app.post('/api/users/requests/:id'function(req,res){User.find({"_id":req.params.id})
.find({"friendRequests.isAccepted":false},function(err,callback){}})
You can use array filter to pop out the subdocument in array based on the filter
User.find({"_id":req.params.id}, function (err, user) {
var friendRequests = user.friendRequests.filter(function (fr) {
return fr.isAccepted == false;
}).pop();
console.log(friendRequests); //logs { "friendId": "58bf8cb4c26d5811b188a600", "isAccepted": false
});

Resources