I create an array of Objects from a database query and call the
array jobListRecords. There are multiple records in the array created that have the same "customerID" and "name".
I would like to create a new array that has one record for each customer with a new field , "jobArray", that contains another array of all of that customers services. (see sortCustomer array down below)
An example of the initial array:
jobListRecords = [
{
"customerID" : "1",
"name" : "Larry Bird",
"serviceID" : "101",
"serviceName" : "Dog Walking"
},
{
"customerID" : "2",
"name" : "Andrew Luck",
"serviceID" : "202",
"serviceName" : "Baby Sitting"
},
{
"customerID" : "2",
"name" : "Andrew Luck",
"serviceID" : "101",
"serviceName" : "Dog Walking"
}
]
Desired Result
sortCustomer Example:
sortCustomer = [
{
"customerID" : "1",
"name" : " Larry Bird",
"jobArray" : [
{
"serviceID" : "101",
"serviceName" : "Dog Walking"
}
]
},
{
"customerID" : "2",
"name" : "Andrew Luck",
"jobArray" : [
{
"serviceID" : "202",
"serviceName" : "Baby Sitting"
},
{
"serviceID" : "101",
"serviceName" : "Dog Walking"
}
]
}
Is their a simple or efficient way of solving this without having to iterate through all the data 3+ times. Thank You for your time, below is one of the several things I tried.
I tried solving this using one example I found but it grouped all the serviceIDs together which is not what I need.
Example that DID NOT work that I tried.
jobListGrouped = _
.chain(jobListRecords)
.groupBy('customerID')
.map(function(value, key) {
return {
CustomerID: key,
services: _.pluck(value, 'serviceID')
}
})
.value();
You're plucking only the serviceIDs into that array. Instead, you would need to do something like
.map(function(values, key) {
return {
customerID: key,
name: values[0].name.
services: _.map(values, _.partial(_.pick, _, 'serviceID', 'serviceName'))
}
})
or even more explicit
.map(function(values, key) {
return _.extend(_.omit(values[0], 'serviceID', 'serviceName'), {
services: _.map(values, _.partial(_.pick, _, 'serviceID', 'serviceName'))
}
})
(where that partial call is the same as function(value) { return _.pick(value, 'serviceID', 'serviceName'); })
Related
I'm trying to get all the values(which are arrays) of the "coordinate" type in my data like that:
[
["51.50064317423898","-0.09372711181640626"],
["51.48465408363687","-0.13149261474609378"]
]
I tried db.collections("mydb").distinct("coordinate") but i get:
[
'-0.09372711181640626',
'-0.13149261474609378',
'51.48465408363687',
'51.50064317423898'
]
Does anyone have an idea how i can just have all my arrays like i want and not ordered in one array?
"mydb" looks like this:
{
"name":"dfbfdbf",
"coordinate":["51.50064317423898","-0.09372711181640626"],
"rating":"8",
"description":"geojzglijsen"
},
{
"name":"qzfgs",
"coordinate":["51.48465408363687","-0.13149261474609378"],
"rating":"5",
"description":"femkndsmnk"
}
Thank you!
If I've understood correctly you can try this aggregate query:
The point is $group by null to get all values and use $addToSet which prevents the duplicates values.
db.collection.aggregate([
{
"$group": {
"_id": null,
"coordinate": {
"$addToSet": "$coordinate"
}
}
},
{
"$project": {
"_id": 0
}
}
])
Example here where I've duplicated one object to see how the repeated value is not displayed.
If you need to fetch distinct coordinates from your collection:
mongos> db.a.find()
{ "_id" : ObjectId("619ea12e032deead586f3f91"), "name" : "dfbfdbf", "coordinate" : [ "51.50064317423898", "-0.09372711181640626" ] }
{ "_id" : ObjectId("619ea138032deead586f3f92"), "name" : "a", "coordinate" : [ "51.50064317423898", "-0.09372711181640626" ] }
{ "_id" : ObjectId("619ea14c032deead586f3f93"), "name" : "a", "coordinate" : [ "51.50064317423898", "-0.19372711181640626" ] }
{ "_id" : ObjectId("619ea157032deead586f3f94"), "name" : "a", "coordinate" : [ "51.50064317423898", "-0.09372711181640626" ] }
{ "_id" : ObjectId("619ea15b032deead586f3f95"), "name" : "a", "coordinate" : [ "52.50064317423898", "-0.09372711181640626" ] }
{ "_id" : ObjectId("619ea160032deead586f3f96"), "name" : "a", "coordinate" : [ "52.50064317423898", "-0.09372711181640626" ] }
mongos> db.a.aggregate([
{ $addFields:{coordinates:{$reduce:{ input: {$slice:["$coordinate",1,{$size:"$coordinate"} ]},initialValue:{$arrayElemAt:["$coordinate",0]},in:{$concat:["$$value",";","$$this" ]} }} }} ,
{ $group:{_id:"$coordinates" , cnt:{$sum:1}}} ,
{ $project : { coordinate : { $split: ["$_id", ";"] } ,_id:0}}
])
{ "coordinate" : [ "51.50064317423898", "-0.19372711181640626" ] }
{ "coordinate" : [ "51.50064317423898", "-0.09372711181640626" ] }
{ "coordinate" : [ "52.50064317423898", "-0.09372711181640626" ] }
mongos>
Example:
here
explained:
Remove duplicate coordinates from collection
create new field coordinates where you join the coordinates in single string
group the coordinates to remove duplicates
split the coordinates to the original values.
This solution has no limitation of distinct coordinates array summary size of 16MB as well ...
This question already has answers here:
How to sort array inside collection record in MongoDB?
(16 answers)
Closed 4 years ago.
I want to fetch the data by sorting xm_score but it's not working with my query.
query = match.find({ '_id': 'k00012' }).sort('npi.xm_score');
I need to get the objects in npi get sorted by xm_score in this array.
I have the data as follows,
{
"term":'k00012',
"npi" : [
{
"npi" : "1003000126",
"xm_score" : 77.1,
"geo" : [
-75.53091147,
40.60619643
],
"state" : "PA",
"zip" : "18103",
"specialty" : [
"x010"
]
},
{
"npi" : "1003000126",
"xm_score" : 70.1,
"geo" : [
-75.53091147,
40.60619643
],
"state" : "PA",
"zip" : "18103",
"specialty" : [
"x010"
]
}]
}
You can simply have a custom function for sorting array
let obj = {
"term":'k00012',
"npi" : [
{
"npi" : "1003000126",
"xm_score" : 77.1,
"geo" : [
-75.53091147,
40.60619643
],
"state" : "PA",
"zip" : "18103",
"specialty" : [
"x010"
]
},
{
"npi" : "1003000126",
"xm_score" : 70.1,
"geo" : [
-75.53091147,
40.60619643
],
"state" : "PA",
"zip" : "18103",
"specialty" : [
"x010"
]
}]
}
let arr = obj.npi;
arr.sort((a,b) => {
return a.xm_score - b.xm_score
})
console.log(arr)
How do I get a nested object from a selected document?
If this is my document, which I get with Collection.findOne({ _id: 'dZXr2Pg7Ak4M5aYWF'})...
{
"_id" : "dZXr2Pg7Ak4M5aYWF",
"points" : [
{
"id" : "Gwf5BzorXyYBZSEzK",
"coordinates" : [
433,
215
],
"content" : "anything"
},
{
"id" : "iwSM98W5PD87BtcLa",
"coordinates" : [
666,
186
]
}
]
}
... I need to get the complete data of the point with the id Gwf5BzorXyYBZSEzK. So my result should look like:
result = {
"id" : "Gwf5BzorXyYBZSEzK",
"coordinates" : [
433,
215
],
"content" : "anything"
}
You can simply filter the points array, with Array.prototype.filter, like this
console.log(data.points.filter(function(obj) {
return obj.id === "Gwf5BzorXyYBZSEzK";
})[0]);
// { id: 'Gwf5BzorXyYBZSEzK' coordinates: [ 433, 215 ], content: 'anything' }
We just take the first element from the filtered result array. If you want to get all the elements, which have the specific id, then just remove the subscript.
If your environment supports ECMAScript 2015's Arrow functions, then you can write the same as
console.log(data.points.filter((obj) => obj.id === "Gwf5BzorXyYBZSEzK")[0]);
var data = {
"_id": "dZXr2Pg7Ak4M5aYWF",
"points": [{
"id": "Gwf5BzorXyYBZSEzK",
"coordinates": [433, 215],
"content": "anything"
}, {
"id": "iwSM98W5PD87BtcLa",
"coordinates": [666, 186]
}]
};
function finder(id){
for(i=0;i<data.points.length;i++){
if(data.points[i].id==id){
return data.points[i];
}
}
}
var result = finder("Gwf5BzorXyYBZSEzK");
document.write(JSON.stringify(result));
Problem Statement
I'm trying to create an array with another array inside this array, but it doesn't work for me.
This is what i wrote:
var arr = '{"project":['
+ '{"id":"01","name":"project1","activity":['
+ '{"num":"001","time":"7","desc":"desc","stam":['
+ ' "pre":"005","pre2":"002"]}'
+ '{"num":"002","time":"6","desc":"desc"}'
+ '{"num":"003","time":"5","desc":"desc"}'
+ '{"num":"004","time":"4","desc":"desc"}'
+ '{"num":"005","time":"3","desc":"desc"}]}]}';
Your JSON looks corrupted. You can use several online editors and validators to verify the JSON string. editor and validator just as an example of mony others. You also might have a look here.
, is missing between the array elements
the property stam looks more like an object than an array
It should look like this:
{"project":[
{"id":"01","name":"project1","activity":
[
{"num":"001","time":"7","desc":"desc","stam":{
"pre":"005",
"pre2":"002"
}
},
{"num":"002","time":"6","desc":"desc"},
{"num":"003","time":"5","desc":"desc"},
{"num":"004","time":"4","desc":"desc"},
{"num":"005","time":"3","desc":"desc"}
]
}
]
}
The json is not formatted correctly:
{
project : [{
id : "01",
name: "project1",
activity :[
{
num : "001",
time : "7",
desc : "desc",
stam : [{
pre : "005",
pre2: "002"
}]
},
{
num : "002",
time: "6",
desc: "desc"
},
{
num : "003",
time: "5",
desc:"desc"
},
{
num : "004",
time: "4",
desc: "desc"
},
{
num : "005",
time: "3",
desc: "desc"
}
]
}]
}
My JSON currently looks like this:
{
"_id" : 393,
"item" : 34,
"comments" : [
{
"name" : "kevin",
"messages" : [
"item",
"item"
]
},
{
"name" : "ryan",
"messages" : [
"item",
"item"
]
}
]
}
How could I push new items onto the messages array for the first or second item in the comments array?
db.newcon.update({_id: 393}, { $push: { comments['kevin']: {messages: 39 } } })
Using $elemMatch and $ operator you can update your documents check below query :
db.collectionName.update({"_id":393,"comments":{"$elemMatch":{"name":"kevin"}}},
{"$push":{"comments.$.messages":39}})
Something like this will work:
var newMessage = '39';
comments.forEach(function(item) {
if (item.name === 'kevin') {
item.comments.push(newMessage);
}
});