How to find data within embedded documents array using id mongodb? - javascript

I am using mongodb with nodejs to find data in embedded document. strange fact is query works in database but not in actual nodejs code.
here is my data object:
{
"_id" : ObjectId("5c65866488a1c53464e46dc7"),
"cat_lang" : [
{
"_id" : ObjectId("5c65866488a1c53464e46dc8"),
"en" : "temp",
"it" : "temp"
}
],
"providers" : [
{
"_id" : ObjectId("5c65866488a1c53464e46dc9"),
"provider_name" : "temp0",
"url" : "http://uber.com",
},
{
"_id" : ObjectId("5c65866488a1c53464e46dca"),
"provider_name" : "temp1",
"url" : "http://uber2.com",
}
]}
I have tried these queries in the mongodb shell works perfectly fine.
db.sideservices.findOne({"_id" : ObjectId("5c65866488a1c53464e46dc7")},{providers: {$elemMatch: {"_id" : ObjectId("5c65866488a1c53464e46dca")}}})
AND
db.sideservices.find({"providers._id":ObjectId("5c65866488a1c53464e46dca")},{'providers.$':1})
But when using the same functions in nodejs, it returns the whole object instead document with the given id.
this.db.collection('sideservices').find({'providers':{'$elemMatch':{'_id':ObjectId('5c65866488a1c53464e46dca')}}}).toArray((err,res) => {...})

You can do this way
this.collection("sideservices").find({
"providers": { "$elemMatch": { "_id": ObjectId("5c65866488a1c53464e46dca") } }
})
.project({
"providers": { "$elemMatch": { "_id": ObjectId("5c65866488a1c53464e46dca") } }
})
.toArray((err,res) => {...})

Related

Gifted Chat disorganized messages

I have a problem with GiftedChat, the messages appear completely disorganized in the app and even looking for messages directly from the firebase (where it is correct), the app does not get a logical order. When sending is organized, however the problem is when you load the messages. I'm completely lost
loadMessages = async () => {
const { user } = this.props;
const matchId = this.props.navigation.getParam('matchId');
const data = (await firebase.database().ref(`matchs/${matchId}/messages`).limitToLast(300).once('value')).val();
let messages = [];
if(data){
Object.keys(data)
.forEach(messageId => {
let message = data[messageId];
if(_.get(message, 'user._id') !== user.uid) _.push(message);
messages.push(message);
});
}
this.setState(() => ({
messages,
}));
}
My JSON:
{
"-LkAMYoS3fySk46Pbpan" : {
"_id" : "f5ba3d9a-c346-4f79-b371-c5d54798567e",
"createdAt" : 1563558815857,
"text" : "First message",
"user" : {
"_id" : "BVY4MDwSaaSDI2bAGjwkZlYktsK2",
"avatar" : "https://firebasestorage.googleapis.com/v0/b/wefound-760f2.appspot.com/o/users%2FBVY4MDwSaaSDI2bAGjwkZlYktsK2%2Fphotos%2Fk1xuqv26wdrjxoxmp8m.jpg?alt=media&token=7c16a0e4-2cb8-45a5-83a4-635d49c71180",
"name" : "Rafael"
}
},
"-LkAMZiITDxHE1WfCBGC" : {
"_id" : "c2755b48-136d-4a68-b283-377ebac7df8e",
"createdAt" : 1563558819564,
"text" : "Second message",
"user" : {
"_id" : "BVY4MDwSaaSDI2bAGjwkZlYktsK2",
"avatar" : "https://firebasestorage.googleapis.com/v0/b/wefound-760f2.appspot.com/o/users%2FBVY4MDwSaaSDI2bAGjwkZlYktsK2%2Fphotos%2Fk1xuqv26wdrjxoxmp8m.jpg?alt=media&token=7c16a0e4-2cb8-45a5-83a4-635d49c71180",
"name" : "Rafael"
}
},
"-LkAM_l4o_w_QeCsYRc8" : {
"_id" : "65772152-afd9-4353-b752-ac65978a536d",
"createdAt" : 1563558823838,
"text" : "Third message",
"user" : {
"_id" : "BVY4MDwSaaSDI2bAGjwkZlYktsK2",
"avatar" : "https://firebasestorage.googleapis.com/v0/b/wefound-760f2.appspot.com/o/users%2FBVY4MDwSaaSDI2bAGjwkZlYktsK2%2Fphotos%2Fk1xuqv26wdrjxoxmp8m.jpg?alt=media&token=7c16a0e4-2cb8-45a5-83a4-635d49c71180",
"name" : "Rafael"
}
},
"-LkAMcSSTOP7L1CwyiU4" : {
"_id" : "e69f3a72-0f4e-4c06-a763-518ef1984aa0",
"createdAt" : 1563558834859,
"text" : "Fourth message",
"user" : {
"_id" : "BVY4MDwSaaSDI2bAGjwkZlYktsK2",
"avatar" : "https://firebasestorage.googleapis.com/v0/b/wefound-760f2.appspot.com/o/users%2FBVY4MDwSaaSDI2bAGjwkZlYktsK2%2Fphotos%2Fk1xuqv26wdrjxoxmp8m.jpg?alt=media&token=7c16a0e4-2cb8-45a5-83a4-635d49c71180",
"name" : "Rafael"
}
},
"-LkAMduvBrEnUG6POGKt" : {
"_id" : "897b2042-25dc-46ec-a5f3-5bdc1fc355dd",
"createdAt" : 1563558840853,
"text" : "Fifth message",
"user" : {
"_id" : "BVY4MDwSaaSDI2bAGjwkZlYktsK2",
"avatar" : "https://firebasestorage.googleapis.com/v0/b/wefound-760f2.appspot.com/o/users%2FBVY4MDwSaaSDI2bAGjwkZlYktsK2%2Fphotos%2Fk1xuqv26wdrjxoxmp8m.jpg?alt=media&token=7c16a0e4-2cb8-45a5-83a4-635d49c71180",
"name" : "Rafael"
}
}
}
I gave console.tron.log () in the messages and they appear disorganized exactly the same is in the app, the problem is in the component?
1 - refers to the function that loads the messages.
2 - JSON file
There are two steps to ordering the data:
Telling the Firebase Database server to return the child nodes in the correct order.
Maintaining that order in your client-side code.
As far as I can tell your code does neither of these, which means the nodes end up in whatever order your client uses for JSON properties (which are by definition unordered).
Let's first see how to retrieve the data in the correct order from Firebase:
const snapshot = (await firebase.database().ref(`matchs/${matchId}/messages`).orderByChild('createdAt').limitToLast(300).once('value'));
The above orders all child nodes by the value of their createdAt property, then returns the last 300 in order to the client.
You'll note that I don't call val() here yet. The reason for that is that snapshot.val() returns a JSON object, and properties in a JSON object have no defined order. So if you call .val() too early, you lose the ordering information that the server returned.
Next up is processing them in the client-side code to not lose that order, which depends on using DataSnapshot.forEach():
data.forEach((message) => {
messages.push(message.val());
})
Finally, I am able to solve this problem by sorting the JSON which is coming to from the server based on the date and time(CreatedAT).
If the JSON data stored in a variable called discussion then your code should be
discussion.sort(function compare(a, b) {
var dateA = new Date(a.createdAt);
var dateB = new Date(b.createdAt);
return dateB - dateA;
});
In your case, data or messages is the one which holds the JSON. Add this code once you get the code in JSON format.
Thank you.

Sending the result of a mongoDB view to another collection ( INSERT....SELECT from SQL )

I could create a big query, and turn it into a view. Let's call it DBA_VIEW.
db.DBA_VIEW.find()
I'm using noSQLbooster to interact with mongodb and I'm trying to insert the result of this view into another collection.
I don't want to "right click > export" because I need to do this via noSQLbooster itself.
I've seen some querie sthat can do the trick, but, as a SQL SERVER dba, I think I can't get the logic behind, let's say, this one below:
db.full_set.find({date:"20120105"}).forEach(function(doc){
db.subset.insert(doc);
});
how can I use such approach to do my taks?
I just need the result of that view from a collection, to be inserted in another collection, then after this we are going to export the data into a .json file or even a .TXT.
You can design the query in the following way so that the output is directly inserted in a new collection('subset' in this example) without iterating through the result set.
db.full_set.aggregate([
{
$match:{
"date":"20120105"
}
},
{
$out:"subset"
}
])
If 'full_set' has the following documents:
{
"_id" : ObjectId("5d423675bd542251420b6b8e"),
"date" : "20130105",
"name" : "Mechanic1"
}
{
"_id" : ObjectId("5d423675bd542251420b6b8f"),
"date" : "20120105",
"name" : "Mechanic2"
}
{
"_id" : ObjectId("5d423675bd542251420b6b90"),
"date" : "20120105",
"name" : "Mechanic3"
}
With the above query, the 'subset' collection would be having the following documents:
{
"_id" : ObjectId("5d423675bd542251420b6b8f"),
"date" : "20120105",
"name" : "Mechanic2"
}
{
"_id" : ObjectId("5d423675bd542251420b6b90"),
"date" : "20120105",
"name" : "Mechanic3"
}

Firebase retrieve data from a list of children without knowing the keys (Web)

I am working on a web application that allows some users to send others push notifications. The list of users "subscribed" to any one user is stored in a firebase database, the structure is as follows;
senderUserID
senderSubscribers
subscriberOneID
token: subToken
subscriberTwoID
token: subToken
subscriberThreeID
token: subToken
Basically I need to store the list of tokens in an array in order to use each of them to specify the clients receiving a push notification.
Here is my javaScript that returns the subscriber list 'Node'. In my case senderSubscribers is actually 'players'
firebase.database().ref('/users/'+currentUserId+'/players/').once('value').then(function(snapshot){
var allPlayersNode = snapshot.val();
console.log(allPlayersNode);
});
Console.log looks something like
firstUserID:Object
regID: the first subscribers token
secondUserID:Object
regID: the second subscribers token
JSON code:
"emails" : {
"kylebehiels#hotmail" : "vlHVHcIetlZp7zS8mm6GcwoFRsB3",
"test#gmail" : "hJuVfpGTJvRyP4qsA6xyyvgQDay1"
},
"users" : {
"hJuVfpGTJvRyP4qsA6xyyvgQDay1" : {
"email" : "test#gmail.com",
"first_name" : "kyle",
"games" : {
"placeholder" : "placeholder"
},
"last_name" : "behiels",
"practices" : {
"placeholder" : "placeholder"
},
"regid" : "c_z_KWeWorU:APA91bHORVZqSph-HikfxtO2XjvMnwudIymORoSm9t3gupKZ1fFIZCLxGUbX5dsrYooHHpeEiPXhcXEMu5Eo5-nwF8bBjw-OTwSbn_rujTuPVaCDOXUKp9mzIYqeZq7SFMaWssZfyKj7",
"workouts" : {
"placeholder" : "placeholder"
}
},
"vlHVHcIetlZp7zS8mm6GcwoFRsB3" : {
"email" : "kylebehiels#hotmail.com",
"first_name" : "kyle",
"games" : {
"placeholder" : "placeholder"
},
"last_name" : "behiels",
"players" : {
"hJuVfpGTJvRyP4qsA6xyyvgQDay1" : {
"playerRegID" : "c_z_KWeWorU:APA91bHORVZqSph-HikfxtO2XjvMnwudIymORoSm9t3gupKZ1fFIZCLxGUbX5dsrYooHHpeEiPXhcXEMu5Eo5-nwF8bBjw-OTwSbn_rujTuPVaCDOXUKp9mzIYqeZq7SFMaWssZfyKj7"
},
"vlHVHcIetlZp7zS8mm6GcwoFRsB3" : {
"playerRegID" : "cvZj3hb_zkk:APA91bEcmKlDlC5VKOI6wc1BvRI5mGgmWFA3QuTR3jH48l9fz565RhY2PEXE2GkXyhKXgb67qu7ieRlWF403q6rQPi0-xgGIbfvOkhGzopfyTFLNQg7ADgNHFAd1YfwwesbHjL5IHLZd"
}
},
"practices" : {
"placeholder" : "placeholder"
},
"regid" : "cvZj3hb_zkk:APA91bEcmKlDlC5VKOI6wc1BvRI5mGgmWFA3QuTR3jH48l9fz565RhY2PEXE2GkXyhKXgb67qu7ieRlWF403q6rQPi0-xgGIbfvOkhGzopfyTFLNQg7ADgNHFAd1YfwwesbHjL5IHLZd",
"workouts" : {
"placeholder" : "placeholder"
}
}
}
}

MongoDB and Mongoose: How to retrieve nested Object

I have the following documents in my mongodb collection:
{
"current" :
{
"aksd" : "5555",
"BullevardBoh" : "123"
},
"history" :
{ "1" : {
"deleted" : false,
"added" : false,
"date" : "21-08-2014"
}
},
{ "2" : {
"deleted" : false,
"added" : false,
"date" : "01-01-2013"
}
},
"_id" : ObjectId("53f74dad2cbfdc136a07bf16"),
"__v" : 0
}
I have multiple of these documents. Now I want to achieve two things with my Mongoose/Express API.
Query for all nested "current" in each document and retrieve them as JSON objects like such: {"aksd":"5555","BullevardBoh":"123"},{..},{..}.
Retrieve all history revisions (1,2...) where "date" is smaller than a given date.
As you can clearly see this is a kind of versioning I am trying to implement. I would also be interested if this kind of data structure will get indexed by MongoDB and if there is possibly a better way. (e.g. with arrays inside objects?)
This isn't working in MongoDB:
db.ips.findOne({current.aksd: {$exists:true}});
I think the quotes around the field are missing here:
db.ips.findOne({current.aksd: {$exists:true}});
This should work instead:
db.ips.findOne({"current.aksd": {$exists:true}});
While Ritesh's reply was a step in the right direction, I rather wanted to fetch the current object literal and its members inside the document not the whole document.
1.) Query for all nested "current" in each document
db.ips.find({"current":{$exists:true}}, {"current":1});
This is giving back all nested documents where the aksd literal is present:
{ "current" : { "aksd" : "5555", "BullevardBoh" : "123" }, "_id" : ObjectId("53f74dad2cb3dc136a07bf16") }
...
2.) Retrieving history revisions where date is smaller then a given date:
db.ips.find({"history.date": {$lt: "01-01-2014"}},{history:{$elemMatch:{date: {$lt:"01-01-2014"}}}});
Giving back the wanted nested date literal(s):
{ "historie" : [ { "date" : "01-01-2013", "added" : false, "deleted" : false } ], "_id" : ObjectId("53faf20f399a954b2b7736b6") }

searching for nested elements in mongodb, using api nodejs

At this moment I have in Node.JS API written a function
Board.find({ users : req.user._id})
It will find all documents where is id of user inside of array users,
for example
So this function will find this document.
{
"_id" : ObjectId("5a7f4b46f489dd236410d88a"),
"name" : "first",
"users" : [
ObjectId("5a1db9e8db97d318ac70715d")
]
}
What If I will change array of users in document for array objects id
{
"_id" : ObjectId("5a7f4b46f489dd236410d77c"),
"name" : "second",
"users" : [
{ _id : ObjectId("5a1db9e8db97d318ac70715d") }
]
}
How to find now this document in this situation, using only req.user._id which is saved inside object of users[]?
we can find it somehow now or not??
You just need to change it as : Board.find({ 'users._id' : req.user._id})
You could also use:
db.collection_name.find( { "user": { "_id" : req.user._id } } )

Categories