Combine different collection result into one in Mongo - mongodb

Below is my query I want the result of shp_tx_survey_with_index and
for each loop collection shp_counties_with_index name1 and name2 together of both this collection. If running this query separate then getting the result but this query gives me nothing. I want result like Range_Township, Survey, Section, abstract, centroid, name_1, name_2.
db.shp_tx_survey_with_index.aggregate(
[
{ $match: { "centroid": { "$ne": null } } },
{ $limit: 5 },
{
$project: {
Range_Township: "$l1surnam",
Survey: "$l4surnam",
Section: "$l1surnam",
abstract: "$abstract_",
centroid: "$centroid"
}
}
]
).forEach((obj) => {
var item = db.shp_counties_with_index.findOne({
geom_geojson: {
$nearSphere: {
$geometry: obj.centroid
}
}
}, { 'name_1': 1, 'name_2': 1 });
});
shp_counties_with_index sample collection
{
"_id" : ObjectId("5846bf55834d5b761f00000a"),
"engtype_2" : "County",
"geom_geojson" : {
"type" : "MultiPolygon",
"coordinates" : [
[
[
[
-73.6516685561232,
34.2445059658098
],
[
-73.6516685623318,
34.2445059757618
],
[
-73.6516685538257,
34.244505973301
],
[
-73.6516685561232,
34.2445059658098
]
]
] ]
},
"name_0" : "United States",
"name_1" : "Michigan",
"name_2" : "Chippewa",
"shape_area" : "0.481851809544",
"shape_leng" : "9.37720288177",
"type_2" : "County",
"validfr_2" : "Unknown",
"validto_2" : "Unknown",
"centroid" : {
"coordinates" : [
-73.65166855807875,
34.244505970785795
],
"type" : "Point"
}
}
shp_tx_survey_with_index sample collection
{
"_id" : ObjectId("5846bf76834d5b761f013fa7"),
"abstract_" : "321.000000000",
"abstract_i" : "322.000000000",
"anum" : "443962",
"area" : "0.0000666764235294",
"geom" : "01060000000100000001030000000100000008000000EC90DE47A07659C0F062332AEA813E403471FBB0A17759C06082096CE6813E4034A2C2ABA17759C0700AAF2731823E40B49BADAAA17759C09092F09440823E401C588E90A17759C000B4279A6A823E400019834C677559C02026721261823E403073564B677559C080C77880E6813E40EC90DE47A07659C0F062332AEA813E40",
"geom_geojson" : {
"type" : "MultiPolygon",
"coordinates" : [
[
[
[
-73.6517272344497,
34.2444627902475
],
[
-73.6517271719931,
34.2444627964974
],
[
-73.6517271718375,
34.2444627914072
],
[
-73.6517272344497,
34.2444627902475
]
]
]
]
},
"geom_text" : "MULTIPOLYGON(((-73.6517272344497 34.2444627902475,-73.6517271719931 34.2444627964974,-73.6517271718375 34.2444627914072,-73.6517272344497 34.2444627902475)))",
"gid" : "271508",
"l1surnam" : "TEMPLETON, J S",
"l2block" : null,
"l3surnum" : "4",
"l4surnam" : null,
"perimeter" : "0.0735082380545",
"probflag" : "0",
"shape_area" : "0.0000666764230571",
"shape_leng" : "0.0735082374282",
"centroid" : {
"coordinates" : [
-73.6517272031436,
34.24446279337245
],
"type" : "Point"
}
}
Thanks in advance.

When you want to combine information from 2 collections in a aggregation pipeline you can use the $lookup operator.
This operator is available from MongoDB 3.2 and up.

Related

Return only matching sub document from MongoDB document

We have following structure in our Mongo collection
{
"_id" : ObjectId("5f98aeadbaf1ea001affe4c0"),
"name" : "Temp",
"campaigntype" : 3,
"startdate" : ISODate("2021-01-01T00:00:00.000Z"),
"enddate" : ISODate("2021-01-01T00:00:00.000Z"),
"affiliatetag" : "",
"promotedtitles" : [
{
"primaryisbn" : "9781453238431",
"promoprice" : "1.99",
"countries" : [
"US",
"CA",
"AU",
"GB"
],
"retailers" : [
"ALL"
],
"dlp" : "17.99",
"notes1" : "History",
"notes2" : "",
"sequence" : 1
},
{
"primaryisbn" : "9781504063562",
"promoprice" : "1.99",
"countries" : [
"US",
"CA"
],
"retailers" : [
"ALL"
],
"dlp" : "11.99",
"notes1" : "Thrillers",
"notes2" : "",
"sequence" : 2
},
{
"primaryisbn" : "9781497673984",
"promoprice" : "0.99",
"countries" : [
"US",
"CA"
],
"retailers" : [
"ALL"
],
"dlp" : "6.99",
"notes1" : "Romantic Suspense",
"notes2" : "",
"sequence" : 3
},
{
"primaryisbn" : "9780547526959",
"promoprice" : "1.99",
"countries" : [
"CA"
],
"retailers" : [
"All"
],
"dlp" : "17.99",
"notes1" : "History",
"notes2" : "",
"sequence" : 4
},
{
"primaryisbn" : "9781453274248",
"promoprice" : "1.99",
"countries" : [
"US"
],
"retailers" : [
"All"
],
"dlp" : "9.99",
"notes1" : "Historical Fiction",
"notes2" : "",
"sequence" : 5
}
],
"active" : true,
"createdby" : ObjectId("5d2e2755d3851f0012108a05")
}
We need to write a query by passing single country like ['US'] or multiple country like ['US', 'CA']. Query should only return us matching sub document from promoted titles.
For example, If we pass country as 'US', we should get primary isbn 9781453238431, 9781504063562, 9781497673984 and 9781453274248. If we pass country as ['GB', 'CA'], we need to get 9781453238431, 9781504063562, 9781497673984 and 9780547526959. If we pass ['GB'], we should only get 9781453238431 sub document
We were trying with promotedtitles.countries : {$in : ['US', 'CA']} but that don't work.
Thanks in advance
You can $unwind and $match like this:
$unwind is to deconstruct the array and get every object as a different value instead all together in an array.
Then you can filter each object using $match and $in.
db.collection.aggregate([
{
"$unwind": "$promotedtitles"
},
{
"$match": {
"promotedtitles.countries": {
"$in": [
"US"
]
}
}
},
{
"$project": {
"_id": 0,
"result": "$promotedtitles.primaryisbn"
}
}
])
Example here using US and here with GB, CA.
Also, if you want to get all ISBNs in an array you can add a $group like this example

Sort query for dynamic array in Mongo DB

I have a collection in MongoDB like below format. Now i want to know how to apply sorting. Please find example of collection below,
{
"_id" : ObjectId("5e5e140f113a6c3970eef3bb"),
"FormId" : "5cd3a0a0cb20953208fcb549",
"FieldsDatas" : [
{
"FieldId" : "4fbcef5b-d60a-4908-a037-5ff085b70709",
"Value" : [
"202003031"
]
},
{
"FieldId" : "708e1baf-fcd0-45fa-b1de-27f34391c35c",
"Value" : [
"202003031"
]
},
{
"FieldId" : "0b563a80-2b0a-4803-ad7f-652a381e134c",
"Value" : [
"New Source",
"Endpoint"
]
},
{
"FieldId" : "15355b82-4fae-4c09-acb4-13f95e8c2d4e",
"Value" : [
"2020-03-03 13:51:17"
]
},
{
"FieldId" : "1e32a283-34a9-4a7b-b851-3e5ac7f93d2c",
"Value" : [
"tets"
]
}
]
}
{
"_id" : ObjectId("5e5e1c89113a6c3970eef3bc"),
"FormId" : "5cd3a0a0cb20953208fcb549"
"FieldsDatas" : [
{
"FieldId" : "708e1baf-fcd0-45fa-b1de-27f34391c35c",
"Value" : [
"202003032"
]
},
{
"FieldId" : "0eca0881-a69b-4db3-b8b1-d74b0a16d4ef",
"Value" : [
"20200303_2#mail.com"
]
},
{
"FieldId" : "2da67714-aaf3-433d-9a86-1b48c75470ec",
"Value" : [
"mani lj"
]
},
{
"FieldId" : "a0b26aac-cad0-4c5e-83b4-9a01ac4ce97a",
"Value" : []
},
{
"FieldId" : "15355b82-4fae-4c09-acb4-13f95e8c2d4e",
"Value" : [
"2020-03-03 14:29:23"
]
}
]
}
For above collection i have date inside the array of objects called FieldsDatas where "FieldId": "15355b82-4fae-4c09-acb4-13f95e8c2d4e" in that same "Value" array has datetime. I want to sort the result based in this datetime.
I have a filter query. How to add sort query for above scenario?
db.getCollection('Collection').find({
"$and":[
{
FieldsDatas: {
$elemMatch:{
FieldId:'955c9843-1535-4df8-a1c4-09430ac9f6ba',
Value: { $ne: ["Contact"] }
}
}
}
]
})
.limit(5)
.skip(30);
Anyone please help me to add sorting for this query like above datetime field.
Any possibilities to achieve this by Stored procedure or functions. Please let me know.
Thanks in advance,
Mani

in mongo, cannot perform $setIntersection on array with aggregate into project

I have this two collection which each document presents a chat session:
{
"_id" : ObjectId("58136ba83bdddd2d3cd4b3fb"),
"Created" : ISODate("2016-10-28T15:15:52.563Z"),
"Messages" : [
{
"Created" : ISODate("2016-10-28T15:15:52.567Z"),
"ReadBy" : [
ObjectId("57c96a14870ae36ede4d8085"),
ObjectId("57c972b6fc8effecde6cf0fa")
],
"Content" : "Hello"
}
]
}
{
"_id" : ObjectId("5813ac380a45415df8e7fc08"),
"Created" : ISODate("2016-10-28T15:16:52.563Z"),
"Messages" : [
{
"Created" : ISODate("2016-10-28T15:15:52.567Z"),
"ReadBy" : [
ObjectId("57c96a14870ae36ede4d8234"),
ObjectId("57c972b6fc8effecde6cf987")
],
"Content" : "Hello2"
}
]
}
I am trying to use $aggregate with $project, and to perform a simple $setIntersection in order to get matching ObjectIds.
This is the projection:
db.getCollection('Chats').aggregate([
{
$project: {
Created: 1,
Messages: 1,
Match: {
$setIntersection: [ "$Messages.ReadBy", [ObjectId("57c96a14870ae36ede4d8085")] ]
},
ReadBy: "$Messages.ReadBy"
}
}
])
The result i am getting from this aggregate, seems to insert "$Messages.ReadBy" into Sub-Array of Array [[ObjectId("....")]] for example.
The Result is that $setIntersection returns null although there is something relevant for me, and the new "ReadBy" field i added for debug shows the problem of sub-array:
{
"_id" : ObjectId("58136ba83bdddd2d3cd4b3fb"),
"Created" : ISODate("2016-10-28T15:15:52.563Z"),
"Messages" : [
{
"Created" : ISODate("2016-10-28T15:15:52.567Z"),
"ReadBy" : [
ObjectId("57c96a14870ae36ede4d8085"),
ObjectId("57c972b6fc8effecde6cf0fa")
],
"Content" : "Hello"
}
],
"Match" : [],
"ReadBy" : [
[
ObjectId("57c96a14870ae36ede4d8085"),
ObjectId("57c972b6fc8effecde6cf0fa")
]
]
}
{
"_id" : ObjectId("5813ac380a45415df8e7fc08"),
"Created" : ISODate("2016-10-28T15:16:52.563Z"),
"Messages" : [
{
"Created" : ISODate("2016-10-28T15:15:52.567Z"),
"ReadBy" : [
ObjectId("57c96a14870ae36ede4d8234"),
ObjectId("57c972b6fc8effecde6cf987")
],
"Content" : "Hello2"
}
],
"Match" : [],
"ReadBy" : [
[
ObjectId("57c96a14870ae36ede4d8234"),
ObjectId("57c972b6fc8effecde6cf987")
]
]
}
Why is "Match" field returns empty array?
And why "ReadBy" wrapping the source field with extra array?
a solution is to use $arrayElemAt to get the sub array.
the new query is
db.getCollection('Chats').aggregate([
{
$project:{
Created:1,
Messages:1,
Match:{
$setIntersection:[
{
$arrayElemAt:[
"$Messages.ReadBy",
0
]
},
[
ObjectId("57c96a14870ae36ede4d8085")
]
]
},
ReadBy:"$Messages.ReadBy"
}
}
])
and the result is now
{
"_id" : ObjectId("58136ba83bdddd2d3cd4b3fb"),
"Created" : ISODate("2016-10-28T15:15:52.563Z"),
"Messages" : [
{
"Created" : ISODate("2016-10-28T15:15:52.567Z"),
"ReadBy" : [
ObjectId("57c96a14870ae36ede4d8085"),
ObjectId("57c972b6fc8effecde6cf0fa")
],
"Content" : "Hello"
}
],
"Match" : [
ObjectId("57c96a14870ae36ede4d8085")
],
"ReadBy" : [
[
ObjectId("57c96a14870ae36ede4d8085"),
ObjectId("57c972b6fc8effecde6cf0fa")
]
]
}
{
"_id" : ObjectId("5813ac380a45415df8e7fc08"),
"Created" : ISODate("2016-10-28T15:16:52.563Z"),
"Messages" : [
{
"Created" : ISODate("2016-10-28T15:15:52.567Z"),
"ReadBy" : [
ObjectId("57c96a14870ae36ede4d8234"),
ObjectId("57c972b6fc8effecde6cf987")
],
"Content" : "Hello2"
}
],
"Match" : [ ],
"ReadBy" : [
[
ObjectId("57c96a14870ae36ede4d8234"),
ObjectId("57c972b6fc8effecde6cf987")
]
]
}

get length of array via variable just created mongodb

I am new to mongodb, I have a dataset that looks like the following, and I'm trying to Write an aggregation query that will determine the number of unique companies with which an individual has been associated.
Schema:
{
"_id" : ObjectId("52cdef7c4bab8bd675297d8b"),
"name" : "AdventNet",
"permalink" : "abc3",
"crunchbase_url" : "http://www.crunchbase.com/company/adventnet",
"homepage_url" : "http://adventnet.com",
"blog_url" : "",
"blog_feed_url" : "",
"twitter_username" : "manageengine",
"category_code" : "enterprise",
"number_of_employees" : 600,
"founded_year" : 1996,
"deadpooled_year" : 2,
"tag_list" : "",
"alias_list" : "Zoho ManageEngine ",
"email_address" : "pr#adventnet.com",
"phone_number" : "925-924-9500",
"description" : "Server Management Software",
"created_at" : ISODate("2007-05-25T19:24:22Z"),
"updated_at" : "Wed Oct 31 18:26:09 UTC 2012",
"overview" : "<p>AdventNet is now Zoho ManageEngine.</p>\n\n<p>Founded in 1996, AdventNet has served a diverse range of enterprise IT, networking and telecom customers.</p>\n\n<p>AdventNet supplies server and network management software.</p>",
"image" : {
"available_sizes" : [
[
[
150,
55
],
"assets/images/resized/0001/9732/19732v1-max-150x150.png"
],
[
[
150,
55
],
"assets/images/resized/0001/9732/19732v1-max-250x250.png"
],
[
[
150,
55
],
"assets/images/resized/0001/9732/19732v1-max-450x450.png"
]
]
},
"products" : [ ],
"relationships" : [
{
"is_past" : true,
"title" : "CEO and Co-Founder",
"person" : {
"first_name" : "Sridhar",
"last_name" : "Vembu",
"permalink" : "sridhar-vembu"
}
},
{
"is_past" : true,
"title" : "VP of Business Dev",
"person" : {
"first_name" : "Neil",
"last_name" : "Butani",
"permalink" : "neil-butani"
}
},
{
"is_past" : true,
"title" : "Usabiliy Engineer",
"person" : {
"first_name" : "Bharath",
"last_name" : "Balasubramanian",
"permalink" : "bharath-balasibramanian"
}
},
{
"is_past" : true,
"title" : "Director of Engineering",
"person" : {
"first_name" : "Rajendran",
"last_name" : "Dandapani",
"permalink" : "rajendran-dandapani"
}
},
{
"is_past" : true,
"title" : "Market Analyst",
"person" : {
"first_name" : "Aravind",
"last_name" : "Natarajan",
"permalink" : "aravind-natarajan"
}
},
{
"is_past" : true,
"title" : "Director of Product Management",
"person" : {
"first_name" : "Hyther",
"last_name" : "Nizam",
"permalink" : "hyther-nizam"
}
},
{
"is_past" : true,
"title" : "Western Regional OEM Sales Manager",
"person" : {
"first_name" : "Ian",
"last_name" : "Wenig",
"permalink" : "ian-wenig"
}
}
],
"competitions" : [ ],
"providerships" : [
{
"title" : "DHFH",
"is_past" : true,
"provider" : {
"name" : "A Small Orange",
"permalink" : "a-small-orange"
}
}
],
"total_money_raised" : "$0",
"funding_rounds" : [ ],
"investments" : [ ],
"acquisition" : null,
"acquisitions" : [ ],
"offices" : [
{
"description" : "Headquarters",
"address1" : "4900 Hopyard Rd.",
"address2" : "Suite 310",
"zip_code" : "94588",
"city" : "Pleasanton",
"state_code" : "CA",
"country_code" : "USA",
"latitude" : 37.692934,
"longitude" : -121.904945
}
],
"milestones" : [ ],
"video_embeds" : [ ],
"screenshots" : [
{
"available_sizes" : [
[
[
150,
94
],
"assets/images/resized/0004/3400/43400v1-max-150x150.png"
],
[
[
250,
156
],
"assets/images/resized/0004/3400/43400v1-max-250x250.png"
],
[
[
450,
282
],
"assets/images/resized/0004/3400/43400v1-max-450x450.png"
]
],
"attribution" : null
}
],
"external_links" : [ ],
"partners" : [ ]
}
Here is the query I tried:
db.companies.aggregate([{
$match: {
"relationships.person": {
$ne: null
}
}
}, {
$project: {
relationships: 1,
_id: 0
}
}, {
$unwind: "$relationships"
}, {
$group: {
_id: "$relationships.person",
count: {
$addToSet: "$relationships"
}
}
}])
I think I now need to get the length of the $relationships array? How would I do that?
When you only want the size of the array you really don't need to unwind...
Just use $size.
Alter your aggregation to:
db.companies.aggregate([{
$match: {
"relationships.person": {
$ne: null
}
}
}, {
$project: {
relationships: 1,
_id: 0,
relationship_size : { $size : "$relationships"}
}
}
}])
This should give you the result you want
From the comment i understand you want some more logic in the aggregation, from outta my head i would alter your aggregation to:
db.companies.aggregate([{
$match: {
"relationships.person": {
$ne: null
}
}
}, {
$project: {
relationships: 1,
_id: 0
}
}, {
$unwind: "$relationships"
}, {
$group: {
_id: "$relationships.person.permalink",
count : {$sum : 1}
}
}])
I can't find a "company name" in your relationships array so i use the permalink property

Return intersection of subdocument array with user defined array?

I am trying to use Mongo Aggregation Framework to find out intersection between an array inside my document AND another user defined array.
I don't get a correct result and my guess is its because of the fact that I have array inside of an array.
Here is my data set.
My documents:
{
"_id" : 1,
"pendingEntries" : [
{
"entryID" : ObjectId("5701b4c3c6b126083332e65f"),
"tags" : [
{
"tagKey" : "owner",
"tagValue" : "john"
},
{
"tagKey" : "ErrorCode",
"tagValue" : "7001"
},
{
"tagKey" : "ErrorDescription",
"tagValue" : "error123"
}
],
"entryTime" : ISODate("2016-04-04T00:26:43.167Z")
}
]
},
/* 1 */
{
"_id" : 2,
"pendingEntries" : [
{
"entryID" : ObjectId("5701b4c3c6b126083332e65d"),
"tags" : [
{
"tagKey" : "owner",
"tagValue" : "peter"
},
{
"tagKey" : "ErrorCode",
"tagValue" : "6001"
},
{
"tagKey" : "JIRA",
"tagValue" : "Oabc-123"
}
],
"entryTime" : ISODate("2016-04-04T00:26:43.167Z")
}
]
},
/* 2 */
{
"_id" : 3,
"pendingEntries" : [
{
"entryID" : ObjectId("5701b4c3c6b126083332e65c"),
"tags" : [
{
"tagKey" : "owner",
"tagValue" : "abc"
},
{
"tagKey" : "ErrorCode",
"tagValue" : "6001"
},
{
"tagKey" : "JIRA",
"tagValue" : "abc-123"
}
],
"entryTime" : ISODate("2016-04-04T00:26:43.167Z")
}
]
}
My Query:
db.entrylike.aggregate(
[
{ $project: { "pendingEntries.entryID": 1, "common": { $setIntersection: [ "$pendingEntries.tags", [{ "tagKey" : "ErrorCode", "tagValue" : "7001" }] ] } } }
]
)
Result:
{
"result" : [
{
"_id" : 1,
"pendingEntries" : [
{
"entryID" : ObjectId("5701b4c3c6b126083332e65f")
}
],
"common" : []
},
{
"_id" : 2,
"pendingEntries" : [
{
"entryID" : ObjectId("5701b4c3c6b126083332e65d")
}
],
"common" : []
},
{
"_id" : 3,
"pendingEntries" : [
{
"entryID" : ObjectId("5701b4c3c6b126083332e65c")
}
],
"common" : []
}
],
"ok" : 1
}
I am not expecting first common field to be empty. Can someone let me know what is it that I am doing wrong? Or any work arounds that I can take.
I am using mongodb 3.0.8. I am aware of the fact that Mongodb 3.2 can offer some features which will fulfill my needs but 3.2 upgrade is not in our pipeline soon and I am looking to resolve this using Mongo3.0 if possible.
My goal is to either replace tags array with the common elements from the user defined list or add a new field with common elements. My am trying to to the later in my example.
The reason you the common field is empty is because your "pendingEntries" array and your user defined array have not element in common. What you really want is to return an array that contains the elements that appear in your "tags" array and your user defined array. To do that you can simply use the $map operator and apply the $setIntersection operator to each subdocument "tags" in the "pendingEntries" array.
db.entrylike.aggregate([
{ "$project": {
"common": {
"$map": {
"input": "$pendingEntries",
"as": "p",
"in": {
"entryID": "$$p.entryID",
"tags": {
"$setIntersection": [
"$$p.tags",
{ "$literal": [
{
"tagKey" : "ErrorCode",
"tagValue" : "7001"
}
]}
]
}
}
}
}
}}
])
Which returns:
{
"_id" : 1,
"common" : [
{
"entryID" : ObjectId("5701b4c3c6b126083332e65f"),
"tags" : [
{
"tagKey" : "ErrorCode",
"tagValue" : "7001"
}
]
}
]
}
{
"_id" : 2,
"common" : [
{
"entryID" : ObjectId("5701b4c3c6b126083332e65d"),
"tags" : [ ]
}
]
}
{
"_id" : 3,
"common" : [
{
"entryID" : ObjectId("5701b4c3c6b126083332e65c"),
"tags" : [ ]
}
]
}