diff --git a/reference/operators/aggregation/$addfields.md b/reference/operators/aggregation/$addfields.md new file mode 100644 index 0000000..3332cc9 --- /dev/null +++ b/reference/operators/aggregation/$addfields.md @@ -0,0 +1,240 @@ +--- +title: $addFields +description: The $addFields stage in the aggregation pipeline is used to add new fields to documents. +type: operators +category: aggregation +--- + +# $addFields + +The $addFields stage in the aggregation pipeline is used to add new fields to documents. It can also be used to reset the values of existing fields. This stage is particularly useful when you need to create new fields based on existing data or modify existing fields within your documents. + +## Syntax + +```javascript +{ + $addFields: { + : , + : , + ... + } +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **`newField1`** | The name of the new field to add or the existing field to modify. | +| **`expression1`** | The expression to compute the value of newField1. | + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "0fcc0bf0-ed18-4ab8-b558-9848e18058f4", + "name": "First Up Consultants | Beverage Shop - Satterfieldmouth", + "location": { + "lat": -89.2384, + "lon": -46.4012 + }, + "staff": { + "totalStaff": { + "fullTime": 8, + "partTime": 20 + } + }, + "sales": { + "totalSales": 75670, + "salesByCategory": [ + { + "categoryName": "Wine Accessories", + "totalSales": 34440 + }, + { + "categoryName": "Bitters", + "totalSales": 39496 + }, + { + "categoryName": "Rum", + "totalSales": 1734 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Unbeatable Bargain Bash", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 23 + }, + "endDate": { + "Year": 2024, + "Month": 7, + "Day": 2 + } + }, + "discounts": [ + { + "categoryName": "Whiskey", + "discountPercentage": 7 + }, + { + "categoryName": "Bitters", + "discountPercentage": 15 + }, + { + "categoryName": "Brandy", + "discountPercentage": 8 + }, + { + "categoryName": "Sports Drinks", + "discountPercentage": 22 + }, + { + "categoryName": "Vodka", + "discountPercentage": 19 + } + ] + }, + { + "eventName": "Steal of a Deal Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 29 + } + }, + "discounts": [ + { + "categoryName": "Organic Wine", + "discountPercentage": 19 + }, + { + "categoryName": "White Wine", + "discountPercentage": 20 + }, + { + "categoryName": "Sparkling Wine", + "discountPercentage": 19 + }, + { + "categoryName": "Whiskey", + "discountPercentage": 17 + }, + { + "categoryName": "Vodka", + "discountPercentage": 23 + } + ] + } + ] +} +``` + +### Example 1: Adding a new field + +This query adds a new field totalDiscountEvents that counts the number of promotion events + +```javascript +db.stores.aggregate([ + { + $addFields: { + totalDiscountEvents: { $size: "$store.promotionEvents" } + } + } +]) +``` + +This query returns the following result: + +```json +[ + { + "_id": "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c5", + "store": { + "name": "Downtown Store", + "promotionEvents": ["Summer Sale", "Black Friday", "Holiday Deals"] + }, + "totalDiscountEvents": 3 + } +] +``` + +### Example 2: Modifying an Existing Field + +This query adds a field totalStaffCount that sums up the full-time and part-time staff. + +```javascript +db.stores.aggregate([ + { + $addFields: { + totalStaffCount: { + $add: ["$store.staff.totalStaff.fullTime", "$store.staff.totalStaff.partTime"] + } + } + } +]) +``` + +This query returns the following result: + +```json +[ + { + "_id": "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c5", + "store": { + "name": "Downtown Store", + "staff": { + "totalStaff": { + "fullTime": 12, + "partTime": 8 + } + } + }, + "totalStaffCount": 20 + } +] +``` + +### Example 3: Adding Nested Fields + +This query adds a nested field location.coordinates that combines latitude and longitude into an array. + +```javascript +db.stores.aggregate([ + { + $addFields: { + "store.location.coordinates": ["$store.location.lat", "$store.location.lon"] + } + } +]) +``` + +This query returns the following result: + +```json +[ + { + "_id": "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c5", + "store": { + "name": "Downtown Store", + "location": { + "lat": 47.6097, + "lon": -122.3331, + "coordinates": [47.6097, -122.3331] + } + } + } +] +``` diff --git a/reference/operators/aggregation/$bucket.md b/reference/operators/aggregation/$bucket.md new file mode 100644 index 0000000..bf9074c --- /dev/null +++ b/reference/operators/aggregation/$bucket.md @@ -0,0 +1,178 @@ +--- +title: $bucket +description: Groups input documents into buckets based on specified boundaries. +type: operators +category: aggregation +--- + +# $bucket + +The `$bucket` stage in an aggregation pipeline groups input documents into buckets based on specified boundaries. This is especially useful for creating histograms or categorizing data into ranges. It allows you to define custom bucket boundaries and provides a way to summarize data within these ranges. + +## Syntax + +```javascript +{ + $bucket: { + groupBy: , + boundaries: [ , , ... ], + default: , + output: { + : { }, + ... + } + } +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **`groupBy`** | The expression to group documents by. | +| **`boundaries`** | An array of boundary values to define the buckets. The array must be sorted in ascending order and include at least two values. | +| **`default`** | The name of the bucket for documents that do not fall within the specified boundaries. | +| **`output`** | An optional field to specify computed fields for each bucket. | + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "0fcc0bf0-ed18-4ab8-b558-9848e18058f4", + "name": "First Up Consultants | Beverage Shop - Satterfieldmouth", + "location": { + "lat": -89.2384, + "lon": -46.4012 + }, + "staff": { + "totalStaff": { + "fullTime": 8, + "partTime": 20 + } + }, + "sales": { + "totalSales": 75670, + "salesByCategory": [ + { + "categoryName": "Wine Accessories", + "totalSales": 34440 + }, + { + "categoryName": "Bitters", + "totalSales": 39496 + }, + { + "categoryName": "Rum", + "totalSales": 1734 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Unbeatable Bargain Bash", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 23 + }, + "endDate": { + "Year": 2024, + "Month": 7, + "Day": 2 + } + }, + "discounts": [ + { + "categoryName": "Whiskey", + "discountPercentage": 7 + }, + { + "categoryName": "Bitters", + "discountPercentage": 15 + }, + { + "categoryName": "Brandy", + "discountPercentage": 8 + }, + { + "categoryName": "Sports Drinks", + "discountPercentage": 22 + }, + { + "categoryName": "Vodka", + "discountPercentage": 19 + } + ] + }, + { + "eventName": "Steal of a Deal Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 29 + } + }, + "discounts": [ + { + "categoryName": "Organic Wine", + "discountPercentage": 19 + }, + { + "categoryName": "White Wine", + "discountPercentage": 20 + }, + { + "categoryName": "Sparkling Wine", + "discountPercentage": 19 + }, + { + "categoryName": "Whiskey", + "discountPercentage": 17 + }, + { + "categoryName": "Vodka", + "discountPercentage": 23 + } + ] + } + ] +} +``` + +### Example 1: Categorizing `fullSales` into ranges + +This query categorizes the `fullSales` field into three buckets: `[0, 1000)`, `[1000, 5000)`, and `[5000, 10000)`. Documents that do not fall into these ranges are grouped into a default bucket. + +```javascript +db.stores.aggregate([ + { + $bucket: { + groupBy: "$sales.fullSales", + boundaries: [0, 1000, 5000, 10000], + default: "Other", + output: { + count: { $sum: 1 }, + totalSales: { $sum: "$sales.fullSales" } + } + } + } +]) +``` + +This query returns the following results: + +```json +[ + { "_id": 1000, "count": 1, "totalSales": 3700 }, + { "_id": "Other", "count": 41504, "totalSales": 0 } +] +``` diff --git a/reference/operators/aggregation/$changestream.md b/reference/operators/aggregation/$changestream.md new file mode 100644 index 0000000..ba10015 --- /dev/null +++ b/reference/operators/aggregation/$changestream.md @@ -0,0 +1,191 @@ +--- +title: $changeStream +description: The $changeStream stage opens a change stream cursor to track data changes in real-time. +type: operators +category: aggregation +--- + +# $changeStream + +The `$changeStream` aggregation stage opens a change stream cursor that tracks data changes in real-time. This stage enables applications to react to insert, update, delete, and other operations as they occur in the collection. + +## Syntax + +```javascript +{ + $changeStream: { + allChangesForCluster: , + fullDocument: , + fullDocumentBeforeChange: , + resumeAfter: , + startAfter: , + startAtOperationTime: , + showExpandedEvents: + } +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **`allChangesForCluster`** | Optional. Boolean. If true, returns changes for the entire cluster. Default is false. | +| **`fullDocument`** | Optional. String. Determines what to return for update operations. Options: 'default', 'updateLookup', 'whenAvailable', 'required'. | +| **`fullDocumentBeforeChange`** | Optional. String. Returns the preimage of the document. Options: "off", "whenAvailable", "required". | +| **`resumeAfter`** | Optional. Resume token to resume change stream after a specific event. | +| **`startAfter`** | Optional. Resume token to start change stream after a specific event. | +| **`startAtOperationTime`** | Optional. timestamp for starting change stream from a specific time. | +| **`showExpandedEvents`** | Optional. Boolean. Include another change stream events. Default is false. | + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "0fcc0bf0-ed18-4ab8-b558-9848e18058f4", + "name": "First Up Consultants | Beverage Shop - Satterfieldmouth", + "location": { + "lat": -89.2384, + "lon": -46.4012 + }, + "staff": { + "totalStaff": { + "fullTime": 8, + "partTime": 20 + } + }, + "sales": { + "totalSales": 75670, + "salesByCategory": [ + { + "categoryName": "Wine Accessories", + "totalSales": 34440 + }, + { + "categoryName": "Bitters", + "totalSales": 39496 + }, + { + "categoryName": "Rum", + "totalSales": 1734 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Unbeatable Bargain Bash", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 23 + }, + "endDate": { + "Year": 2024, + "Month": 7, + "Day": 2 + } + }, + "discounts": [ + { + "categoryName": "Whiskey", + "discountPercentage": 7 + }, + { + "categoryName": "Bitters", + "discountPercentage": 15 + }, + { + "categoryName": "Brandy", + "discountPercentage": 8 + }, + { + "categoryName": "Sports Drinks", + "discountPercentage": 22 + }, + { + "categoryName": "Vodka", + "discountPercentage": 19 + } + ] + }, + { + "eventName": "Steal of a Deal Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 29 + } + }, + "discounts": [ + { + "categoryName": "Organic Wine", + "discountPercentage": 19 + }, + { + "categoryName": "White Wine", + "discountPercentage": 20 + }, + { + "categoryName": "Sparkling Wine", + "discountPercentage": 19 + }, + { + "categoryName": "Whiskey", + "discountPercentage": 17 + }, + { + "categoryName": "Vodka", + "discountPercentage": 23 + } + ] + } + ] +} +``` + +### Example 1: Monitor all changes in stores collection + +This operation sets up a change stream to monitor all changes in the stores collection. + +```javascript +db.stores.aggregate([ + { + $changeStream: { + fullDocument: "updateLookup" + } + } +]) +``` + +When a store document is updated, the change stream returns the change event with the full document. + +```json +{ + "_id": { "_data": "AeARBpQ/AAAA" }, + "operationType": "update", + "fullDocument": { + "_id": "905d1939-e03a-413e-a9c4-221f74055aac", + "name": "Trey Research | Home Office Depot - Lake Freeda", + "sales": { + "revenue": 42500 + }, + "company": "Trey Research", + "lastUpdated": "ISODate('2024-06-16T10:30:00.000Z')" + }, + "ns": { + "db": "StoreData", + "coll": "stores" + }, + "documentKey": { + "_id": "905d1939-e03a-413e-a9c4-221f74055aac" + } +} +``` diff --git a/reference/operators/aggregation/$collstats.md b/reference/operators/aggregation/$collstats.md new file mode 100644 index 0000000..8920caa --- /dev/null +++ b/reference/operators/aggregation/$collstats.md @@ -0,0 +1,166 @@ +--- +title: $collStats +description: The $collStats stage in the aggregation pipeline is used to return statistics about a collection. +type: operators +category: aggregation +--- + +# $collStats + +The $collStats stage in the aggregation pipeline is used to return statistics about a collection. This stage can be particularly useful for understanding the performance characteristics of a collection, such as the number of documents, the size of the collection, and storage statistics. It provides detailed information that can help with database optimization and monitoring. + +## Syntax + +```javascript +{ + $collStats: { + latencyStats: { histograms: }, + storageStats: { scale: }, + count: {} + } +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **`latencyStats`** | Optional. Specifies whether to include latency statistics. The `histograms` field is a boolean that indicates whether to include histograms of latency data. | +| **`storageStats`** | Optional. Specifies whether to include storage statistics. The `scale` field is a number that indicates the scale factor for the storage statistics. | +| **`count`** | Optional. Includes the count of documents in the collection. | + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "0fcc0bf0-ed18-4ab8-b558-9848e18058f4", + "name": "First Up Consultants | Beverage Shop - Satterfieldmouth", + "location": { + "lat": -89.2384, + "lon": -46.4012 + }, + "staff": { + "totalStaff": { + "fullTime": 8, + "partTime": 20 + } + }, + "sales": { + "totalSales": 75670, + "salesByCategory": [ + { + "categoryName": "Wine Accessories", + "totalSales": 34440 + }, + { + "categoryName": "Bitters", + "totalSales": 39496 + }, + { + "categoryName": "Rum", + "totalSales": 1734 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Unbeatable Bargain Bash", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 23 + }, + "endDate": { + "Year": 2024, + "Month": 7, + "Day": 2 + } + }, + "discounts": [ + { + "categoryName": "Whiskey", + "discountPercentage": 7 + }, + { + "categoryName": "Bitters", + "discountPercentage": 15 + }, + { + "categoryName": "Brandy", + "discountPercentage": 8 + }, + { + "categoryName": "Sports Drinks", + "discountPercentage": 22 + }, + { + "categoryName": "Vodka", + "discountPercentage": 19 + } + ] + }, + { + "eventName": "Steal of a Deal Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 29 + } + }, + "discounts": [ + { + "categoryName": "Organic Wine", + "discountPercentage": 19 + }, + { + "categoryName": "White Wine", + "discountPercentage": 20 + }, + { + "categoryName": "Sparkling Wine", + "discountPercentage": 19 + }, + { + "categoryName": "Whiskey", + "discountPercentage": 17 + }, + { + "categoryName": "Vodka", + "discountPercentage": 23 + } + ] + } + ] +} +``` + +### Example: Basic collection statistics + +This query counts all the documents in the stores collection. + +```javascript +db.stores.aggregate([ + { + $collStats: { + count: {} + } + } +]) +``` + +This query returns the following result: + +```json +[ + { "ns": "StoreData.stores", "count": 41505 } +] +``` diff --git a/reference/operators/aggregation/$convert.md b/reference/operators/aggregation/$convert.md new file mode 100644 index 0000000..7ff044f --- /dev/null +++ b/reference/operators/aggregation/$convert.md @@ -0,0 +1,250 @@ +--- +title: $convert +description: The $convert operator converts an expression into the specified type +type: operators +category: aggregation +--- + +# $convert + +The $convert operator converts an expression into a value of the specified type. + +## Syntax + +```javascript +{ + $convert: { + input: < expression > , + to: < type > , + format: < binData format > , + onError: < value to return on error > , + onNull: < value to return on null > + } +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **`input`** | The input value to be converted to the specified type| +| **`to`** | The type to convert the input value into| +| **`format`** | (Optional) The binData format of the input or output when converting a value to or from binData| +| **`onError`** | (Optional) The value to return when the conversion of the input to the specified type fails| +| **`onNull`** | (Optional) The value to return when the input value to be converted to the specified type is null or missing| + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "0fcc0bf0-ed18-4ab8-b558-9848e18058f4", + "name": "First Up Consultants | Beverage Shop - Satterfieldmouth", + "location": { + "lat": -89.2384, + "lon": -46.4012 + }, + "staff": { + "totalStaff": { + "fullTime": 8, + "partTime": 20 + } + }, + "sales": { + "totalSales": 75670, + "salesByCategory": [ + { + "categoryName": "Wine Accessories", + "totalSales": 34440 + }, + { + "categoryName": "Bitters", + "totalSales": 39496 + }, + { + "categoryName": "Rum", + "totalSales": 1734 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Unbeatable Bargain Bash", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 23 + }, + "endDate": { + "Year": 2024, + "Month": 7, + "Day": 2 + } + }, + "discounts": [ + { + "categoryName": "Whiskey", + "discountPercentage": 7 + }, + { + "categoryName": "Bitters", + "discountPercentage": 15 + }, + { + "categoryName": "Brandy", + "discountPercentage": 8 + }, + { + "categoryName": "Sports Drinks", + "discountPercentage": 22 + }, + { + "categoryName": "Vodka", + "discountPercentage": 19 + } + ] + }, + { + "eventName": "Steal of a Deal Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 29 + } + }, + "discounts": [ + { + "categoryName": "Organic Wine", + "discountPercentage": 19 + }, + { + "categoryName": "White Wine", + "discountPercentage": 20 + }, + { + "categoryName": "Sparkling Wine", + "discountPercentage": 19 + }, + { + "categoryName": "Whiskey", + "discountPercentage": 17 + }, + { + "categoryName": "Vodka", + "discountPercentage": 23 + } + ] + } + ] +} +``` + +### Example 1: Convert an Int value into a String + +To convert the fullTime field from an integer to a string, run a query using the $convert operator to make the conversion. + +```javascript +db.stores.aggregate([{ + $match: { + _id: "b0107631-9370-4acd-aafa-8ac3511e623d" + } +}, { + $project: { + fulltimeStaff: "$staff.totalStaff.fullTime", + fulltimeStaffAsString: { + $convert: { + input: "$staff.totalStaff.fullTime", + to: "string" + } + } + } +}]) +``` + +This query returns the following result: + +```json +[ + { + "_id": "b0107631-9370-4acd-aafa-8ac3511e623d", + "fulltimeStaff": 3, + "fulltimeStaffAsString": "3" + } +] +``` + +### Example 2: Convert an Int value into a Boolean value + +To convert the fullTime field from an integer to a boolean, run a query using the $convert operator to make the conversion. Any positive value for the fullTime field will be converted to true. + +```javascript +db.stores.aggregate([{ + $match: { + _id: "b0107631-9370-4acd-aafa-8ac3511e623d" + } +}, { + $project: { + fulltimeStaff: "$staff.totalStaff.fullTime", + fulltimeStaffAsBool: { + $convert: { + input: "$staff.totalStaff.fullTime", + to: "bool" + } + } + } +}]) +``` + +This query returns the following result: + +```json +[ + { + "_id": "b0107631-9370-4acd-aafa-8ac3511e623d", + "fulltimeStaff": 3, + "fulltimeStaffAsBool": true + } +] +``` + +### Example 3: Convert an Int value into a Decimal value + +To convert the fullTime staff field from an integer to a decimal value, run a query using the $convert operator to make the conversion. + +```javascript +db.stores.aggregate([{ + $match: { + _id: "b0107631-9370-4acd-aafa-8ac3511e623d" + } +}, { + $project: { + fulltimeStaff: "$staff.totalStaff.fullTime", + fulltimeStaffAsDecimal: { + $convert: { + input: "$staff.totalStaff.fullTime", + to: "decimal" + } + } + } +}]) +``` + +This query returns the following result: + +```json +[ + { + "_id": "b0107631-9370-4acd-aafa-8ac3511e623d", + "fulltimeStaff": 3, + "fulltimeStaffAsDecimal": "Decimal128('3')" + } +] +``` diff --git a/reference/operators/aggregation/$densify.md b/reference/operators/aggregation/$densify.md new file mode 100644 index 0000000..50ad7f9 --- /dev/null +++ b/reference/operators/aggregation/$densify.md @@ -0,0 +1,249 @@ +--- +title: $densify +description: Adds missing data points in a sequence of values within an array or collection. +type: operators +category: aggregation +--- + +# $densify + +The `$densify` stage in an aggregation pipeline is used to fill in missing data points within a sequence of values. It helps in creating a more complete dataset by generating missing values based on a specified field, range, and step. This is useful in scenarios like time-series data analysis, where gaps in data points need to be filled to ensure accurate analysis. + +## Syntax + +```javascript +{ + $densify: { + field: , + range: { + step: , + unit: , // Optional, e.g., "hour", "day", "month", etc. + bounds: [, ] // Optional + }, + partitionByFields: [, , ...] // Optional + } +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **`field`** | The field on which densification is performed. | +| **`range.step`** | The step size for generating missing values. | +| **`range.unit`** | (Optional) The unit of the step size, such as time units (e.g., "hour", "day"). | +| **`range.bounds`** | (Optional) Specifies the range (lower and upper bounds) for densification. | +| **`partitionByFields`** | (Optional) Fields used to group data for densification. | + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "0fcc0bf0-ed18-4ab8-b558-9848e18058f4", + "name": "First Up Consultants | Beverage Shop - Satterfieldmouth", + "location": { + "lat": -89.2384, + "lon": -46.4012 + }, + "staff": { + "totalStaff": { + "fullTime": 8, + "partTime": 20 + } + }, + "sales": { + "totalSales": 75670, + "salesByCategory": [ + { + "categoryName": "Wine Accessories", + "totalSales": 34440 + }, + { + "categoryName": "Bitters", + "totalSales": 39496 + }, + { + "categoryName": "Rum", + "totalSales": 1734 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Unbeatable Bargain Bash", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 23 + }, + "endDate": { + "Year": 2024, + "Month": 7, + "Day": 2 + } + }, + "discounts": [ + { + "categoryName": "Whiskey", + "discountPercentage": 7 + }, + { + "categoryName": "Bitters", + "discountPercentage": 15 + }, + { + "categoryName": "Brandy", + "discountPercentage": 8 + }, + { + "categoryName": "Sports Drinks", + "discountPercentage": 22 + }, + { + "categoryName": "Vodka", + "discountPercentage": 19 + } + ] + }, + { + "eventName": "Steal of a Deal Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 29 + } + }, + "discounts": [ + { + "categoryName": "Organic Wine", + "discountPercentage": 19 + }, + { + "categoryName": "White Wine", + "discountPercentage": 20 + }, + { + "categoryName": "Sparkling Wine", + "discountPercentage": 19 + }, + { + "categoryName": "Whiskey", + "discountPercentage": 17 + }, + { + "categoryName": "Vodka", + "discountPercentage": 23 + } + ] + } + ] +} +``` + +### Example 1: Densify a time-series dataset + +This query fills in missing days in the date field. + +```javascript +db.aggregate([ + { + $documents: [ + { date: new ISODate("2024-01-01"), value: 10 }, + { date: new ISODate("2024-01-03"), value: 15 } + ] + }, + { + $densify: { + field: "date", + range: { + step: 1, + unit: "day", + bounds: "full" + } + } + } + ]); +``` + +This query returns the following results: + +```json +[ + { + "date": "ISODate('2024-01-01T00:00:00.000Z')", + "value": 10 + }, + { + "date": "ISODate('2024-01-02T00:00:00.000Z')" + }, + { + "date": "ISODate('2024-01-03T00:00:00.000Z')", + "value": 15 + } +] + +``` + +### Example 2: Densify numeric data + +This query fills in missing numeric values in the `sales.fullSales` field: + +```javascript +db.aggregate([ + { + $documents: [ + { level: 1, score: 10 }, + { level: 3, score: 30 } + ] + }, + { + $densify: { + field: "level", + range: { + step: 1, + bounds: [1, 5] + } + } + } + ]); +``` + +This query returns the following results: + +```json +[ + { + "level": 1, + "score": 10 + }, + { + "level": 2 + }, + { + "level": 3, + "score": 30 + }, + { + "level": 4 + } +] +``` + +## Limitations + +The following table summarizes the key restrictions and behaviors associated with the $densify stage in aggregation pipelines: + +| Category| Condition / Behavior | +| --- | --- | +| Field Restrictions | - Errors if any document has a **date** value and `unit` is **not specified**.
- Errors if any document has a **numeric** value and `unit` is **specified**.
- Field name **starts with `$`**. Use `$project` to rename it.| +| partitionByFields | - Any field evaluates to a **non-string** value.
- Field name **starts with `$`**. | +| range.bounds | - **Lower bound** defines the start value, regardless of existing documents.
- **Lower bound is inclusive**.
- **Upper bound is exclusive**.
- `$densify` does **not filter out** documents outside the bounds. | diff --git a/reference/operators/aggregation/$documents.md b/reference/operators/aggregation/$documents.md new file mode 100644 index 0000000..0e56d42 --- /dev/null +++ b/reference/operators/aggregation/$documents.md @@ -0,0 +1,281 @@ +--- +title: $documents +description: The $documents stage creates a pipeline from a set of provided documents. +type: operators +category: aggregation +--- + +# $documents + +The `$documents` aggregation pipeline stage is used to create a pipeline from a set of provided documents. This stage is particularly useful when you want to process specific documents without querying a collection. + +## Syntax + +```javascript +{ + $documents: [ + , + , + ... + ] +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **``** | A JSON object representing a document to include in the pipeline. | + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "0fcc0bf0-ed18-4ab8-b558-9848e18058f4", + "name": "First Up Consultants | Beverage Shop - Satterfieldmouth", + "location": { + "lat": -89.2384, + "lon": -46.4012 + }, + "staff": { + "totalStaff": { + "fullTime": 8, + "partTime": 20 + } + }, + "sales": { + "totalSales": 75670, + "salesByCategory": [ + { + "categoryName": "Wine Accessories", + "totalSales": 34440 + }, + { + "categoryName": "Bitters", + "totalSales": 39496 + }, + { + "categoryName": "Rum", + "totalSales": 1734 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Unbeatable Bargain Bash", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 23 + }, + "endDate": { + "Year": 2024, + "Month": 7, + "Day": 2 + } + }, + "discounts": [ + { + "categoryName": "Whiskey", + "discountPercentage": 7 + }, + { + "categoryName": "Bitters", + "discountPercentage": 15 + }, + { + "categoryName": "Brandy", + "discountPercentage": 8 + }, + { + "categoryName": "Sports Drinks", + "discountPercentage": 22 + }, + { + "categoryName": "Vodka", + "discountPercentage": 19 + } + ] + }, + { + "eventName": "Steal of a Deal Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 29 + } + }, + "discounts": [ + { + "categoryName": "Organic Wine", + "discountPercentage": 19 + }, + { + "categoryName": "White Wine", + "discountPercentage": 20 + }, + { + "categoryName": "Sparkling Wine", + "discountPercentage": 19 + }, + { + "categoryName": "Whiskey", + "discountPercentage": 17 + }, + { + "categoryName": "Vodka", + "discountPercentage": 23 + } + ] + } + ] +} +``` + +### Example 1: Create a pipeline from specific documents + +This query demonstrates how to use the `$documents` stage to process a set of predefined documents: + +```javascript +db.aggregate([{ + $documents: [{ + _id: "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c5", + name: "Lakeshore Retail | Holiday Supply Hub - Marvinfort", + location: { + lat: 60.1441, + lon: -141.5012 + }, + sales: { + fullSales: 3700 + }, + tag: ["#ShopLocal", "#SeasonalSale"] + }, { + _id: "7e53ca0f-6e24-4177-966c-fe62a11e9af5", + name: "Contoso, Ltd. | Office Supply Deals - South Shana", + location: { + lat: 40.7128, + lon: -74.0060 + }, + sales: { + fullSales: 5400 + }, + tag: ["#TechDeals", "#FreeShipping"] + }] +}, { + $project: { + _id: 1, + name: 1, + "location.lat": 1, + "location.lon": 1, + "sales.fullSales": 1, + tags: "$tag" + } +}]) +``` + +This query returns the following results: + +```json +[ + { + "_id": "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c5", + "name": "Lakeshore Retail | Holiday Supply Hub - Marvinfort", + "location": { + "lat": 60.1441, + "lon": -141.5012 + }, + "sales": { + "fullSales": 3700 + }, + "tags": [ + "#ShopLocal", + "#SeasonalSale" + ] + }, + { + "_id": "7e53ca0f-6e24-4177-966c-fe62a11e9af5", + "name": "Contoso, Ltd. | Office Supply Deals - South Shana", + "location": { + "lat": 40.7128, + "lon": -74.006 + }, + "sales": { + "fullSales": 5400 + }, + "tags": [ + "#TechDeals", + "#FreeShipping" + ] + } +] +``` + +### Example 2: Combine `$documents` with other pipeline stages + +This query combines the $documents pipeline stage along with the $match and $sort pipeline stages. + +```javascript +db.aggregate([{ + $documents: [{ + _id: "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c5", + name: "Lakeshore Retail | Holiday Supply Hub - Marvinfort", + location: { + lat: 60.1441, + lon: -141.5012 + }, + sales: { + fullSales: 3700 + }, + tag: ["#ShopLocal", "#SeasonalSale"] + }, { + _id: "7e53ca0f-6e24-4177-966c-fe62a11e9af5", + name: "Contoso, Ltd. | Office Supply Deals - South Shana", + location: { + lat: 40.7128, + lon: -74.0060 + }, + sales: { + fullSales: 5400 + }, + tag: ["#TechDeals", "#FreeShipping"] + }] +}, { + $match: { + "sales.fullSales": { + $gt: 4000 + } + } +}, { + $sort: { + "sales.fullSales": -1 + } +}]) +``` + +This query returns the following result: + +```json +[ + { + "_id": "7e53ca0f-6e24-4177-966c-fe62a11e9af5", + "name": "Contoso, Ltd. | Office Supply Deals - South Shana", + "location": { "lat": 40.7128, "lon": -74.006 }, + "sales": { "fullSales": 5400 }, + "tag": [ "#TechDeals", "#FreeShipping" ] + } +] +``` + +## Limitations + +- The $documents stage is only supported in database-level aggregation pipelines. +- It must be the first stage in the pipeline to function correctly. diff --git a/reference/operators/aggregation/$facet.md b/reference/operators/aggregation/$facet.md new file mode 100644 index 0000000..c184d37 --- /dev/null +++ b/reference/operators/aggregation/$facet.md @@ -0,0 +1,187 @@ +--- +title: $facet +description: The $facet allows for multiple parallel aggregations to be executed within a single pipeline stage. +type: operators +category: aggregation +--- + +# $facet + +The `$facet` stage aggregation pipelines allow for multiple parallel aggregations to be executed within a single pipeline stage. It's useful for performing multiple analyses on the same dataset in a single query. + +## Syntax + +```javascript +{ + "$facet": { + "outputField1": [ { "stage1": {} }, { "stage2": {} } ], + "outputField2": [ { "stage1": {} }, { "stage2": {} } ] + } +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **`outputFieldN`**| The name of the output field.| +| **`stageN`**| The aggregation stage to be executed.| + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "0fcc0bf0-ed18-4ab8-b558-9848e18058f4", + "name": "First Up Consultants | Beverage Shop - Satterfieldmouth", + "location": { + "lat": -89.2384, + "lon": -46.4012 + }, + "staff": { + "totalStaff": { + "fullTime": 8, + "partTime": 20 + } + }, + "sales": { + "totalSales": 75670, + "salesByCategory": [ + { + "categoryName": "Wine Accessories", + "totalSales": 34440 + }, + { + "categoryName": "Bitters", + "totalSales": 39496 + }, + { + "categoryName": "Rum", + "totalSales": 1734 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Unbeatable Bargain Bash", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 23 + }, + "endDate": { + "Year": 2024, + "Month": 7, + "Day": 2 + } + }, + "discounts": [ + { + "categoryName": "Whiskey", + "discountPercentage": 7 + }, + { + "categoryName": "Bitters", + "discountPercentage": 15 + }, + { + "categoryName": "Brandy", + "discountPercentage": 8 + }, + { + "categoryName": "Sports Drinks", + "discountPercentage": 22 + }, + { + "categoryName": "Vodka", + "discountPercentage": 19 + } + ] + }, + { + "eventName": "Steal of a Deal Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 29 + } + }, + "discounts": [ + { + "categoryName": "Organic Wine", + "discountPercentage": 19 + }, + { + "categoryName": "White Wine", + "discountPercentage": 20 + }, + { + "categoryName": "Sparkling Wine", + "discountPercentage": 19 + }, + { + "categoryName": "Whiskey", + "discountPercentage": 17 + }, + { + "categoryName": "Vodka", + "discountPercentage": 23 + } + ] + } + ] +} +``` + +### Example 1: Faceted search on sales and promotions + +To perform simultaneous analyses on sales and promotions, for specified product categories. The `salesAnalysis` pipeline unwinds the `salesByCategory`, filters for certain categories, and groups them to sum `totalSales`. The promotion analysis pipeline unwinds promotional events and their discounts, filters for specific categories like `Laptops`, `Smartphones` etc., and groups them to calculate the average discount percentage. The input documents from `stores` collection are fetched from the database only once, at the beginning of this operation. + +```javascript +db.stores.aggregate([ + { + $facet: { + salesAnalysis: [ + { $unwind: "$sales.salesByCategory" }, + { $match: { "sales.salesByCategory.categoryName": { $in: ["Laptops", "Smartphones", "Cameras", "Watches"] } } }, + { $group: { _id: "$sales.salesByCategory.categoryName", totalSales: { $sum: "$sales.salesByCategory.totalSales" } } } + ], + promotionAnalysis: [ + { $unwind: "$promotionEvents" }, + { $unwind: "$promotionEvents.discounts" }, + { $match: { "promotionEvents.discounts.categoryName": { $in: ["Laptops", "Smartphones", "Cameras", "Watches"] } } }, + { $group: { _id: "$promotionEvents.discounts.categoryName", avgDiscount: { $avg: "$promotionEvents.discounts.discountPercentage" } } } + ] + } + } +]).pretty() +``` + +This query returns the following result: + +```json +[ + { + "salesAnalysis": [ + { "_id": "Smartphones", "totalSales": 440815 }, + { "_id": "Laptops", "totalSales": 679453 }, + { "_id": "Cameras", "totalSales": 481171 }, + { "_id": "Watches", "totalSales": 492299 } + ], + "promotionAnalysis": [ + { "_id": "Smartphones", "avgDiscount": 14.32 }, + { "_id": "Laptops", "avgDiscount": 14.780645161290323 }, + { "_id": "Cameras", "avgDiscount": 15.512195121951219 }, + { "_id": "Watches", "avgDiscount": 15.174418604651162 } + ] + } +] +``` diff --git a/reference/operators/aggregation/$fill.md b/reference/operators/aggregation/$fill.md new file mode 100644 index 0000000..74f42f8 --- /dev/null +++ b/reference/operators/aggregation/$fill.md @@ -0,0 +1,301 @@ +--- +title: $fill +description: The $fill stage allows filling missing values in documents based on specified methods and criteria. +type: operators +category: aggregation +--- + +# $fill + +The `$fill` stage is used to fill missing or null values in documents within the aggregation pipeline. It provides various methods to populate missing data, including using static values, linear interpolation, or values from previous/next documents. + +## Syntax + +```javascript +{ + $fill: { + sortBy: , + partitionBy: , + partitionByFields: , + output: { + : { value: }, + : { method: } + } + } +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **`sortBy`** | Specifies the sort order for documents when applying fill methods that depend on document order. | +| **`partitionBy`** | Optional. Groups documents into partitions. Fill operations are applied within each partition separately. | +| **`partitionByFields`** | Optional. Alternative syntax for partitionBy using an array of field names. | +| **`output`** | Specifies the fields to fill and the method or value to use for filling missing data. | + +### Fill Methods + +| Method | Description | +| --- | --- | +| **`value`** | Fill with a specified static value or expression result. | +| **`linear`** | Fill using linear interpolation between known values (numeric fields only). | +| **`locf`** | Last Observation Carried Forward - use the last known value. | +| **`linear`** | Linear interpolation between surrounding values. | + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "2cf3f885-9962-4b67-a172-aa9039e9ae2f", + "name": "First Up Consultants | Bed and Bath Center - South Amir", + "location": { + "lat": 60.7954, + "lon": -142.0012 + }, + "staff": { + "totalStaff": { + "fullTime": 18, + "partTime": 17 + } + }, + "sales": { + "totalSales": 37701, + "salesByCategory": [ + { + "categoryName": "Mattress Toppers", + "totalSales": 37701 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Price Drop Palooza", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 30 + } + }, + "discounts": [ + { + "categoryName": "Bath Accessories", + "discountPercentage": 18 + }, + { + "categoryName": "Pillow Top Mattresses", + "discountPercentage": 17 + } + ] + } + ] +} +``` + +### Example 1: Fill missing values with static value + +This query fills missing `totalSales` values in the `salesByCategory` array with a default value of 0. + +```javascript +db.stores.aggregate([{ + $match: { + company: { + $in: ["First Up Consultants"] + } + } +}, { + $unwind: "$sales.salesByCategory" +}, { + $fill: { + output: { + "sales.salesByCategory.totalSales": { + value: 0 + } + } + } +}, { + $group: { + _id: "$_id", + name: { + $first: "$name" + }, + salesByCategory: { + $push: "$sales.salesByCategory" + } + } +}]) +``` + +The first two results returned by this query are: + +```json +[ + { + "_id": "affdc09c-7356-4fff-a857-e8301f57159c", + "name": "First Up Consultants | Sports Gear Pantry - Wildermanhaven", + "salesByCategory": [ + { + "categoryName": "Baseball Gear", + "totalSales": 33878 + }, + { + "categoryName": "Volleyball Gear", + "totalSales": 34031 + } + ] + }, + { + "_id": "1cf667b4-d8ce-4f1a-bad1-a1f0bbce26c2", + "name": "First Up Consultants | Picture Frame Variety - New Abrahamborough", + "salesByCategory": [ + { + "categoryName": "Picture Hanging Supplies", + "totalSales": 7229 + }, + { + "categoryName": "Collage Frames", + "totalSales": 40014 + } + ] + } +] +``` + +### Example 2: Fill missing staff data using last observation carried forward + +This query fills missing part-time staff data using the last known value within each store group. + +```javascript +db.stores.aggregate([{ + $fill: { + sortBy: { + "_id": 1 + }, + output: { + "staff.totalStaff.partTime": { + method: "locf" + } + } + } +}, { + $project: { + name: 1, + "staff.totalStaff": 1 + } +}]) +``` + +The first two results returned by this query are: + +```json +[ + { + "_id": "00003278-4226-4ca7-871d-e80d8f414431", + "name": "Wide World Importers | Camera Depot - Lake Luramouth", + "staff": { + "totalStaff": { + "fullTime": 20, + "partTime": 6 + } + } + }, + { + "_id": "00009bd0-c44e-4cc8-ab03-347076d74a1a", + "name": "Wide World Importers | Music Stop - Rebeccaside", + "staff": { + "totalStaff": { + "fullTime": 9, + "partTime": 0 + } + } + } +] +``` + +### Example 3: Fill missing discount percentages with average value + +This query fills missing discount percentages with the average discount percentage across all stores. + +```javascript +db.stores.aggregate([ + { $unwind: "$promotionEvents" }, + { $unwind: "$promotionEvents.discounts" }, + { + $fill: { + partitionBy: "$promotionEvents.eventName", + sortBy: { "promotionEvents.discounts.categoryName": 1 }, + output: { + "promotionEvents.discounts.discountPercentage": { + value: { $avg: "$promotionEvents.discounts.discountPercentage" } + } + } + } + }, + { + $group: { + _id: { storeId: "$_id", eventName: "$promotionEvents.eventName" }, + storeName: { $first: "$name" }, + eventName: { $first: "$promotionEvents.eventName" }, + discounts: { $push: "$promotionEvents.discounts" } + } + } +]) +``` + +The first two results returned by this query are: + +```json +[ + { + "_id": { + "storeId": "70d4cc90-23b1-46e3-8f59-630648e311a4", + "eventName": "Price Slash Spectacular" + }, + "storeName": "Wide World Importers | Music Bazaar - West Johnpaulhaven", + "eventName": "Price Slash Spectacular", + "discounts": [ + { + "categoryName": "CDs", + "discountPercentage": 22 + }, + { + "categoryName": "Vinyl Records", + "discountPercentage": 21 + } + ] + }, + { + "_id": { + "storeId": "24873ac4-b2d1-4216-a425-3375a384b23d", + "eventName": "Massive Deal Mania" + }, + "storeName": "Northwind Traders | Furniture Pantry - Farrellchester", + "eventName": "Massive Deal Mania", + "discounts": [ + { + "categoryName": "Bookcases", + "discountPercentage": 22 + }, + { + "categoryName": "Cabinets", + "discountPercentage": 8 + } + ] + } +] +``` + +## Use Cases + +- **Data Cleaning**: Fill missing values in imported datasets +- **Time Series Data**: Handle gaps in sequential data using interpolation +- **Default Values**: Assign default values to optional fields +- **Data Normalization**: Ensure consistent data structure across documents diff --git a/reference/operators/aggregation/$geonear.md b/reference/operators/aggregation/$geonear.md new file mode 100644 index 0000000..4bb4c4d --- /dev/null +++ b/reference/operators/aggregation/$geonear.md @@ -0,0 +1,262 @@ +--- +title: $geoNear +description: The $geoNear operator finds and sorts documents by their proximity to a geospatial point, returning distance information for each document. +type: operators +category: aggregation +--- + +# $geoNear + +The `$geoNear` aggregation stage calculates distances between a specified point and the location field in each document, sorts the documents by distance, and can optionally limit results by distance. + +## Syntax + +```javascript +{ + $geoNear: { + near: { + type: "Point", + coordinates: [, ] + }, + distanceField: , + maxDistance: , + minDistance: , + query: , + includeLocs: , + distanceMultiplier: , + spherical: , + key: + } +} +``` + +## Parameters + +| Parameter | Type | Description | +|-----------|------|-------------| +| `near` | Object | The point from which to calculate distances | +| `distanceField` | String | The field that contains computed distance | +| `maxDistance` | Number | Optional. Maximum distance in meters from point | +| `minDistance` | Number | Optional. Minimum distance in meters from point | +| `query` | Document | Optional query conditions | +| `includeLocs` | Boolean | Optional. Include locations in results | +| `distanceMultiplier` | Number | Optional. Multiply distances by this value | +| `spherical` | Boolean | Must be true for 2dsphere indexes | +| `key` | String | Optional. Field path to use for calculating distances | + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "2cf3f885-9962-4b67-a172-aa9039e9ae2f", + "name": "First Up Consultants | Bed and Bath Center - South Amir", + "location": { + "lat": 60.7954, + "lon": -142.0012 + }, + "staff": { + "totalStaff": { + "fullTime": 18, + "partTime": 17 + } + }, + "sales": { + "totalSales": 37701, + "salesByCategory": [ + { + "categoryName": "Mattress Toppers", + "totalSales": 37701 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Price Drop Palooza", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 30 + } + }, + "discounts": [ + { + "categoryName": "Bath Accessories", + "discountPercentage": 18 + }, + { + "categoryName": "Pillow Top Mattresses", + "discountPercentage": 17 + } + ] + } + ] +} +``` + +### Example 1: Basic distance calculation + +This query retrieves all stores near the "VanArsdel Picture Frame Store" location, sorted by distance: + +```javascript +db.stores.aggregate([ + { + $geoNear: { + near: { + type: "Point", + coordinates: [-141.9922, 16.8331] // VanArsdel Picture Frame Store location + }, + distanceField: "distance", + spherical: true + } + }, + { + $project: { + name: 1, + distance: 1 + } + } +]) +``` + +The first three results returned by this query are: + +```json +[ + { + "_id": "643b2756-c22d-4063-9777-0945b9926346", + "name": "Contoso, Ltd. | Outdoor Furniture Corner - Pagacfort", + "distance": 5458613.2813355485 + }, + { + "_id": "daa71e60-75d4-4e03-8b45-9df59af0811f", + "name": "First Up Consultants | Handbag Corner - South Salvatore", + "distance": 5469362.958855379 + }, + { + "_id": "02a78a15-b1fc-4bbd-ae1d-641b7428dc78", + "name": "VanArsdel, Ltd. | Kitchen Appliance Corner - Llewellynberg", + "distance": 5472684.4628977 + } +] +``` + +### Example 2: With distance limits and optional query + +This query retrieves all stores within 30 KM of "Proseware Home Entertainment Hub" that have more than 10 full-time staff: + +```javascript +db.stores.aggregate([ + { + $geoNear: { + near: { + type: "Point", + coordinates: [69.7296, 70.1272] // "Proseware Home Entertainment Hub" location + }, + distanceField: "distance", + maxDistance: 30000, // 30 kilometers in meters + query: { "staff.totalStaff.fullTime": { $gt: 10 } }, + spherical: true + } + }, + { + $project: { + name: 1, + distance: 1, + "staff.totalStaff.fullTime": 1 + } + } +]) +``` + +The first result returned by this query is: + +```javascript +[ + { + "_id": "bbec6d3e-1666-45b4-8803-8b7ef8544845", + "name": "First Up Consultants | Baby Products Bargains - South Keenan", + "staff": { + "totalStaff": { + "fullTime": 19 + } + }, + "distance": 29934.71888123174 + } +] +``` + +### Example 3: Including location data and distance multiplier + +This query retrieves stores with distance in kilometers and included location data: + +```javascript +db.stores.aggregate([ + { + $geoNear: { + near: { + type: "Point", + coordinates: [-38.4071, -47.2548] // "Fabrikam Car Accessory Outlet" location + }, + distanceField: "distanceInKm", + includeLocs: "storeLocation", + distanceMultiplier: 0.001, // Convert meters to kilometers + spherical: true + } + }, + { + $project: { + name: 1, + distanceInKm: 1, + storeLocation: 1 + } + } +]) +``` + +The first three results returned by this query are: + +```javascript +[ + { + "_id": "b677846e-bb73-46ec-9cba-7d94afee382c", + "name": "Northwind Traders | Health Food Shoppe - Brooklynmouth", + "storeLocation": { + "lat": -38.3032, + "lon": -132.7866 + }, + "distanceInKm": 9.095634270192285 + }, + { + "_id": "27c64b44-2382-4477-b3ce-c08e74882156", + "name": "Relecloud | VR Headset Gallery - West Jonasbury", + "storeLocation": { + "lat": -37.9628, + "lon": -132.6637 + }, + "distanceInKm": 34.7104536140246 + }, + { + "_id": "505e83eb-09bc-46a4-ba85-16135611b9de", + "name": "Fabrikam, Inc. | Pharmacy Hub - Elijahville", + "storeLocation": { + "lat": -38.0349, + "lon": -47.9571 + }, + "distanceInKm": 82.92766541748313 + } +] +``` + +## Limitations + +* Can't use with sharded collections +* Only one $geoNear stage per pipeline +* Must be the first stage in the pipeline diff --git a/reference/operators/aggregation/$group.md b/reference/operators/aggregation/$group.md new file mode 100644 index 0000000..9da180c --- /dev/null +++ b/reference/operators/aggregation/$group.md @@ -0,0 +1,145 @@ +--- +title: $group +description: The $group stage groups documents by specified identifier expressions and applies accumulator expressions. +type: operators +category: aggregation +--- + +# $group + +The `$group` aggregation stage groups documents by specified identifier expressions and applies accumulator expressions to create computed fields for each group. This stage is essential for data aggregation and summarization operations. + +## Syntax + +```javascript +{ + $group: { + _id: , + : { : }, + : { : } + } +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **`_id`** | Required. The expression to group by. Use null to calculate accumulated values for all input documents. | +| **`field`** | Optional. Computed using accumulator operators like $sum, $avg, $max, $min, $count, etc. | + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "2cf3f885-9962-4b67-a172-aa9039e9ae2f", + "name": "First Up Consultants | Bed and Bath Center - South Amir", + "location": { + "lat": 60.7954, + "lon": -142.0012 + }, + "staff": { + "totalStaff": { + "fullTime": 18, + "partTime": 17 + } + }, + "sales": { + "totalSales": 37701, + "salesByCategory": [ + { + "categoryName": "Mattress Toppers", + "totalSales": 37701 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Price Drop Palooza", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 30 + } + }, + "discounts": [ + { + "categoryName": "Bath Accessories", + "discountPercentage": 18 + }, + { + "categoryName": "Pillow Top Mattresses", + "discountPercentage": 17 + } + ] + } + ] +} +``` + +### Example 1: Group staffing analysis by city + +This query groups stores by city and analyzes the staffing patterns across different locations. + +```javascript +db.stores.aggregate([ + { + $group: { + _id: "$city", + totalFullTimeStaff: { $sum: "$staff.employeeCount.fullTime" }, + totalPartTimeStaff: { $sum: "$staff.employeeCount.partTime" }, + avgFullTimeStaff: { $avg: "$staff.employeeCount.fullTime" }, + storesInCity: { $count: {} } + } + }, + { + $project: { + city: "$_id", + totalFullTimeStaff: 1, + totalPartTimeStaff: 1, + avgFullTimeStaff: { $round: ["$avgFullTimeStaff", 1] }, + storesInCity: 1, + fullTimeRatio: { + $round: [ + { $divide: ["$totalFullTimeStaff", { $add: ["$totalFullTimeStaff", "$totalPartTimeStaff"] }] }, + 2 + ] + } + } + }, + { $limit : 2} +]) +``` + +The first two results returned by this query are: + +```json +[ + { + "_id": "New Ellsworth", + "totalFullTimeStaff": 11, + "totalPartTimeStaff": 1, + "avgFullTimeStaff": 11, + "storesInCity": 1, + "city": "New Ellsworth", + "fullTimeRatio": 0.92 + }, + { + "_id": "Jalonborough", + "totalFullTimeStaff": 4, + "totalPartTimeStaff": 1, + "avgFullTimeStaff": 4, + "storesInCity": 1, + "city": "Jalonborough", + "fullTimeRatio": 0.8 + } +] +``` diff --git a/reference/operators/aggregation/$indexstats.md b/reference/operators/aggregation/$indexstats.md new file mode 100644 index 0000000..40cf1e9 --- /dev/null +++ b/reference/operators/aggregation/$indexstats.md @@ -0,0 +1,190 @@ +--- +title: $indexStats +description: The $indexStats stage returns usage statistics for each index in the collection. +type: operators +category: aggregation +--- + +# $indexStats + +The `$indexStats` aggregation stage returns usage statistics for each index in the collection. This stage is useful for analyzing index performance, identifying unused indexes, and optimizing query performance. + +## Syntax + +```javascript +{ + $indexStats: {} +} +``` + +## Parameters + +The `$indexStats` stage takes no parameters. + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "0fcc0bf0-ed18-4ab8-b558-9848e18058f4", + "name": "First Up Consultants | Beverage Shop - Satterfieldmouth", + "location": { + "lat": -89.2384, + "lon": -46.4012 + }, + "staff": { + "totalStaff": { + "fullTime": 8, + "partTime": 20 + } + }, + "sales": { + "totalSales": 75670, + "salesByCategory": [ + { + "categoryName": "Wine Accessories", + "totalSales": 34440 + }, + { + "categoryName": "Bitters", + "totalSales": 39496 + }, + { + "categoryName": "Rum", + "totalSales": 1734 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Unbeatable Bargain Bash", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 23 + }, + "endDate": { + "Year": 2024, + "Month": 7, + "Day": 2 + } + }, + "discounts": [ + { + "categoryName": "Whiskey", + "discountPercentage": 7 + }, + { + "categoryName": "Bitters", + "discountPercentage": 15 + }, + { + "categoryName": "Brandy", + "discountPercentage": 8 + }, + { + "categoryName": "Sports Drinks", + "discountPercentage": 22 + }, + { + "categoryName": "Vodka", + "discountPercentage": 19 + } + ] + }, + { + "eventName": "Steal of a Deal Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 29 + } + }, + "discounts": [ + { + "categoryName": "Organic Wine", + "discountPercentage": 19 + }, + { + "categoryName": "White Wine", + "discountPercentage": 20 + }, + { + "categoryName": "Sparkling Wine", + "discountPercentage": 19 + }, + { + "categoryName": "Whiskey", + "discountPercentage": 17 + }, + { + "categoryName": "Vodka", + "discountPercentage": 23 + } + ] + } + ] +} +``` + +### Example 1 - Fetch index statistics + +This query retrieves usage statistics for all indexes on the stores collection. + +```javascript +db.stores.aggregate([ + { $indexStats: {} } +]) +``` + +The query returns statistics for each index including access patterns and usage frequency. + +```json +[ + { + "name": "_id_", + "key": { "_id": 1 }, + "accesses": { "ops": 41675, "since": "2025-06-07T13:51:41.231Z" }, + "spec": { "v": 2, "key": { "_id": 1 }, "name": "_id_" } + }, + { + "name": "location_2dsphere", + "key": { "location": "2dsphere" }, + "accesses": { "ops": 0, "since": "2025-06-07T13:51:41.231Z" }, + "spec": { + "v": 2, + "key": { "location": "2dsphere" }, + "name": "location_2dsphere", + "2dsphereIndexVersion": 3 + } + }, + { + "name": "name_text_sales.salesByCategory.categoryName_text_promotionEvents.eventName_text_promotionEvents.discounts.categoryName_text", + "key": { + "name": "text", + "sales.salesByCategory.categoryName": "text", + "promotionEvents.eventName": "text", + "promotionEvents.discounts.categoryName": "text" + }, + "accesses": { "ops": 8, "since": "2025-06-07T13:51:41.231Z" }, + "spec": { + "v": 2, + "key": { + "name": "text", + "sales.salesByCategory.categoryName": "text", + "promotionEvents.eventName": "text", + "promotionEvents.discounts.categoryName": "text" + }, + "name": "name_text_sales.salesByCategory.categoryName_text_promotionEvents.eventName_text_promotionEvents.discounts.categoryName_text" + } + } +] +``` diff --git a/reference/operators/aggregation/$isnumber.md b/reference/operators/aggregation/$isnumber.md new file mode 100644 index 0000000..794339f --- /dev/null +++ b/reference/operators/aggregation/$isnumber.md @@ -0,0 +1,229 @@ +--- +title: $isNumber +description: The $isNumber operator checks if a specified expression is a numerical type +type: operators +category: aggregation +--- + +# $isNumber + +The `$isNumber` operator returns true if the input expression is a numerical type. The `$isNumber` operator returns false for an expression of any other type. + +## Syntax + +```javascript +{ + $isNumber: < expression > +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **`expression`** | The specified value to check for a number| + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "0fcc0bf0-ed18-4ab8-b558-9848e18058f4", + "name": "First Up Consultants | Beverage Shop - Satterfieldmouth", + "location": { + "lat": -89.2384, + "lon": -46.4012 + }, + "staff": { + "totalStaff": { + "fullTime": 8, + "partTime": 20 + } + }, + "sales": { + "totalSales": 75670, + "salesByCategory": [ + { + "categoryName": "Wine Accessories", + "totalSales": 34440 + }, + { + "categoryName": "Bitters", + "totalSales": 39496 + }, + { + "categoryName": "Rum", + "totalSales": 1734 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Unbeatable Bargain Bash", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 23 + }, + "endDate": { + "Year": 2024, + "Month": 7, + "Day": 2 + } + }, + "discounts": [ + { + "categoryName": "Whiskey", + "discountPercentage": 7 + }, + { + "categoryName": "Bitters", + "discountPercentage": 15 + }, + { + "categoryName": "Brandy", + "discountPercentage": 8 + }, + { + "categoryName": "Sports Drinks", + "discountPercentage": 22 + }, + { + "categoryName": "Vodka", + "discountPercentage": 19 + } + ] + }, + { + "eventName": "Steal of a Deal Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 29 + } + }, + "discounts": [ + { + "categoryName": "Organic Wine", + "discountPercentage": 19 + }, + { + "categoryName": "White Wine", + "discountPercentage": 20 + }, + { + "categoryName": "Sparkling Wine", + "discountPercentage": 19 + }, + { + "categoryName": "Whiskey", + "discountPercentage": 17 + }, + { + "categoryName": "Vodka", + "discountPercentage": 23 + } + ] + } + ] +} +``` + +### Example 1: Check if a Double value is a number + +To verify if the value of the latitude field is numeric, run a query using the $isNumber operator to validate that the double value of the field is a number. + +```javascript +db.stores.aggregate([{ + $match: { + _id: "b0107631-9370-4acd-aafa-8ac3511e623d" + } +}, { + $project: { + originalLatitude: "$location.lat", + latitudeIsNumber: { + $isNumber: "$location.lat" + } + } +}]) +``` + +This query returns the following result: + +```json +[ + { + "_id": "b0107631-9370-4acd-aafa-8ac3511e623d", + "originalLatitude": 72.8377, + "latitudeIsNumber": true + } +] +``` + +### Example 2: Check if an Int value is a number + +To verify if the value of the totalSales field is numeric, run a query using the $isNumber operator to validate that the double value of the field is a number. + +```javascript +db.stores.aggregate([{ + $match: { + _id: "b0107631-9370-4acd-aafa-8ac3511e623d" + } +}, { + $project: { + originalTotalSales: "$sales.totalSales", + totalSalesIsNumber: { + $isNumber: "$sales.totalSales" + } + } +}]) +``` + +This query returns the following result: + +```json +[ + { + "_id": "b0107631-9370-4acd-aafa-8ac3511e623d", + "originalTotalSales": 9366, + "totalSalesIsNumber": true + } +] +``` + +### Example 3: Check if a string is a number + +To verify if the value of the _id field is numeric, run a query using the $isNumber operator to validate that the string value of the field is not a number. + +```javascript +db.stores.aggregate([{ + $match: { + _id: "b0107631-9370-4acd-aafa-8ac3511e623d" + } +}, { + $project: { + idIsNumber: { + $isNumber: "$_id" + } + } +}]) +``` + +This query returns the following result: + +```json +[ + { + "_id": "b0107631-9370-4acd-aafa-8ac3511e623d", + "idIsNumber": false + } +] +``` diff --git a/reference/operators/aggregation/$lookup.md b/reference/operators/aggregation/$lookup.md new file mode 100644 index 0000000..d711ca2 --- /dev/null +++ b/reference/operators/aggregation/$lookup.md @@ -0,0 +1,252 @@ +--- +title: $lookup +description: The $lookup stage in the Aggregation Framework is used to perform left outer joins with other collections. +type: operators +category: aggregation +--- + +# $lookup + +The `$lookup` stage in the Aggregation Framework is used to perform left outer joins with other collections. It allows you to combine documents from different collections based on a specified condition. This operator is useful for enriching documents with related data from other collections without having to perform multiple queries. + +## Syntax + +```javascript +{ + $lookup: { + from: , + localField: , + foreignField: , + as: + } +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **`from`** | The name of the collection to join with.| +| **`localField`** | The field from the input documents that are matched with the `foreignField`.| +| **`foreignField`** | The field from the documents in the `from` collection that are matched with the `localField`.| +| **`as`** | The name of the new array field to add to the input documents. This array contains the matched documents from the `from` collection.| + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "0fcc0bf0-ed18-4ab8-b558-9848e18058f4", + "name": "First Up Consultants | Beverage Shop - Satterfieldmouth", + "location": { + "lat": -89.2384, + "lon": -46.4012 + }, + "staff": { + "totalStaff": { + "fullTime": 8, + "partTime": 20 + } + }, + "sales": { + "totalSales": 75670, + "salesByCategory": [ + { + "categoryName": "Wine Accessories", + "totalSales": 34440 + }, + { + "categoryName": "Bitters", + "totalSales": 39496 + }, + { + "categoryName": "Rum", + "totalSales": 1734 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Unbeatable Bargain Bash", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 23 + }, + "endDate": { + "Year": 2024, + "Month": 7, + "Day": 2 + } + }, + "discounts": [ + { + "categoryName": "Whiskey", + "discountPercentage": 7 + }, + { + "categoryName": "Bitters", + "discountPercentage": 15 + }, + { + "categoryName": "Brandy", + "discountPercentage": 8 + }, + { + "categoryName": "Sports Drinks", + "discountPercentage": 22 + }, + { + "categoryName": "Vodka", + "discountPercentage": 19 + } + ] + }, + { + "eventName": "Steal of a Deal Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 29 + } + }, + "discounts": [ + { + "categoryName": "Organic Wine", + "discountPercentage": 19 + }, + { + "categoryName": "White Wine", + "discountPercentage": 20 + }, + { + "categoryName": "Sparkling Wine", + "discountPercentage": 19 + }, + { + "categoryName": "Whiskey", + "discountPercentage": 17 + }, + { + "categoryName": "Vodka", + "discountPercentage": 23 + } + ] + } + ] +} +``` + +Let's say we have another `ratings` collection with two documents. + +```json +{ + "_id": "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c5", + "rating": 5 +} +{ + "_id": "fecca713-35b6-44fb-898d-85232c62db2f", + "rating": 3 +} +``` + +### Example 1: Combine two collections to list promotion events for stores with a rating of 5 + +This query joins the `ratings` collection with the `stores` collection to list promotion events related to each store having a 5 rating. + +```javascript +db.ratings.aggregate([ + // filter based on rating in ratings collection + { + $match: { + "rating": 5 + } + }, + // find related documents in stores collection + { + $lookup: { + from: "stores", + localField: "_id", + foreignField: "_id", + as: "storeEvents" + } + }, + // deconstruct array to output a document for each element of the array + { + $unwind: "$storeEvents" + }, + // Include only _id and name fields in the output + { $project: { _id: 1, "storeEvents.name": 1 } } + +]) +``` + +This query returns the following result: + +```json +[ + { + "_id": "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c5", + "storeEvents": { "name": "Lakeshore Retail | DJ Equipment Stop - Port Cecile" } + } +] +``` + +### Example 2: Joining two collections (ratings and stores) using a variable from ratings. + +```javascript +db.ratings.aggregate([ + { + $match: { rating: 5 } + }, + { + $lookup: { + from: "stores", + let: { id: "$_id" }, + pipeline: [ + { + $match: { + $expr: { $eq: ["$_id", "$$id"] } + } + }, + { + $project: { _id: 0, name: 1 } + } + ], + as: "storeInfo" + } + }, + { + $unwind: "$storeInfo" + }, + { + $project: { + _id: 1, + rating: 1, + "storeInfo.name": 1 + } + } +]) +``` + +This query returns the following result: + +```json +[ + { + "_id": "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c5", + "rating": 5, + "storeInfo": { + "name": "Lakeshore Retail | DJ Equipment Stop - Port Cecile" + } + } +] +``` diff --git a/reference/operators/aggregation/$match.md b/reference/operators/aggregation/$match.md new file mode 100644 index 0000000..c7162d8 --- /dev/null +++ b/reference/operators/aggregation/$match.md @@ -0,0 +1,227 @@ +--- +title: $match +description: The $match stage in the aggregation pipeline is used to filter documents that match a specified condition. +type: operators +category: aggregation +--- + +# $match + +The `$match` stage in the aggregation pipeline is used to filter documents that match a specified condition. It's similar to the `find` operation but is used within the aggregation pipeline to narrow down the documents that pass through to the next stage. This stage is highly useful for optimizing performance by reducing the number of documents that need to be processed in subsequent stages. + +## Syntax + +```javascript +{ + $match: { + + } +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **``**| A standard MongoDB query document that specifies the conditions that the documents must meet.| + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c5", + "name": "Lakeshore Retail | DJ Equipment Stop - Port Cecile", + "location": { + "lat": 60.1441, + "lon": -141.5012 + }, + "staff": { + "totalStaff": { + "fullTime": 2, + "partTime": 0 + } + }, + "sales": { + "salesByCategory": [ + { + "categoryName": "DJ Headphones", + "totalSales": 35921 + } + ], + "fullSales": 3700 + }, + "promotionEvents": [ + { + "eventName": "Bargain Blitz Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 3, + "Day": 11 + }, + "endDate": { + "Year": 2024, + "Month": 2, + "Day": 18 + } + }, + "discounts": [ + { + "categoryName": "DJ Turntables", + "discountPercentage": 18 + }, + { + "categoryName": "DJ Mixers", + "discountPercentage": 15 + } + ] + } + ], + "tag": [ + "#ShopLocal", + "#SeasonalSale", + "#FreeShipping", + "#MembershipDeals" + ] +} +``` + +### Example 1: Match documents using string comparison + +This query retrieves documents where the `_id` is "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c5": + +```javascript +db.stores.aggregate([ + { + $match: { + "_id": "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c5" + } + } +]) +``` + +This query returns the following result: + +```json +[ + { + "_id": "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c5", + "name": "Lakeshore Retail | DJ Equipment Stop - Port Cecile", + "location": { + "lat": 60.1441, + "lon": -141.5012 + }, + "staff": { + "employeeCount": { + "fullTime": 2, + "partTime": 0 + } + }, + "sales": { + "salesByCategory": [ + { + "categoryName": "DJ Headphones", + "totalSales": 35921 + }, + { + "categoryName": "DJ Cables", + "totalSales": 1000 + } + ], + "fullSales": 3700 + }, + "promotionEvents": [], + "tag": [ + "#ShopLocal", + "#NewArrival", + "#NewArrival", + "#FreeShipping" + ], + "company": "Lakeshore Retail", + "city": "Port Cecile", + "lastUpdated": "2025-08-04T05:57:04.619Z", + "storeOpeningDate": "2024-09-12T10:21:58.274Z" + } +] +``` + +### Example 2: Match documents using numeric comparison + +This query retrieves all stores where the total sales are greater than $35,000: + +```javascript +db.stores.aggregate([ + { + $match: { + "sales.totalSales": { $gt: 35000 } + } + }, + // Limit the result to the first 3 documents + { $limit: 3 }, + // Include only _id and name fields in the output + { $project: { _id: 1, name: 1 } } +]) +``` + +The first three results returned by this query are: + +```json +[ + { + "_id": "8345de34-73ec-4a99-9cb6-a81f7b145c34", + "name": "Northwind Traders | Bed and Bath Place - West Oraland" + }, + { + "_id": "57cc4095-77d9-4345-af20-f8ead9ef0197", + "name": "Wide World Importers | Bed and Bath Store - West Vitafort" + }, + { + "_id": "560099f8-325f-4c35-a4e5-2e0879eb95af", + "name": "Wide World Importers | Bed and Bath Depot - North Maritzaberg" + } +] +``` + +### Example 3: Match documents within sub documents + +This query retrieves all stores with a discount of 15% on DJ Mixers: + +```javascript +db.stores.aggregate([ + { + $match: { + "promotionEvents.discounts": { + $elemMatch: { + "categoryName": "DJ Mixers", + "discountPercentage": 15 + } + } + } + }, + // Limit the result to the first 3 documents + { $limit: 3 }, + // Include only _id and name fields in the output + { $project: { _id: 1, name: 1 } } +]) +``` + +The first three results returned by this query are: + +```json +[ + { + "_id": "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c5", + "name": "Lakeshore Retail | DJ Equipment Stop - Port Cecile" + }, + { + "_id": "3c7eda41-23a1-4226-abf6-17ee9e851b5b", + "name": "Boulder Innovations | DJ Equipment Bazaar - New Ceasarview" + }, + { + "_id": "63831a7d-13a9-4d8b-bf1d-ac004057f96d", + "name": "Contoso, Ltd. | DJ Equipment Shop - Reillyfurt" + } +] +``` diff --git a/reference/operators/aggregation/$merge.md b/reference/operators/aggregation/$merge.md new file mode 100644 index 0000000..ad631e1 --- /dev/null +++ b/reference/operators/aggregation/$merge.md @@ -0,0 +1,143 @@ +--- +title: $merge +description: The $merge stage in an aggregation pipeline writes the results of the aggregation to a specified collection. +type: operators +category: aggregation +--- + +# $merge + +The `$merge` stage in an aggregation pipeline is used to write the results of the aggregation query into a specified collection. This stage is particularly useful for tasks like updating or inserting documents into a target collection based on the output of an aggregation operation. It helps streamline workflows by combining data transformation and data persistence in a single operation. + +## Syntax + +```javascript +{ + $merge: { + into: , + on: , + whenMatched: , + whenNotMatched: + } +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **`into`** | Specifies the target collection where the aggregation results will be written. | +| **`on`** | Specifies the field(s) to identify matching documents in the target collection. | +| **`whenMatched`** | Specifies the action to take when a matching document is found. Options include `merge`, `replace`, `keepExisting`, `fail`, or a custom pipeline. | +| **`whenNotMatched`** | Specifies the action to take when no matching document is found. Options include `insert` or `discard`. | + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c5", + "name": "Lakeshore Retail | DJ Equipment Stop - Port Cecile", + "location": { + "lat": 60.1441, + "lon": -141.5012 + }, + "staff": { + "totalStaff": { + "fullTime": 2, + "partTime": 0 + } + }, + "sales": { + "salesByCategory": [ + { + "categoryName": "DJ Headphones", + "totalSales": 35921 + } + ], + "fullSales": 3700 + }, + "promotionEvents": [ + { + "eventName": "Bargain Blitz Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 3, + "Day": 11 + }, + "endDate": { + "Year": 2024, + "Month": 2, + "Day": 18 + } + }, + "discounts": [ + { + "categoryName": "DJ Turntables", + "discountPercentage": 18 + }, + { + "categoryName": "DJ Mixers", + "discountPercentage": 15 + } + ] + } + ], + "tag": [ + "#ShopLocal", + "#SeasonalSale", + "#FreeShipping", + "#MembershipDeals" + ] +} +``` + +### Example 1: Merge data into a collection + +This query aggregates documents and writes the results to a collection named `salesSummary`, updating existing documents where the `_id` matches and inserting new documents otherwise. + +```javascript +db.sales.aggregate([ + { + $group: { + _id: "$sales.salesByCategory.categoryName", + totalSales: { $sum: "$sales.salesByCategory.totalSales" } + } + }, + { + $merge: { + into: "salesSummary", + on: "_id", + whenMatched: "merge", + whenNotMatched: "insert" + } + } +]) +``` + +### Example 2: Replace documents in the target collection + +This example replaces documents in the `promotionEventsSummary` collection based on the `_id` field. + +```javascript +db.promotionEvents.aggregate([ + { + $project: { + _id: "$eventName", + startDate: "$promotionalDates.startDate", + endDate: "$promotionalDates.endDate", + totalDiscounts: { $size: "$discounts" } + } + }, + { + $merge: { + into: "promotionEventsSummary", + on: "_id", + whenMatched: "replace", + whenNotMatched: "insert" + } + } +]) +``` diff --git a/reference/operators/aggregation/$out.md b/reference/operators/aggregation/$out.md new file mode 100644 index 0000000..f2975bc --- /dev/null +++ b/reference/operators/aggregation/$out.md @@ -0,0 +1,175 @@ +--- +title: $out +description: The `$out` stage in an aggregation pipeline writes the resulting documents to a specified collection. +type: operators +category: aggregation +--- + +# $out + +The `$out` stage in an aggregation pipeline allows you to write the resulting documents of the pipeline into a specified collection. It is commonly used to save the output of complex aggregation operations for further use or analysis. When used, the specified collection is either created or replaced with the new documents. + +## Syntax + +```javascript +{ + $out: "" +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **``** | The name of the collection where the aggregation result will be stored. | + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "0fcc0bf0-ed18-4ab8-b558-9848e18058f4", + "name": "First Up Consultants | Beverage Shop - Satterfieldmouth", + "location": { + "lat": -89.2384, + "lon": -46.4012 + }, + "staff": { + "totalStaff": { + "fullTime": 8, + "partTime": 20 + } + }, + "sales": { + "totalSales": 75670, + "salesByCategory": [ + { + "categoryName": "Wine Accessories", + "totalSales": 34440 + }, + { + "categoryName": "Bitters", + "totalSales": 39496 + }, + { + "categoryName": "Rum", + "totalSales": 1734 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Unbeatable Bargain Bash", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 23 + }, + "endDate": { + "Year": 2024, + "Month": 7, + "Day": 2 + } + }, + "discounts": [ + { + "categoryName": "Whiskey", + "discountPercentage": 7 + }, + { + "categoryName": "Bitters", + "discountPercentage": 15 + }, + { + "categoryName": "Brandy", + "discountPercentage": 8 + }, + { + "categoryName": "Sports Drinks", + "discountPercentage": 22 + }, + { + "categoryName": "Vodka", + "discountPercentage": 19 + } + ] + }, + { + "eventName": "Steal of a Deal Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 29 + } + }, + "discounts": [ + { + "categoryName": "Organic Wine", + "discountPercentage": 19 + }, + { + "categoryName": "White Wine", + "discountPercentage": 20 + }, + { + "categoryName": "Sparkling Wine", + "discountPercentage": 19 + }, + { + "categoryName": "Whiskey", + "discountPercentage": 17 + }, + { + "categoryName": "Vodka", + "discountPercentage": 23 + } + ] + } + ] +} +``` + +### Example 1:Writing aggregation results to a new collection + +This query writes stores with total sales greater than 30,000 into a new collection called `highSales`. + +```javascript +db.stores.aggregate([ + { + $match: { + "sales.salesByCategory.totalSales": { $gt: 30000 } + } + }, + { + $out: "highSales" + } +]) +``` + +### Example 2: Writing processed data to another collection + +This query extracts promotion events and writes them into a collection named `promotionEventsSummary`. + +```javascript +db.stores.aggregate([ + { + $project: { + eventName: 1, + promotionalDates: 1, + "discounts.categoryName": 1, + "discounts.discountPercentage": 1 + } + }, + { + $out: "promotionEventsSummary" + } +]) +``` diff --git a/reference/operators/aggregation/$redact.md b/reference/operators/aggregation/$redact.md new file mode 100644 index 0000000..89b52de --- /dev/null +++ b/reference/operators/aggregation/$redact.md @@ -0,0 +1,239 @@ +--- +title: $redact +description: Filters the content of the documents based on access rights. +type: operators +category: aggregation +--- + +# $redact + +The `$redact` stage in aggregation pipeline is used to filter fields of the documents in a collection dynamically based on access rights or other conditions. It processes each document in the pipeline and removes or retains fields based on the specified logic. + +## Syntax + +```javascript +{ + $redact: +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **``** | A valid MongoDB expression that evaluates to one of the following: `$$DESCEND`, `$$PRUNE`, or `$$KEEP`. These variables determine whether to keep, remove, or traverse deeper into the document. | + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "0fcc0bf0-ed18-4ab8-b558-9848e18058f4", + "name": "First Up Consultants | Beverage Shop - Satterfieldmouth", + "location": { + "lat": -89.2384, + "lon": -46.4012 + }, + "staff": { + "totalStaff": { + "fullTime": 8, + "partTime": 20 + } + }, + "sales": { + "totalSales": 75670, + "salesByCategory": [ + { + "categoryName": "Wine Accessories", + "totalSales": 34440 + }, + { + "categoryName": "Bitters", + "totalSales": 39496 + }, + { + "categoryName": "Rum", + "totalSales": 1734 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Unbeatable Bargain Bash", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 23 + }, + "endDate": { + "Year": 2024, + "Month": 7, + "Day": 2 + } + }, + "discounts": [ + { + "categoryName": "Whiskey", + "discountPercentage": 7 + }, + { + "categoryName": "Bitters", + "discountPercentage": 15 + }, + { + "categoryName": "Brandy", + "discountPercentage": 8 + }, + { + "categoryName": "Sports Drinks", + "discountPercentage": 22 + }, + { + "categoryName": "Vodka", + "discountPercentage": 19 + } + ] + }, + { + "eventName": "Steal of a Deal Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 29 + } + }, + "discounts": [ + { + "categoryName": "Organic Wine", + "discountPercentage": 19 + }, + { + "categoryName": "White Wine", + "discountPercentage": 20 + }, + { + "categoryName": "Sparkling Wine", + "discountPercentage": 19 + }, + { + "categoryName": "Whiskey", + "discountPercentage": 17 + }, + { + "categoryName": "Vodka", + "discountPercentage": 23 + } + ] + } + ] +} +``` + +### Example 1: Redacting sensitive information + +This query filters the `promotionEvents` field for documents where the `discountPercentage` in a promotion exceeds 15%. + +```javascript +db.stores.aggregate([ + { + $redact: { + $cond: { + if: { + $gt: ["$promotionEvents.discounts.discountPercentage", 15] + }, + then: "$$PRUNE", + else: "$$DESCEND" + } + } + } +]) +``` + +The first two results returned by this query are: + +```json +[ + { + "_id": "new-store-001", + "name": "Adatum Corporation - Downtown Branch", + "sales": { + "totalSales": 5000 + }, + "createdDate": "2025-06-11T11:11:32.262Z", + "status": "new", + "staff": { + "totalStaff": { + "fullTime": 0, + "partTime": 0 + } + }, + "version": 1, + "storeOpeningDate": "2025-06-11T11:11:32.262Z", + "storeFeatures": 213 + }, + { + "_id": "gaming-store-mall-001", + "name": "Trey Research | Gaming Paradise - Mall Location", + "location": { + "lat": 35.6762, + "lon": 139.6503 + }, + "createdDate": "2025-06-11T11:13:27.180Z", + "status": "active", + "staff": { + "totalStaff": { + "fullTime": 8, + "partTime": 12 + }, + "manager": "Alex Johnson", + "departments": [ + "gaming", + "accessories", + "repairs" + ] + }, + "sales": { + "totalSales": 0, + "salesByCategory": [] + }, + "operatingHours": { + "weekdays": "10:00-22:00", + "weekends": "09:00-23:00" + }, + "metadata": { + "version": 1, + "source": "store-management-system" + }, + "storeOpeningDate": "2025-06-11T11:11:32.262Z", + "storeFeatures": 189 + } +] +``` + +### Example 2: Restricting access based on tags + +This query removes all documents that contain the tag `#MembershipDeals`. + +```javascript +db.stores.aggregate([ + { + $redact: { + $cond: { + if: { + $in: ["#MembershipDeals", "$tag"] + }, + then: "$$PRUNE", + else: "$$DESCEND" + } + } + } +]) +``` diff --git a/reference/operators/aggregation/$replacewith.md b/reference/operators/aggregation/$replacewith.md new file mode 100644 index 0000000..e0e0ad6 --- /dev/null +++ b/reference/operators/aggregation/$replacewith.md @@ -0,0 +1,198 @@ +--- +title: $replaceWith +description: The $replaceWith operator in DocumentDB returns a document after replacing a document with the specified document +type: operators +category: aggregation +--- + +# $replaceWith + +The `$replaceWith` aggregation stage operator is used to replace the input document with the specified document. The `$replaceWith` operator transforms documents from one structure to another or replaces them entirely with new fields and values. + +## Syntax + +```mongodb +{ + "$replaceWith": +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **`newDocument`** | The new document to replace the original document| + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "0fcc0bf0-ed18-4ab8-b558-9848e18058f4", + "name": "First Up Consultants | Beverage Shop - Satterfieldmouth", + "location": { + "lat": -89.2384, + "lon": -46.4012 + }, + "staff": { + "totalStaff": { + "fullTime": 8, + "partTime": 20 + } + }, + "sales": { + "totalSales": 75670, + "salesByCategory": [ + { + "categoryName": "Wine Accessories", + "totalSales": 34440 + }, + { + "categoryName": "Bitters", + "totalSales": 39496 + }, + { + "categoryName": "Rum", + "totalSales": 1734 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Unbeatable Bargain Bash", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 23 + }, + "endDate": { + "Year": 2024, + "Month": 7, + "Day": 2 + } + }, + "discounts": [ + { + "categoryName": "Whiskey", + "discountPercentage": 7 + }, + { + "categoryName": "Bitters", + "discountPercentage": 15 + }, + { + "categoryName": "Brandy", + "discountPercentage": 8 + }, + { + "categoryName": "Sports Drinks", + "discountPercentage": 22 + }, + { + "categoryName": "Vodka", + "discountPercentage": 19 + } + ] + }, + { + "eventName": "Steal of a Deal Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 29 + } + }, + "discounts": [ + { + "categoryName": "Organic Wine", + "discountPercentage": 19 + }, + { + "categoryName": "White Wine", + "discountPercentage": 20 + }, + { + "categoryName": "Sparkling Wine", + "discountPercentage": 19 + }, + { + "categoryName": "Whiskey", + "discountPercentage": 17 + }, + { + "categoryName": "Vodka", + "discountPercentage": 23 + } + ] + } + ] +} +``` + +### Example 1 - Return a document that replaces the contents of the original document with a subset of items + +First, match a specific document to replace by the _id field and replace the contents of the document with the specified fields. + +```javascript +db.stores.aggregate([{ + $match: { + _id: "bda56164-954d-4f47-a230-ecf64b317b43" + } +}, { + $replaceWith: { + _id: "$_id", + name: "$name", + sales: "$sales.totalSales" + } +}]) +``` + +This query returns the following result: + +```json +[ + { + "_id": "bda56164-954d-4f47-a230-ecf64b317b43", + "name": "Boulder Innovations | Home Security Place - Ankundingburgh", + "sales": 37015 + } +] +``` + +### Example 2 - Return a document that replaces the contents of the original document after aggregating specified fields + +```javascript +db.stores.aggregate([{ + $match: { + _id: "bda56164-954d-4f47-a230-ecf64b317b43" + } +}, { + $replaceWith: { + _id: "$_id", + name: "$name", + totalStaff: { + $add: ["$staff.totalStaff.fullTime", "$staff.totalStaff.partTime"] + } + } +}]) +``` + +This returns the following result: + +```json +[ + { + "_id": "bda56164-954d-4f47-a230-ecf64b317b43", + "name": "Boulder Innovations | Home Security Place - Ankundingburgh", + "totalStaff": 29 + } +] +``` diff --git a/reference/operators/aggregation/$sample.md b/reference/operators/aggregation/$sample.md new file mode 100644 index 0000000..3552ac1 --- /dev/null +++ b/reference/operators/aggregation/$sample.md @@ -0,0 +1,164 @@ +--- +title: $sample +description: The $sample operator in DocumentDB returns a randomly selected number of documents +type: operators +category: aggregation +--- + +# $sample + +The `$sample` stage is used in aggregation pipelines to randomly select a specified number of documents from a collection. The `$sample` command is useful during testing, data analysis, and generating random subsets of data for machine learning. + +## Syntax + +```javascript +{ + $sample: { size: } +} +``` + +### Parameters + +| Parameter | Description | +| --- | --- | +| **`size`** | The number of documents to randomly select from the collection| + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "0fcc0bf0-ed18-4ab8-b558-9848e18058f4", + "name": "First Up Consultants | Beverage Shop - Satterfieldmouth", + "location": { + "lat": -89.2384, + "lon": -46.4012 + }, + "staff": { + "totalStaff": { + "fullTime": 8, + "partTime": 20 + } + }, + "sales": { + "totalSales": 75670, + "salesByCategory": [ + { + "categoryName": "Wine Accessories", + "totalSales": 34440 + }, + { + "categoryName": "Bitters", + "totalSales": 39496 + }, + { + "categoryName": "Rum", + "totalSales": 1734 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Unbeatable Bargain Bash", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 23 + }, + "endDate": { + "Year": 2024, + "Month": 7, + "Day": 2 + } + }, + "discounts": [ + { + "categoryName": "Whiskey", + "discountPercentage": 7 + }, + { + "categoryName": "Bitters", + "discountPercentage": 15 + }, + { + "categoryName": "Brandy", + "discountPercentage": 8 + }, + { + "categoryName": "Sports Drinks", + "discountPercentage": 22 + }, + { + "categoryName": "Vodka", + "discountPercentage": 19 + } + ] + }, + { + "eventName": "Steal of a Deal Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 29 + } + }, + "discounts": [ + { + "categoryName": "Organic Wine", + "discountPercentage": 19 + }, + { + "categoryName": "White Wine", + "discountPercentage": 20 + }, + { + "categoryName": "Sparkling Wine", + "discountPercentage": 19 + }, + { + "categoryName": "Whiskey", + "discountPercentage": 17 + }, + { + "categoryName": "Vodka", + "discountPercentage": 23 + } + ] + } + ] +} +``` + +### Example 1 - Randomly select five documents and project the corresponding document IDs + +```javascript + db.stores.aggregate([{ + $sample: { + size: 5 + } + }, { + $project: { + _id: 1 + } + }]) +``` + +This query returns the following results: + +```json +[ + { "_id": "f7ae8b40-0c66-4e80-9261-ab31bbabffb4" }, + { "_id": "25350272-6797-4f98-91f8-fe79084755c7" }, + { "_id": "c7fd1d22-1a29-4cb0-9155-1ad71d600c2b" }, + { "_id": "e602b444-9519-42e3-a2e1-b5a3da5f6e64" }, + { "_id": "189c239a-edca-434b-baae-aada3a27a2c5" } +] +``` diff --git a/reference/operators/aggregation/$set.md b/reference/operators/aggregation/$set.md new file mode 100644 index 0000000..35dcbc0 --- /dev/null +++ b/reference/operators/aggregation/$set.md @@ -0,0 +1,211 @@ +--- +title: $set +description: The $set operator in DocumentDB updates or creates a new field with a specified value +type: operators +category: aggregation +--- + +# $set + +The `$set` operator updates an existing field or creates a new field with the specified value if it does not exist. One or more fields listed are updated or created. The dot notation is used to update or create nested objects. + +## Syntax + +```javascript +{ + $set: { + newField: + } +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **`newField`** | The name of the field to update or create| +| **`expression`** | The expression that defines the value of the new or updated field| + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "0fcc0bf0-ed18-4ab8-b558-9848e18058f4", + "name": "First Up Consultants | Beverage Shop - Satterfieldmouth", + "location": { + "lat": -89.2384, + "lon": -46.4012 + }, + "staff": { + "totalStaff": { + "fullTime": 8, + "partTime": 20 + } + }, + "sales": { + "totalSales": 75670, + "salesByCategory": [ + { + "categoryName": "Wine Accessories", + "totalSales": 34440 + }, + { + "categoryName": "Bitters", + "totalSales": 39496 + }, + { + "categoryName": "Rum", + "totalSales": 1734 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Unbeatable Bargain Bash", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 23 + }, + "endDate": { + "Year": 2024, + "Month": 7, + "Day": 2 + } + }, + "discounts": [ + { + "categoryName": "Whiskey", + "discountPercentage": 7 + }, + { + "categoryName": "Bitters", + "discountPercentage": 15 + }, + { + "categoryName": "Brandy", + "discountPercentage": 8 + }, + { + "categoryName": "Sports Drinks", + "discountPercentage": 22 + }, + { + "categoryName": "Vodka", + "discountPercentage": 19 + } + ] + }, + { + "eventName": "Steal of a Deal Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 29 + } + }, + "discounts": [ + { + "categoryName": "Organic Wine", + "discountPercentage": 19 + }, + { + "categoryName": "White Wine", + "discountPercentage": 20 + }, + { + "categoryName": "Sparkling Wine", + "discountPercentage": 19 + }, + { + "categoryName": "Whiskey", + "discountPercentage": 17 + }, + { + "categoryName": "Vodka", + "discountPercentage": 23 + } + ] + } + ] +} +``` + +### Example 1 - Update an existing field + +```javascript +db.stores.updateOne({ + _id: "8eefe8bd-5d6f-4038-90e8-05a8277637f0" + }, + { + $set: { + name: "Lakeshore Retail" + } + }) +``` + +### Example 2 - Update an existing field in a nested object + +```javascript +db.stores.updateOne({ + _id: "8eefe8bd-5d6f-4038-90e8-05a8277637f0" + }, + { + $set: { + "staff.totalStaff.partTime": 9 + } + }) +``` + +### Example 3 - Create a new field that does not exist + +Create a new field called "formerName" with the old name of the store. + +```javascript +db.stores.updateOne({ + _id: "8eefe8bd-5d6f-4038-90e8-05a8277637f0" + }, + { + $set: { + formerName: "Tailwind Traders | Drone Shoppe - New Theodora" + } + }) +``` + +### Example 4 - Create a new field in a nested object + +Create a new field within the nested totalStaff object to specify a count of temporary staff members. + +```javascript +db.stores.updateOne({ + _id: "8eefe8bd-5d6f-4038-90e8-05a8277637f0" + }, + { + $set: { + "staff.totalStaff.temporary": 3 + } + }) +``` + +### Example 5 - Update multiple fields + +```javascript +db.stores.updateOne({ + _id: "8eefe8bd-5d6f-4038-90e8-05a8277637f0" + }, + { + $set: { + "staff.totalStaff.partTime": 9, + "sales.totalSales": 3611 + } + }) +``` diff --git a/reference/operators/aggregation/$skip.md b/reference/operators/aggregation/$skip.md new file mode 100644 index 0000000..f5a025d --- /dev/null +++ b/reference/operators/aggregation/$skip.md @@ -0,0 +1,355 @@ +--- +title: $skip +description: The $skip stage in the aggregation pipeline is used to skip a specified number of documents from the input and pass the remaining documents to the next stage in the pipeline. +type: operators +category: aggregation +--- + +# $skip + +The $skip stage in the aggregation pipeline is used to skip a specified number of documents from the input and pass the remaining documents to the next stage in the pipeline. The stage is useful for implementing pagination in queries and for controlling the subset of documents that subsequent stages in the pipeline operate on. + +## Syntax + +```javascript +{ + $skip: +} +``` + +### Parameters + +| Parameter | Description | +| --- | --- | +| **`number`** | The number of documents to skip before passing the remaining documents to the next stage. | + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + _id: '0fcc0bf0-ed18-4ab8-b558-9848e18058f4', + name: 'First Up Consultants | Beverage Shop - Satterfieldmouth', + location: { lat: -89.2384, lon: -46.4012 }, + staff: { employeeCount: { fullTime: 2, partTime: 20 } }, + sales: { + salesByCategory: [ + { categoryName: 'Wine Accessories', totalSales: 34450 }, + { categoryName: 'Bitters', totalSales: 39496 }, + { categoryName: 'Rum', totalSales: 1734 } + ], + revenue: 75670 + }, + promotionEvents: [ + { + eventName: 'Unbeatable Bargain Bash', + promotionalDates: { + startDate: { Year: 2024, Month: 6, Day: 23 }, + endDate: { Year: 2024, Month: 7, Day: 2 } + }, + discounts: [ + { categoryName: 'Whiskey', discountPercentage: 7 }, + { categoryName: 'Bitters', discountPercentage: 15 }, + { categoryName: 'Brandy', discountPercentage: 8 }, + { categoryName: 'Sports Drinks', discountPercentage: 22 }, + { categoryName: 'Vodka', discountPercentage: 19 } + ] + }, + { + eventName: 'Steal of a Deal Days', + promotionalDates: { + startDate: { Year: 2024, Month: 9, Day: 21 }, + endDate: { Year: 2024, Month: 9, Day: 29 } + }, + discounts: [ + { categoryName: 'Organic Wine', discountPercentage: 19 }, + { categoryName: 'White Wine', discountPercentage: 20 }, + { categoryName: 'Sparkling Wine', discountPercentage: 19 }, + { categoryName: 'Whiskey', discountPercentage: 17 }, + { categoryName: 'Vodka', discountPercentage: 23 } + ] + }, + { + eventName: 'Summer Sale', + promotionalDates: { + startDate: { Year: 2024, Month: 6, Day: 1 }, + endDate: { Year: 2024, Month: 6, Day: 15 } + }, + discounts: [ { categoryName: 'DJ Speakers', discountPercentage: 20 } ] + } + ], + company: 'First Up Consultants', + city: 'Satterfieldmouth', + storeOpeningDate: ISODate("2024-09-20T18:28:57.302Z"), + lastUpdated: Timestamp({ t: 1729448937, i: 1 }), + store: { promotionEvents: null }, + tag: [ '#ShopLocal' ] + } +``` + +### Example 1: Skipping documents in a collection + +To skip the first 2 documents and return the rest, you can use the following aggregation pipeline: + +```javascript +db.stores.aggregate([ + { $skip: 2 } +]) +``` + +The first two results returned by this query are: + +```json +[ + { + "_id": "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c5", + "store": { + "name": "Downtown Store", + "promotionEvents": ["Summer Sale", "Black Friday", "Holiday Deals"] + } + }, + { + "_id": "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c6", + "store": { + "name": "Uptown Store", + "promotionEvents": ["Back to School", "Winter Sale"] + } + } +] +``` + +### Example 2: Skipping documents and then limiting the result + +To skip the first 2 documents and then limit the result to the next 3 documents, you can combine $skip with $limit: + +```javascript +db.stores.aggregate([ + { $skip: 2 }, + { $limit: 3 } +]) +``` + +The first two results returned by this query are: + +```json +[ + { + "_id": "728c068a-638c-40af-9172-8ccfa7dddb49", + "name": "Contoso, Ltd. | Book Store - Lake Myron", + "location": { + "lat": 29.416, + "lon": 21.5231 + }, + "staff": { + "employeeCount": { + "fullTime": 7, + "partTime": 16 + } + }, + "sales": { + "salesByCategory": [ + { + "categoryName": "Science Fiction", + "totalSales": 34879 + } + ], + "revenue": 34879 + }, + "promotionEvents": [ + { + "eventName": "Blowout Bonanza", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 30 + } + }, + "discounts": [ + { + "categoryName": "Children's Books", + "discountPercentage": 11 + }, + { + "categoryName": "Fiction", + "discountPercentage": 21 + } + ] + } + ], + "company": "Contoso, Ltd.", + "city": "Lake Myron", + "storeOpeningDate": "ISODate('2024-09-28T18:23:21.591Z')", + "lastUpdated": "Timestamp({ t: 1730139801, i: 1 })", + "storeFeatures": 239 + }, + { + "_id": "44fdb9b9-df83-4492-8f71-b6ef648aa312", + "name": "Fourth Coffee | Storage Solution Gallery - Port Camilla", + "location": { + "lat": 78.3889, + "lon": 0.6784 + }, + "staff": { + "employeeCount": { + "fullTime": 17, + "partTime": 15 + } + }, + "sales": { + "salesByCategory": [ + { + "categoryName": "Storage Boxes", + "totalSales": 2236 + } + ], + "revenue": 2236 + }, + "promotionEvents": [ + { + "eventName": "Major Discount Mania", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 23 + }, + "endDate": { + "Year": 2024, + "Month": 7, + "Day": 3 + } + }, + "discounts": [ + { + "categoryName": "Bathroom Storage", + "discountPercentage": 19 + }, + { + "categoryName": "Kitchen Storage", + "discountPercentage": 10 + } + ] + }, + { + "eventName": "Flash Deal Frenzy", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 30 + } + }, + "discounts": [ + { + "categoryName": "Under-Bed Storage", + "discountPercentage": 20 + }, + { + "categoryName": "Closet Organizers", + "discountPercentage": 21 + } + ] + } + ], + "company": "Fourth Coffee", + "city": "Port Camilla", + "storeOpeningDate": "ISODate('2024-09-23T06:02:53.844Z')", + "lastUpdated": "Timestamp({ t: 1729663373, i: 1 })", + "storeFeatures": 222 + } +] +``` + +### Example 3: Skipping documents in a complex pipeline + +To skip the first promotion event and then project the remaining events for a specific store: + +```javascript +db.stores.aggregate([ + { $match: { "_id": "0fcc0bf0-ed18-4ab8-b558-9848e18058f4", } }, + { $unwind: "$promotionEvents" }, + { $skip: 1 }, + { $project: { "promotionEvents": 1, _id: 0 } } +]) +``` + +The first two results returned by this query are: + +```json +[ + { + "promotionEvents": { + "eventName": "Steal of a Deal Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 29 + } + }, + "discounts": [ + { + "categoryName": "Organic Wine", + "discountPercentage": 19 + }, + { + "categoryName": "White Wine", + "discountPercentage": 20 + }, + { + "categoryName": "Sparkling Wine", + "discountPercentage": 19 + }, + { + "categoryName": "Whiskey", + "discountPercentage": 17 + }, + { + "categoryName": "Vodka", + "discountPercentage": 23 + } + ] + } + }, + { + "promotionEvents": { + "eventName": "Summer Sale", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 1 + }, + "endDate": { + "Year": 2024, + "Month": 6, + "Day": 15 + } + }, + "discounts": [ + { + "categoryName": "DJ Speakers", + "discountPercentage": 20 + } + ] + } + } +] +``` diff --git a/reference/operators/aggregation/$sort.md b/reference/operators/aggregation/$sort.md new file mode 100644 index 0000000..dfc9459 --- /dev/null +++ b/reference/operators/aggregation/$sort.md @@ -0,0 +1,301 @@ +--- +title: $sort +description: The $sort stage in the aggregation pipeline is used to order the documents in the pipeline by a specified field or fields. +type: operators +category: aggregation +--- + +# $sort + +The $sort stage in the aggregation pipeline is used to order the documents in the pipeline by a specified field or fields. This stage helps you sort data, like arranging sales by amount or events by date. + +## Syntax + +```javascript +{ + $sort: { + < field1 >: < sort order > , + < field2 >: < sort order > + } +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **`field`** | The field to sort by | +| **`sort order`** | The order in which we should sort the field. 1 for ascending order and -1 for descending order. | + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "0fcc0bf0-ed18-4ab8-b558-9848e18058f4", + "name": "First Up Consultants | Beverage Shop - Satterfieldmouth", + "location": { + "lat": -89.2384, + "lon": -46.4012 + }, + "staff": { + "totalStaff": { + "fullTime": 8, + "partTime": 20 + } + }, + "sales": { + "totalSales": 75670, + "salesByCategory": [ + { + "categoryName": "Wine Accessories", + "totalSales": 34440 + }, + { + "categoryName": "Bitters", + "totalSales": 39496 + }, + { + "categoryName": "Rum", + "totalSales": 1734 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Unbeatable Bargain Bash", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 23 + }, + "endDate": { + "Year": 2024, + "Month": 7, + "Day": 2 + } + }, + "discounts": [ + { + "categoryName": "Whiskey", + "discountPercentage": 7 + }, + { + "categoryName": "Bitters", + "discountPercentage": 15 + }, + { + "categoryName": "Brandy", + "discountPercentage": 8 + }, + { + "categoryName": "Sports Drinks", + "discountPercentage": 22 + }, + { + "categoryName": "Vodka", + "discountPercentage": 19 + } + ] + }, + { + "eventName": "Steal of a Deal Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 29 + } + }, + "discounts": [ + { + "categoryName": "Organic Wine", + "discountPercentage": 19 + }, + { + "categoryName": "White Wine", + "discountPercentage": 20 + }, + { + "categoryName": "Sparkling Wine", + "discountPercentage": 19 + }, + { + "categoryName": "Whiskey", + "discountPercentage": 17 + }, + { + "categoryName": "Vodka", + "discountPercentage": 23 + } + ] + } + ] +} +``` + +### Example 1: Sorting by total sales in sescending order + +To sort the sales categories by their total sales in descending order: + +```javascript +db.collection.aggregate([ + { + $unwind: "$store.sales.salesByCategory" + }, + { + $sort: { "store.sales.salesByCategory.totalSales": -1 } + } +]) +``` + +The first two results returned by this query are: + +```json +[ + { + "_id": "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c5", + "store": { + "name": "Downtown Store", + "sales": { + "salesByCategory": [ + { + "category": "Electronics", + "totalSales": 15000 + }, + { + "category": "Clothing", + "totalSales": 12000 + }, + { + "category": "Home Goods", + "totalSales": 10000 + } + ] + } + } + }, + { + "_id": "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c6", + "store": { + "name": "Uptown Store", + "sales": { + "salesByCategory": [ + { + "category": "Electronics", + "totalSales": 20000 + }, + { + "category": "Clothing", + "totalSales": 18000 + }, + { + "category": "Home Goods", + "totalSales": 15000 + } + ] + } + } + } +] +``` + +### Example 2: Sorting by event start date in ascending order + +To sort the promotion events by their start dates in ascending order: + +```javascript +db.collection.aggregate([ + { + $unwind: "$store.promotionEvents" + }, + { + $sort: { "store.promotionEvents.promotionalDates.startDate": 1 } + } +]) +``` + +The first two results returned by this query are: + +```json +[ + { + "_id": "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c5", + "store": { + "name": "Downtown Store", + "promotionEvents": [ + { + "eventName": "Summer Sale", + "promotionalDates": { + "startDate": "2024-06-01T00:00:00Z", + "endDate": "2024-06-30T23:59:59Z" + } + }, + { + "eventName": "Black Friday", + "promotionalDates": { + "startDate": "2024-11-25T00:00:00Z", + "endDate": "2024-11-25T23:59:59Z" + } + }, + { + "eventName": "Holiday Deals", + "promotionalDates": { + "startDate": "2024-12-01T00:00:00Z", + "endDate": "2024-12-31T23:59:59Z" + } + } + ] + } + }, + { + "_id": "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c6", + "store": { + "name": "Uptown Store", + "promotionEvents": [ + { + "eventName": "Back to School", + "promotionalDates": { + "startDate": "2024-08-01T00:00:00Z", + "endDate": "2024-08-31T23:59:59Z" + } + }, + { + "eventName": "Winter Sale", + "promotionalDates": { + "startDate": "2024-12-01T00:00:00Z", + "endDate": "2024-12-31T23:59:59Z" + } + } + ] + } + } +] +``` + +### Example 3: Sorting an array of objects + +The example sorts the `salesByCategory` array in place based on the `totalSales` field in ascending order. + +```javascript +db.stores.updateOne({ + _id: "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c5" + }, { + $push: { + "sales.salesByCategory": { + $each: [], + $sort: { + totalSales: 1 + } + } + } + } +) +``` diff --git a/reference/operators/aggregation/$sortbycount.md b/reference/operators/aggregation/$sortbycount.md new file mode 100644 index 0000000..96aba36 --- /dev/null +++ b/reference/operators/aggregation/$sortbycount.md @@ -0,0 +1,181 @@ +--- +title: $sortByCount +description: The $sortByCount stage in the aggregation pipeline is used to group documents by a specified expression and then sort the count of documents in each group in descending order. +type: operators +category: aggregation +--- + +# $sortByCount + +The $sortByCount stage in the aggregation pipeline is used to group documents by a specified expression and then sort the count of documents in each group in descending order. The `$sortByCount` stage is useful for quickly identifying the most common values within a dataset. + +## Syntax + +```javascript +{ + $sortByCount: +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **`expression`** | This is the field or computed expression on which to group and count the documents. | + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "0fcc0bf0-ed18-4ab8-b558-9848e18058f4", + "name": "First Up Consultants | Beverage Shop - Satterfieldmouth", + "location": { + "lat": -89.2384, + "lon": -46.4012 + }, + "staff": { + "totalStaff": { + "fullTime": 8, + "partTime": 20 + } + }, + "sales": { + "totalSales": 75670, + "salesByCategory": [ + { + "categoryName": "Wine Accessories", + "totalSales": 34440 + }, + { + "categoryName": "Bitters", + "totalSales": 39496 + }, + { + "categoryName": "Rum", + "totalSales": 1734 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Unbeatable Bargain Bash", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 23 + }, + "endDate": { + "Year": 2024, + "Month": 7, + "Day": 2 + } + }, + "discounts": [ + { + "categoryName": "Whiskey", + "discountPercentage": 7 + }, + { + "categoryName": "Bitters", + "discountPercentage": 15 + }, + { + "categoryName": "Brandy", + "discountPercentage": 8 + }, + { + "categoryName": "Sports Drinks", + "discountPercentage": 22 + }, + { + "categoryName": "Vodka", + "discountPercentage": 19 + } + ] + }, + { + "eventName": "Steal of a Deal Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 29 + } + }, + "discounts": [ + { + "categoryName": "Organic Wine", + "discountPercentage": 19 + }, + { + "categoryName": "White Wine", + "discountPercentage": 20 + }, + { + "categoryName": "Sparkling Wine", + "discountPercentage": 19 + }, + { + "categoryName": "Whiskey", + "discountPercentage": 17 + }, + { + "categoryName": "Vodka", + "discountPercentage": 23 + } + ] + } + ] +} +``` + +### Example 1: Group promotion events by name and count occurrences in descending order + +To group by the eventName field and count the number of occurrences of each event name, sorting the results in descending order of the count + +```javascript +db.stores.aggregate([ + { $unwind: "$promotionEvents" }, + { $sortByCount: "$promotionEvents.eventName" } +]) +``` + +This query returns the following results: + +```json +[ + { "_id": "Crazy Deal Days", "count": 4239 }, + { "_id": "Markdown Madness", "count": 2967 }, + { "_id": "Bargain Bonanza", "count": 2925 }, + { "_id": "Crazy Discount Days", "count": 2922 }, + { "_id": "Price Smash Spectacular", "count": 2915 }, + { "_id": "Super Saver Spectacular", "count": 2900 }, + { "_id": "Crazy Markdown Madness", "count": 2899 }, + { "_id": "Price Cut Carnival", "count": 2868 }, + { "_id": "Grand Bargain Bash", "count": 2849 }, + { "_id": "Bargain Blitz Bash", "count": 2843 }, + { "_id": "Grand Savings Gala", "count": 2826 }, + { "_id": "Super Saver Fiesta", "count": 1551 }, + { "_id": "Major Deal Days", "count": 1548 }, + { "_id": "Price Slash Carnival", "count": 1535 }, + { "_id": "Super Discount Days", "count": 1533 }, + { "_id": "Big Deal Bonanza", "count": 1533 }, + { "_id": "Incredible Savings Showcase", "count": 1531 }, + { "_id": "Unbeatable Savings Spectacular", "count": 1518 }, + { "_id": "Fantastic Deal Days", "count": 1511 }, + { "_id": "Flash Bargain Frenzy", "count": 1504 } +] +``` + +This pipeline will: + +1. Use $unwind to deconstruct the promotionEvents array field from the input documents. +2. Use $sortByCount to group by the eventName field and count the number of occurrences of each event name, sorting the results in descending order of the count. diff --git a/reference/operators/aggregation/$tobool.md b/reference/operators/aggregation/$tobool.md new file mode 100644 index 0000000..0e02e15 --- /dev/null +++ b/reference/operators/aggregation/$tobool.md @@ -0,0 +1,241 @@ +--- +title: $toBool +description: The $toBool operator converts an expression into a Boolean type +type: operators +category: aggregation +--- + +# $toBool + +The `$toBool` operator converts an expression into a Boolean value. Boolean values are returned as is without a conversion. Nonzero numeric values are converted to true while Decimal, Long, Double or Int values of 0 are converted to false. All other data types are converted to true. + +## Syntax + +```javascript +{ + $toBool: < expression > +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **`expression`** | The specified value to convert into a Boolean value| + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "0fcc0bf0-ed18-4ab8-b558-9848e18058f4", + "name": "First Up Consultants | Beverage Shop - Satterfieldmouth", + "location": { + "lat": -89.2384, + "lon": -46.4012 + }, + "staff": { + "totalStaff": { + "fullTime": 8, + "partTime": 20 + } + }, + "sales": { + "totalSales": 75670, + "salesByCategory": [ + { + "categoryName": "Wine Accessories", + "totalSales": 34440 + }, + { + "categoryName": "Bitters", + "totalSales": 39496 + }, + { + "categoryName": "Rum", + "totalSales": 1734 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Unbeatable Bargain Bash", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 23 + }, + "endDate": { + "Year": 2024, + "Month": 7, + "Day": 2 + } + }, + "discounts": [ + { + "categoryName": "Whiskey", + "discountPercentage": 7 + }, + { + "categoryName": "Bitters", + "discountPercentage": 15 + }, + { + "categoryName": "Brandy", + "discountPercentage": 8 + }, + { + "categoryName": "Sports Drinks", + "discountPercentage": 22 + }, + { + "categoryName": "Vodka", + "discountPercentage": 19 + } + ] + }, + { + "eventName": "Steal of a Deal Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 29 + } + }, + "discounts": [ + { + "categoryName": "Organic Wine", + "discountPercentage": 19 + }, + { + "categoryName": "White Wine", + "discountPercentage": 20 + }, + { + "categoryName": "Sparkling Wine", + "discountPercentage": 19 + }, + { + "categoryName": "Whiskey", + "discountPercentage": 17 + }, + { + "categoryName": "Vodka", + "discountPercentage": 23 + } + ] + } + ] +} +``` + +### Example 1: Convert a Double value into a Boolean value + +To convert the value of the latitude field from a double to a boolean, run a query using the $toBool operator on the field to make the conversion. Positive numeric values are converted to true. + +```javascript +db.stores.aggregate([{ + $match: { + _id: "b0107631-9370-4acd-aafa-8ac3511e623d" + } +}, { + $project: { + originalLatitude: "$location.lat", + latitudeAsBool: { + $toBool: "$location.lat" + } + } +}]) +``` + +This query returns the following result: + +```json +[ + { + "_id": "b0107631-9370-4acd-aafa-8ac3511e623d", + "originalLatitude": 72.8377, + "latitudeAsBool": true + } +] +``` + +### Example 2: Convert a String value into a Boolean value + +To convert the value of the _id field from a string to a boolean, run a query using the $toBool value to make the conversion. String values are converted to true. + +```javascript + db.stores.aggregate([{ + $match: { + _id: "b0107631-9370-4acd-aafa-8ac3511e623d" + } + }, { + $project: { + originalId: "$_id", + idAsBool: { + $toBool: "$_id" + } + } + }]) +``` + +This query returns the following result: + +```json +[ + { + "_id": "b0107631-9370-4acd-aafa-8ac3511e623d", + "originalId": "b0107631-9370-4acd-aafa-8ac3511e623d", + "idAsBool": true + } +] +``` + +### Example 3: Convert an Int value into a Boolean value + +To convert the value of the sales.totalSales field from integer to boolean, run a query using the $toBool operator to make the conversion. Positive numeric values are converted to true. + +```javascript +db.stores.aggregate([{ + $match: { + _id: "b0107631-9370-4acd-aafa-8ac3511e623d" + } +}, { + $project: { + originalTotalSales: "$sales.totalSales", + totalSalesAsBool: { + $toBool: "$sales.totalSales" + } + } +}]) +``` + +This query returns the following result: + +```json +[ + { + "_id": "b0107631-9370-4acd-aafa-8ac3511e623d", + "originalTotalSales": 9366, + "totalSalesAsBool": true + } +] +``` + +This table delineates the expected behavior of the $toBool operator based on the data type of the input expression. + +| **Value Type** | **Behavior/Output** | +|--------------------------------------------------------------|---------------------| +| Boolean value true | Output -> true | +| Boolean value false | Output -> false | +| Any Double, Int, Long, or Decimal value | Output -> true | +| Any ISODate value | Output -> true | +| Null value | Output -> null | diff --git a/reference/operators/aggregation/$todate.md b/reference/operators/aggregation/$todate.md new file mode 100644 index 0000000..3bc1f0a --- /dev/null +++ b/reference/operators/aggregation/$todate.md @@ -0,0 +1,173 @@ +--- +title: $toDate +description: The $toDate operator converts supported types to a proper Date object. +type: operators +category: aggregation +--- + +# $toDate + +The `$toDate` operator converts a specified value into a date type. + +## Syntax + +```javascript +{ + $toDate: +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **`expression`** | An expression that can be converted to a date. Supported formats include: ISO date strings, milliseconds since Unix epoch (number), ObjectId, and Timestamp. If the expression can't be converted to a date, the operation returns an error. | + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "0fcc0bf0-ed18-4ab8-b558-9848e18058f4", + "name": "First Up Consultants | Beverage Shop - Satterfieldmouth", + "location": { + "lat": -89.2384, + "lon": -46.4012 + }, + "staff": { + "totalStaff": { + "fullTime": 8, + "partTime": 20 + } + }, + "sales": { + "totalSales": 75670, + "salesByCategory": [ + { + "categoryName": "Wine Accessories", + "totalSales": 34440 + }, + { + "categoryName": "Bitters", + "totalSales": 39496 + }, + { + "categoryName": "Rum", + "totalSales": 1734 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Unbeatable Bargain Bash", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 23 + }, + "endDate": { + "Year": 2024, + "Month": 7, + "Day": 2 + } + }, + "discounts": [ + { + "categoryName": "Whiskey", + "discountPercentage": 7 + }, + { + "categoryName": "Bitters", + "discountPercentage": 15 + }, + { + "categoryName": "Brandy", + "discountPercentage": 8 + }, + { + "categoryName": "Sports Drinks", + "discountPercentage": 22 + }, + { + "categoryName": "Vodka", + "discountPercentage": 19 + } + ] + }, + { + "eventName": "Steal of a Deal Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 29 + } + }, + "discounts": [ + { + "categoryName": "Organic Wine", + "discountPercentage": 19 + }, + { + "categoryName": "White Wine", + "discountPercentage": 20 + }, + { + "categoryName": "Sparkling Wine", + "discountPercentage": 19 + }, + { + "categoryName": "Whiskey", + "discountPercentage": 17 + }, + { + "categoryName": "Vodka", + "discountPercentage": 23 + } + ] + } + ] +} +``` + +### Example 1: Convert timestamp to date + +To convert the value of the lastUpdated field from a Unix timestamp to a date format, run a query using the $toDate operator to make the conversion. + +```javascript +db.stores.aggregate([{ + $match: { + _id: "905d1939-e03a-413e-a9c4-221f74055aac" + } + }, + { + $project: { + name: 1, + lastUpdated: 1, + lastUpdatedAsDate: { + $toDate: "$lastUpdated" + } + } + } +]) +``` + +This query returns the following result: + +```json +[ + { + "_id": "905d1939-e03a-413e-a9c4-221f74055aac", + "name": "Trey Research | Home Office Depot - Lake Freeda", + "lastUpdated": { "t": 1729983325, "i": 1 }, + "lastUpdatedAsDate": ISODate("2024-10-26T22:55:25.000Z") + } +] +``` diff --git a/reference/operators/aggregation/$todecimal.md b/reference/operators/aggregation/$todecimal.md new file mode 100644 index 0000000..570b8cd --- /dev/null +++ b/reference/operators/aggregation/$todecimal.md @@ -0,0 +1,198 @@ +--- +title: $toDecimal +description: The $toDecimal operator converts an expression into a Decimal type +type: operators +category: aggregation +--- + +# $toDecimal + +The `$toDecimal` operator converts an input expression into a Decimal value. Long, Double or Int values are simply converted to a Decimal data type, while Decimal values are returned as is. A boolean value of true is converted to 1, while a boolean false is converted to 0. Lastly, ISODates are converted to a Decimal value corresponding to the number of milliseconds since January 1st, 1970 represented by the ISODate value. + +## Syntax + +```javascript +{ + $toDecimal: < expression > +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **`expression`** | The specified value to convert into a Decimal value| + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "0fcc0bf0-ed18-4ab8-b558-9848e18058f4", + "name": "First Up Consultants | Beverage Shop - Satterfieldmouth", + "location": { + "lat": -89.2384, + "lon": -46.4012 + }, + "staff": { + "totalStaff": { + "fullTime": 8, + "partTime": 20 + } + }, + "sales": { + "totalSales": 75670, + "salesByCategory": [ + { + "categoryName": "Wine Accessories", + "totalSales": 34440 + }, + { + "categoryName": "Bitters", + "totalSales": 39496 + }, + { + "categoryName": "Rum", + "totalSales": 1734 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Unbeatable Bargain Bash", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 23 + }, + "endDate": { + "Year": 2024, + "Month": 7, + "Day": 2 + } + }, + "discounts": [ + { + "categoryName": "Whiskey", + "discountPercentage": 7 + }, + { + "categoryName": "Bitters", + "discountPercentage": 15 + }, + { + "categoryName": "Brandy", + "discountPercentage": 8 + }, + { + "categoryName": "Sports Drinks", + "discountPercentage": 22 + }, + { + "categoryName": "Vodka", + "discountPercentage": 19 + } + ] + }, + { + "eventName": "Steal of a Deal Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 29 + } + }, + "discounts": [ + { + "categoryName": "Organic Wine", + "discountPercentage": 19 + }, + { + "categoryName": "White Wine", + "discountPercentage": 20 + }, + { + "categoryName": "Sparkling Wine", + "discountPercentage": 19 + }, + { + "categoryName": "Whiskey", + "discountPercentage": 17 + }, + { + "categoryName": "Vodka", + "discountPercentage": 23 + } + ] + } + ] +} +``` + +### Example 1: Convert a Double value into a Decimal value + +To convert the value of the latitude field from a double to a decimal value, run a query using the $toDecimal operator to make the conversion. + +```javascript +db.stores.aggregate([{ + $match: { + _id: "b0107631-9370-4acd-aafa-8ac3511e623d" + } +}, { + $project: { + originalLatitude: "$location.lat", + latitudeAsDecimal: { + $toDecimal: "$location.lat" + } + } +}]) +``` + +This query returns the following result: + +```json +[ + { + "_id": "b0107631-9370-4acd-aafa-8ac3511e623d", + "originalLatitude": 72.8377, + "latitudeAsDecimal": "Decimal128('72.8377000000000')" + } +] +``` + +### Example 2: Convert an ISODate value into a Decimal value + +To convert an ISODate to a decimal value, run a query using the $toDecimal operator on the value to make the conversion. + +```javascript +db.stores.aggregate([{ + $match: { + _id: "b0107631-9370-4acd-aafa-8ac3511e623d" + } +}, { + $project: { + dateAsDecimal: { + $toDecimal: ISODate("2025-01-06T00:00:00.000Z") + } + } +}]) +``` + +This query returns the following result: + +```json +[ + { + "_id": "b0107631-9370-4acd-aafa-8ac3511e623d", + "dateAsDecimal": "Decimal128('1736121600000')" + } +] +``` diff --git a/reference/operators/aggregation/$todouble.md b/reference/operators/aggregation/$todouble.md new file mode 100644 index 0000000..9d116b8 --- /dev/null +++ b/reference/operators/aggregation/$todouble.md @@ -0,0 +1,181 @@ +--- +title: $toDouble +description: The $toDouble operator converts an expression into a Double value +type: operators +category: aggregation +--- + +# $toDouble + +The `$toDouble` operator converts a specified value into a Double value. + +## Syntax + +```javascript +{ + $toDouble: < expression > +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **`expression`** | The specified value to convert into a Double value | + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "0fcc0bf0-ed18-4ab8-b558-9848e18058f4", + "name": "First Up Consultants | Beverage Shop - Satterfieldmouth", + "location": { + "lat": -89.2384, + "lon": -46.4012 + }, + "staff": { + "totalStaff": { + "fullTime": 8, + "partTime": 20 + } + }, + "sales": { + "totalSales": 75670, + "salesByCategory": [ + { + "categoryName": "Wine Accessories", + "totalSales": 34440 + }, + { + "categoryName": "Bitters", + "totalSales": 39496 + }, + { + "categoryName": "Rum", + "totalSales": 1734 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Unbeatable Bargain Bash", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 23 + }, + "endDate": { + "Year": 2024, + "Month": 7, + "Day": 2 + } + }, + "discounts": [ + { + "categoryName": "Whiskey", + "discountPercentage": 7 + }, + { + "categoryName": "Bitters", + "discountPercentage": 15 + }, + { + "categoryName": "Brandy", + "discountPercentage": 8 + }, + { + "categoryName": "Sports Drinks", + "discountPercentage": 22 + }, + { + "categoryName": "Vodka", + "discountPercentage": 19 + } + ] + }, + { + "eventName": "Steal of a Deal Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 29 + } + }, + "discounts": [ + { + "categoryName": "Organic Wine", + "discountPercentage": 19 + }, + { + "categoryName": "White Wine", + "discountPercentage": 20 + }, + { + "categoryName": "Sparkling Wine", + "discountPercentage": 19 + }, + { + "categoryName": "Whiskey", + "discountPercentage": 17 + }, + { + "categoryName": "Vodka", + "discountPercentage": 23 + } + ] + } + ] +} +``` + +### Example 1: Convert a String value into a Double value + +To convert the string representation of 72 ("72") into a double value, run a query using the $toDouble operator on the string to make the conversion. + +```javascript +db.stores.aggregate([{ + $match: { + _id: "b0107631-9370-4acd-aafa-8ac3511e623d" + } +}, { + $project: { + originalLatitude: "$location.lat", + latitudeAsDouble: { + $toDouble: { + $toString: "72" + } + } + } +}]) +``` + +This query returns the following result: + +```json +[ + { + "_id": "b0107631-9370-4acd-aafa-8ac3511e623d", + "originalLatitude": 72.8377, + "latitudeAsDouble": 72 + } +] +``` + +This table delineates the expected behavior of the $toDouble operator based on the data type of the input value. + +| **Value Type** | **Behavior/Output** | +|--------------------------------------------------------------|---------------------| +| Boolean value true | Output -> 1 | +| Boolean value false | Output -> 0 | +| Double value. E.g., 72.0 | Output -> 72 | +| String representation of a number value. For example, "72" | Output -> 72 | +| Null value | Output -> null | diff --git a/reference/operators/aggregation/$toint.md b/reference/operators/aggregation/$toint.md new file mode 100644 index 0000000..839beba --- /dev/null +++ b/reference/operators/aggregation/$toint.md @@ -0,0 +1,236 @@ +--- +title: $toInt +description: The $toInt operator converts an expression into an Integer +type: operators +category: aggregation +--- + +# $toInt + +The `$toInt` operator converts a specified value into an integer value. + +## Syntax + +The syntax for the `$toInt` operator is: + +```javascript +{ + $toInt: < expression > +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **`expression`** | The specified value to convert into an Integer value| + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "0fcc0bf0-ed18-4ab8-b558-9848e18058f4", + "name": "First Up Consultants | Beverage Shop - Satterfieldmouth", + "location": { + "lat": -89.2384, + "lon": -46.4012 + }, + "staff": { + "totalStaff": { + "fullTime": 8, + "partTime": 20 + } + }, + "sales": { + "totalSales": 75670, + "salesByCategory": [ + { + "categoryName": "Wine Accessories", + "totalSales": 34440 + }, + { + "categoryName": "Bitters", + "totalSales": 39496 + }, + { + "categoryName": "Rum", + "totalSales": 1734 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Unbeatable Bargain Bash", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 23 + }, + "endDate": { + "Year": 2024, + "Month": 7, + "Day": 2 + } + }, + "discounts": [ + { + "categoryName": "Whiskey", + "discountPercentage": 7 + }, + { + "categoryName": "Bitters", + "discountPercentage": 15 + }, + { + "categoryName": "Brandy", + "discountPercentage": 8 + }, + { + "categoryName": "Sports Drinks", + "discountPercentage": 22 + }, + { + "categoryName": "Vodka", + "discountPercentage": 19 + } + ] + }, + { + "eventName": "Steal of a Deal Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 29 + } + }, + "discounts": [ + { + "categoryName": "Organic Wine", + "discountPercentage": 19 + }, + { + "categoryName": "White Wine", + "discountPercentage": 20 + }, + { + "categoryName": "Sparkling Wine", + "discountPercentage": 19 + }, + { + "categoryName": "Whiskey", + "discountPercentage": 17 + }, + { + "categoryName": "Vodka", + "discountPercentage": 23 + } + ] + } + ] +} +``` + +### Example 1: Convert a Double value into an Integer value + +To convert the value of the latitude field from a double to an int, run a query using the $toInt operator on the field to make the conversion. + +```javascript +db.stores.aggregate([{ + $match: { + _id: "b0107631-9370-4acd-aafa-8ac3511e623d" + } +}, { + $project: { + originalLatitude: "$location.lat", + latitudeAsInt: { + $toInt: "$location.lat" + } + } +}]) +``` + +This query returns the following result: + +```json +[ + { + "_id": "b0107631-9370-4acd-aafa-8ac3511e623d", + "originalLatitude": 72.8377, + "latitudeAsInt": 72 + } +] +``` + +### Example 2: Convert a String value into an Integer value + +To convert the string representation of 72 ("72") to an integer value, run a query using the $toInt operator on the value to make the conversion. + +```javascript +db.stores.aggregate([{ + $match: { + _id: "b0107631-9370-4acd-aafa-8ac3511e623d" + } +}, { + $project: { + originalLatitude: "$location.lat", + latitudeAsInt: { + $toInt: { + $toString: "72" + } + } + } +}]) +``` + +This query returns the following result: + +```json +[ + { + "_id": "b0107631-9370-4acd-aafa-8ac3511e623d", + "originalLatitude": 72.8377, + "latitudeAsInt": 72 + } +] +``` + +However, the following query returns an error since the string "72.0" isn't the string representation of an integer value. + +```javascript +db.stores.aggregate([{ + $match: { + _id: "b0107631-9370-4acd-aafa-8ac3511e623d" + } +}, { + $project: { + originalLatitude: "$location.lat", + latitudeAsInt: { + $toInt: { + $toString: "72.0" + } + } + } +}]) +``` + +This query returns the following error message - "Failed to parse number '72.0' in $convert" + +This table delineates the expected behavior of the $toInt operator based on the data type of the input. + +| **Value Type** | **Behavior/Output** | +|--------------------------------------------------------------|---------------------| +| Boolean value true | Output -> 1 | +| Boolean value false | Output -> 0 | +| Double value. E.g., 72.0 | Output -> 72 | +| String representation of an integer value. For example, "72" | Output -> 72 | +| String representation of a double value. For example, "72.0" | Output -> Error | +| Null value | Output -> null | diff --git a/reference/operators/aggregation/$tolong.md b/reference/operators/aggregation/$tolong.md new file mode 100644 index 0000000..204c6af --- /dev/null +++ b/reference/operators/aggregation/$tolong.md @@ -0,0 +1,213 @@ +--- +title: $toLong +description: The $toLong operator converts an expression into a Long value +type: operators +category: aggregation +--- + +# $toLong + +The `$toLong` operator converts a specified value into a Long value. + +## Syntax + +```javascript +{ + $toLong: < expression > +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **`expression`** | The specified value to convert into a long value| + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "0fcc0bf0-ed18-4ab8-b558-9848e18058f4", + "name": "First Up Consultants | Beverage Shop - Satterfieldmouth", + "location": { + "lat": -89.2384, + "lon": -46.4012 + }, + "staff": { + "totalStaff": { + "fullTime": 8, + "partTime": 20 + } + }, + "sales": { + "totalSales": 75670, + "salesByCategory": [ + { + "categoryName": "Wine Accessories", + "totalSales": 34440 + }, + { + "categoryName": "Bitters", + "totalSales": 39496 + }, + { + "categoryName": "Rum", + "totalSales": 1734 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Unbeatable Bargain Bash", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 23 + }, + "endDate": { + "Year": 2024, + "Month": 7, + "Day": 2 + } + }, + "discounts": [ + { + "categoryName": "Whiskey", + "discountPercentage": 7 + }, + { + "categoryName": "Bitters", + "discountPercentage": 15 + }, + { + "categoryName": "Brandy", + "discountPercentage": 8 + }, + { + "categoryName": "Sports Drinks", + "discountPercentage": 22 + }, + { + "categoryName": "Vodka", + "discountPercentage": 19 + } + ] + }, + { + "eventName": "Steal of a Deal Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 29 + } + }, + "discounts": [ + { + "categoryName": "Organic Wine", + "discountPercentage": 19 + }, + { + "categoryName": "White Wine", + "discountPercentage": 20 + }, + { + "categoryName": "Sparkling Wine", + "discountPercentage": 19 + }, + { + "categoryName": "Whiskey", + "discountPercentage": 17 + }, + { + "categoryName": "Vodka", + "discountPercentage": 23 + } + ] + } + ] +} +``` + +### Example 1: Convert a Double value into a Long value + +To convert the value of the latitude field from a Double to a Long value, run a query using the $toLong operator on the field to make the conversion. + +```javascript +db.stores.aggregate([{ + $match: { + _id: "b0107631-9370-4acd-aafa-8ac3511e623d" + } +}, { + $project: { + originalLatitude: "$location.lat", + latitudeAsLong: { + $toLong: "$location.lat" + } + } +}]) +``` + +This query returns the following result: + +```json +[ + { + "_id": "b0107631-9370-4acd-aafa-8ac3511e623d", + "originalLatitude": 72.8377, + "latitudeAsLong": "Long('72')" + } +] +``` + +### Example 2: Convert a String value into a Long value + +To convert the string representation of 72 ("72") into a Long value, run a query using the $toLong operator on the string to make the conversion. + +```javascript +db.stores.aggregate([{ + $match: { + _id: "b0107631-9370-4acd-aafa-8ac3511e623d" + } +}, { + $project: { + originalLatitude: "$location.lat", + latitudeAsLong: { + $toLong: { + $toString: "72" + } + } + } +}]) +``` + +This query returns the following result: + +```json +[ + { + "_id": "b0107631-9370-4acd-aafa-8ac3511e623d", + "originalLatitude": 72.8377, + "latitudeAsLong": Long('72') + } +] +``` + +This table delineates the expected behavior of the $toLong operator based on the data type of the input value. + +| **Value Type** | **Behavior/Output** | +|--------------------------------------------------------------|---------------------| +| Boolean value true | Output -> Long("1") | +| Boolean value false | Output -> Long("1") | +| Double value. E.g., 72.0 | Output -> Long("72")| +| String representation of a long value. For example, "72" | Output -> Long("72")| +| String representation of a double value. For example, "72.0" | Output -> Error | +| Null value | Output -> null | diff --git a/reference/operators/aggregation/$toobjectid.md b/reference/operators/aggregation/$toobjectid.md new file mode 100644 index 0000000..2edb11c --- /dev/null +++ b/reference/operators/aggregation/$toobjectid.md @@ -0,0 +1,175 @@ +--- +title: $toObjectId +description: The $toObjectId operator converts an expression into an ObjectId +type: operators +category: aggregation +--- + +# $toObjectId + +The `$toObject` operator converts a specified value into an ObjectId. + +## Syntax + +```javascript +{ + $toObject: < expression > +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **`expression`** | The specified string value to convert into an ObjectId| + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "0fcc0bf0-ed18-4ab8-b558-9848e18058f4", + "name": "First Up Consultants | Beverage Shop - Satterfieldmouth", + "location": { + "lat": -89.2384, + "lon": -46.4012 + }, + "staff": { + "totalStaff": { + "fullTime": 8, + "partTime": 20 + } + }, + "sales": { + "totalSales": 75670, + "salesByCategory": [ + { + "categoryName": "Wine Accessories", + "totalSales": 34440 + }, + { + "categoryName": "Bitters", + "totalSales": 39496 + }, + { + "categoryName": "Rum", + "totalSales": 1734 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Unbeatable Bargain Bash", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 23 + }, + "endDate": { + "Year": 2024, + "Month": 7, + "Day": 2 + } + }, + "discounts": [ + { + "categoryName": "Whiskey", + "discountPercentage": 7 + }, + { + "categoryName": "Bitters", + "discountPercentage": 15 + }, + { + "categoryName": "Brandy", + "discountPercentage": 8 + }, + { + "categoryName": "Sports Drinks", + "discountPercentage": 22 + }, + { + "categoryName": "Vodka", + "discountPercentage": 19 + } + ] + }, + { + "eventName": "Steal of a Deal Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 29 + } + }, + "discounts": [ + { + "categoryName": "Organic Wine", + "discountPercentage": 19 + }, + { + "categoryName": "White Wine", + "discountPercentage": 20 + }, + { + "categoryName": "Sparkling Wine", + "discountPercentage": 19 + }, + { + "categoryName": "Whiskey", + "discountPercentage": 17 + }, + { + "categoryName": "Vodka", + "discountPercentage": 23 + } + ] + } + ] +} +``` + +### Example 1: Convert the first 24 alphanumeric characters in the _id field into an ObjectId value + +To remove all occurrences of the "-" character and convert the first twenty four characters in the _id field into an ObjectId, run a query using the $toObjectId on a substring of the modified _id field to make the conversion. + +```javascript +db.stores.aggregate([{ + $match: { + _id: "b0107631-9370-4acd-aafa-8ac3511e623d" + } +}, { + $project: { + idAsObjectId: { + $toObjectId: { + $substr: [{ + $replaceAll: { + input: "$_id", + find: "-", + replacement: "" + } + }, 0, 24] + } + } + } +}]) +``` + +This query returns the following result: + +```json +[ + { + "_id": "b0107631-9370-4acd-aafa-8ac3511e623d", + "idAsObjectId": "ObjectId('b010763193704acdaafa8ac3')" + } +] +``` diff --git a/reference/operators/aggregation/$tostring.md b/reference/operators/aggregation/$tostring.md new file mode 100644 index 0000000..a2d6db4 --- /dev/null +++ b/reference/operators/aggregation/$tostring.md @@ -0,0 +1,209 @@ +--- +title: $toString +description: The $toString operator converts an expression into a String +type: operators +category: aggregation +--- + +# $toString + +The `$toString` operator simply returns the value of the specified expression as a String. + +## Syntax + +```javascript +{ + $toString: < expression > +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **`expression`** | The specified value to convert into a String value| + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "0fcc0bf0-ed18-4ab8-b558-9848e18058f4", + "name": "First Up Consultants | Beverage Shop - Satterfieldmouth", + "location": { + "lat": -89.2384, + "lon": -46.4012 + }, + "staff": { + "totalStaff": { + "fullTime": 8, + "partTime": 20 + } + }, + "sales": { + "totalSales": 75670, + "salesByCategory": [ + { + "categoryName": "Wine Accessories", + "totalSales": 34440 + }, + { + "categoryName": "Bitters", + "totalSales": 39496 + }, + { + "categoryName": "Rum", + "totalSales": 1734 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Unbeatable Bargain Bash", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 23 + }, + "endDate": { + "Year": 2024, + "Month": 7, + "Day": 2 + } + }, + "discounts": [ + { + "categoryName": "Whiskey", + "discountPercentage": 7 + }, + { + "categoryName": "Bitters", + "discountPercentage": 15 + }, + { + "categoryName": "Brandy", + "discountPercentage": 8 + }, + { + "categoryName": "Sports Drinks", + "discountPercentage": 22 + }, + { + "categoryName": "Vodka", + "discountPercentage": 19 + } + ] + }, + { + "eventName": "Steal of a Deal Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 29 + } + }, + "discounts": [ + { + "categoryName": "Organic Wine", + "discountPercentage": 19 + }, + { + "categoryName": "White Wine", + "discountPercentage": 20 + }, + { + "categoryName": "Sparkling Wine", + "discountPercentage": 19 + }, + { + "categoryName": "Whiskey", + "discountPercentage": 17 + }, + { + "categoryName": "Vodka", + "discountPercentage": 23 + } + ] + } + ] +} +``` + +### Example 1: Convert a Double value into a String value + +To convert the value of the latitude field from a Double to a String, run a query using the $toString operator on the field to make the conversion. + +```javascript +db.stores.aggregate([{ + $match: { + _id: "b0107631-9370-4acd-aafa-8ac3511e623d" + } +}, { + $project: { + originalLatitude: "$location.lat", + latitudeAsString: { + $toString: "$location.lat" + } + } +}]) +``` + +This query returns the following result: + +```json +[ + { + "_id": "b0107631-9370-4acd-aafa-8ac3511e623d", + "originalLatitude": 72.8377, + "latitudeAsString": "72.8377" + } +] +``` + +### Example 2: Convert an Int value into a String value + +To convert the value of the totalSales field from an Int to a String, run a query using the $toString operator on the field to make the conversion. + +```javascript +db.stores.aggregate([{ + $match: { + _id: "b0107631-9370-4acd-aafa-8ac3511e623d" + } +}, { + $project: { + originalTotalSales: "$sales.totalSales", + totalSalesAsString: { + $toString: "$sales.totalSales" + } + } +}]) +``` + +This query returns the following result: + +```json +[ + { + "_id": "b0107631-9370-4acd-aafa-8ac3511e623d", + "originalTotalSales": 9366, + "totalSalesAsString": "9366" + } +] +``` + +This table delineates the expected behavior of the $toString operator based on the data type of the input value. + +| **Value Type** | **Behavior/Output** | +|------------------------------------------------------------------------|--------------------------------------| +| Boolean value true | Output -> "true" | +| Boolean value false | Output -> "false" | +| Any Double, Int, Long or Decimal value. For example, 72 | Output -> "72" | +| Any ObjectId value. For example, ObjectId("b010763193704acdaafa8ac3") | Output -> "b010763193704acdaafa8ac3" | diff --git a/reference/operators/aggregation/$unset.md b/reference/operators/aggregation/$unset.md new file mode 100644 index 0000000..ccc1b87 --- /dev/null +++ b/reference/operators/aggregation/$unset.md @@ -0,0 +1,244 @@ +--- +title: $unset +description: The $unset stage in the aggregation pipeline is used to remove specified fields from documents. +type: operators +category: aggregation +--- + +# $unset + +The $unset stage the aggregation pipeline is used to remove specified fields from documents. This can be particularly useful when you need to exclude certain fields from the results of an aggregation query for reasons such as privacy, reducing payload size, or simply cleaning up the output. + +## Syntax + +```javascript +{ + $unset: "" | ["", "", ...] +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **`field1, field2, ...`** | The names of the fields to remove from the documents. | + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "0fcc0bf0-ed18-4ab8-b558-9848e18058f4", + "name": "First Up Consultants | Beverage Shop - Satterfieldmouth", + "location": { + "lat": -89.2384, + "lon": -46.4012 + }, + "staff": { + "totalStaff": { + "fullTime": 8, + "partTime": 20 + } + }, + "sales": { + "totalSales": 75670, + "salesByCategory": [ + { + "categoryName": "Wine Accessories", + "totalSales": 34440 + }, + { + "categoryName": "Bitters", + "totalSales": 39496 + }, + { + "categoryName": "Rum", + "totalSales": 1734 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Unbeatable Bargain Bash", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 23 + }, + "endDate": { + "Year": 2024, + "Month": 7, + "Day": 2 + } + }, + "discounts": [ + { + "categoryName": "Whiskey", + "discountPercentage": 7 + }, + { + "categoryName": "Bitters", + "discountPercentage": 15 + }, + { + "categoryName": "Brandy", + "discountPercentage": 8 + }, + { + "categoryName": "Sports Drinks", + "discountPercentage": 22 + }, + { + "categoryName": "Vodka", + "discountPercentage": 19 + } + ] + }, + { + "eventName": "Steal of a Deal Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 29 + } + }, + "discounts": [ + { + "categoryName": "Organic Wine", + "discountPercentage": 19 + }, + { + "categoryName": "White Wine", + "discountPercentage": 20 + }, + { + "categoryName": "Sparkling Wine", + "discountPercentage": 19 + }, + { + "categoryName": "Whiskey", + "discountPercentage": 17 + }, + { + "categoryName": "Vodka", + "discountPercentage": 23 + } + ] + } + ] +} +``` + +### Example 1: Remove a single field + +To remove the location field from the documents. + +```javascript +db.stores.aggregate([ + { + $unset: "store.location" + } +]) +``` + +The first result returned by this query is: + +```json +[ + { + "_id": "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c5", + "store": { + "name": "Downtown Store", + "sales": { + "totalSales": 15000, + "salesByCategory": [ + { + "category": "Electronics", + "totalSales": 5000 + }, + { + "category": "Clothing", + "totalSales": 10000 + } + ] + } + } + } +] +``` + +### Example 2: Remove multiple fields + +To remove the location and sales.totalSales fields from the documents. + +```javascript +db.stores.aggregate([ + { + $unset: ["store.location", "store.sales.totalSales"] + } +]) +``` + +The first result returned by this query is: + +```json +[ + { + "_id": "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c5", + "store": { + "name": "Downtown Store", + "sales": { + "salesByCategory": [ + { + "category": "Electronics", + "totalSales": 5000 + }, + { + "category": "Clothing", + "totalSales": 10000 + } + ] + } + } + } +] +``` + +### Example 3: Remove nested fields + +To remove the staff.totalStaff.fullTime and promotionEvents.discounts fields from the documents. + +```javascript +db.stores.aggregate([ + { + $unset: ["store.staff.totalStaff.fullTime", "store.promotionEvents.discounts"] + } +]) +``` + +The first result returned by this query is: + +```json +[ + { + "_id": "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c5", + "store": { + "name": "Downtown Store", + "staff": { + "totalStaff": { + "partTime": 8 + } + }, + "promotionEvents": ["Summer Sale", "Black Friday", "Holiday Deals"] + } + } +] +``` diff --git a/reference/operators/aggregation/$unwind.md b/reference/operators/aggregation/$unwind.md new file mode 100644 index 0000000..28d6f26 --- /dev/null +++ b/reference/operators/aggregation/$unwind.md @@ -0,0 +1,277 @@ +--- +title: $unwind +description: The $unwind stage in the aggregation framework is used to deconstruct an array field from the input documents to output a document for each element. +type: operators +category: aggregation +--- + +# $unwind + +The $unwind stage in the aggregation framework is used to deconstruct an array field from the input documents to output a document for each element. Each output document is a copy of the original but with the value of the array field replaced by a single element. This is particularly useful for normalizing data stored in arrays and for performing operations on each element of an array separately. + +## Syntax + +```javascript +{ + $unwind: { + path: , + includeArrayIndex: , // Optional + preserveNullAndEmptyArrays: // Optional + } +} +``` + +## Parameters + +| Parameter | Description | +| --- | --- | +| **`path`** | The field path to an array field. This is a required parameter. | +| **`includeArrayIndex`** | Optional. The name of a new field to hold the array index of the unwound element. | +| **`preserveNullAndEmptyArrays`** | Optional. If true, if the path is null, missing, or an empty array, `$unwind` outputs the document unchanged. | + +## Examples + +Consider this sample document from the stores collection. + +```json +{ + "_id": "0fcc0bf0-ed18-4ab8-b558-9848e18058f4", + "name": "First Up Consultants | Beverage Shop - Satterfieldmouth", + "location": { + "lat": -89.2384, + "lon": -46.4012 + }, + "staff": { + "totalStaff": { + "fullTime": 8, + "partTime": 20 + } + }, + "sales": { + "totalSales": 75670, + "salesByCategory": [ + { + "categoryName": "Wine Accessories", + "totalSales": 34440 + }, + { + "categoryName": "Bitters", + "totalSales": 39496 + }, + { + "categoryName": "Rum", + "totalSales": 1734 + } + ] + }, + "promotionEvents": [ + { + "eventName": "Unbeatable Bargain Bash", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 6, + "Day": 23 + }, + "endDate": { + "Year": 2024, + "Month": 7, + "Day": 2 + } + }, + "discounts": [ + { + "categoryName": "Whiskey", + "discountPercentage": 7 + }, + { + "categoryName": "Bitters", + "discountPercentage": 15 + }, + { + "categoryName": "Brandy", + "discountPercentage": 8 + }, + { + "categoryName": "Sports Drinks", + "discountPercentage": 22 + }, + { + "categoryName": "Vodka", + "discountPercentage": 19 + } + ] + }, + { + "eventName": "Steal of a Deal Days", + "promotionalDates": { + "startDate": { + "Year": 2024, + "Month": 9, + "Day": 21 + }, + "endDate": { + "Year": 2024, + "Month": 9, + "Day": 29 + } + }, + "discounts": [ + { + "categoryName": "Organic Wine", + "discountPercentage": 19 + }, + { + "categoryName": "White Wine", + "discountPercentage": 20 + }, + { + "categoryName": "Sparkling Wine", + "discountPercentage": 19 + }, + { + "categoryName": "Whiskey", + "discountPercentage": 17 + }, + { + "categoryName": "Vodka", + "discountPercentage": 23 + } + ] + } + ] +} +``` + +### Example 1: Unwind sales by category + +To deconstruct the salesByCategory array in the store document: + +```javascript +db.stores.aggregate([ + { + $unwind: "$sales.salesByCategory" + } +]) +``` + +The first two results returned by this query are: + +```json +[ + { + "_id": "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c5", + "store": { + "name": "Downtown Store", + "sales": { + "totalSales": 15000, + "salesByCategory": { + "category": "Electronics", + "totalSales": 5000 + } + } + } + }, + { + "_id": "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c5", + "store": { + "name": "Downtown Store", + "sales": { + "totalSales": 15000, + "salesByCategory": { + "category": "Clothing", + "totalSales": 10000 + } + } + } + } +] +``` + +### Example 2: Unwind promotion events with array index + +To deconstruct the promotionEvents array and include the array index in the output: + +```javascript +db.stores.aggregate([ + { + $unwind: { + path: "$promotionEvents", + includeArrayIndex: "eventIndex" + } + } +]) +``` + +The first two results returned by this query are: + +```json +[ + { + "_id": "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c5", + "store": { + "name": "Downtown Store", + "promotionEvents": { + "eventName": "Summer Sale", + "eventDate": ISODate("2024-08-01T00:00:00Z") + }, + "eventIndex": 0 + } + }, + { + "_id": "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c5", + "store": { + "name": "Downtown Store", + "promotionEvents": { + "eventName": "Black Friday", + "eventDate": ISODate("2024-11-25T00:00:00Z") + }, + "eventIndex": 1 + } + } +] +``` + +### Example 3: Unwind discounts within pomotion events + +To deconstruct the discounts array within each promotion event and preserve documents with no discounts: + +```javascript +db.stores.aggregate([ + { + $unwind: { + path: "$promotionEvents.discounts", + preserveNullAndEmptyArrays: true + } + } +]) +``` + +The first two results returned by this query are: + +```json +[ + { + "_id": "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c5", + "store": { + "name": "Downtown Store", + "promotionEvents": { + "eventName": "Summer Sale", + "discounts": { + "discountType": "Percentage", + "discountAmount": 20 + } + } + } + }, + { + "_id": "7954bd5c-9ac2-4c10-bb7a-2b79bd0963c5", + "store": { + "name": "Downtown Store", + "promotionEvents": { + "eventName": "Black Friday" + } + } + } +] +```