From 315d3b59f554e5c9bd6b757dc80c0fef9c230ea5 Mon Sep 17 00:00:00 2001 From: Anton Romanov Date: Wed, 14 Apr 2021 14:41:56 +0300 Subject: [PATCH] :sparkles: Add limit, skip, sort, upsert in MongoDB node (#1439) * mongodb find command improvements: limit, skip, sort * mongodb update command improvement: upsert * :zap: improve mongo node * :art: add missing semicolons Co-authored-by: ahsan-virani --- .../nodes-base/nodes/MongoDb/MongoDb.node.ts | 25 +++++++-- .../nodes/MongoDb/mongo.node.options.ts | 54 ++++++++++++++++++- 2 files changed, 74 insertions(+), 5 deletions(-) diff --git a/packages/nodes-base/nodes/MongoDb/MongoDb.node.ts b/packages/nodes-base/nodes/MongoDb/MongoDb.node.ts index c03a62816f..00dfe9f3a7 100644 --- a/packages/nodes-base/nodes/MongoDb/MongoDb.node.ts +++ b/packages/nodes-base/nodes/MongoDb/MongoDb.node.ts @@ -60,10 +60,24 @@ export class MongoDb implements INodeType { // find // ---------------------------------- - const queryResult = await mdb + let query = mdb .collection(this.getNodeParameter('collection', 0) as string) - .find(JSON.parse(this.getNodeParameter('query', 0) as string)) - .toArray(); + .find(JSON.parse(this.getNodeParameter('query', 0) as string)); + + const options = this.getNodeParameter('options', 0) as IDataObject; + const limit = options.limit as number; + const skip = options.skip as number; + const sort = options.sort && JSON.parse(options.sort as string); + if (skip > 0) { + query = query.skip(skip); + } + if (limit > 0) { + query = query.limit(limit); + } + if (sort && Object.keys(sort).length !== 0 && sort.constructor === Object) { + query = query.sort(sort); + } + const queryResult = await query.toArray(); returnItems = this.helpers.returnJsonArray(queryResult as IDataObject[]); } else if (operation === 'insert') { @@ -112,6 +126,9 @@ export class MongoDb implements INodeType { let updateKey = this.getNodeParameter('updateKey', 0) as string; updateKey = updateKey.trim(); + const updateOptions = (this.getNodeParameter('upsert', 0) as boolean) + ? { upsert: true } : undefined; + if (!fields.includes(updateKey)) { fields.push(updateKey); } @@ -136,7 +153,7 @@ export class MongoDb implements INodeType { } await mdb .collection(this.getNodeParameter('collection', 0) as string) - .updateOne(filter, { $set: item }); + .updateOne(filter, { $set: item }, updateOptions); } returnItems = this.helpers.returnJsonArray(updateItems as IDataObject[]); } else { diff --git a/packages/nodes-base/nodes/MongoDb/mongo.node.options.ts b/packages/nodes-base/nodes/MongoDb/mongo.node.options.ts index 5fa8972c51..591e5b3afc 100644 --- a/packages/nodes-base/nodes/MongoDb/mongo.node.options.ts +++ b/packages/nodes-base/nodes/MongoDb/mongo.node.options.ts @@ -90,6 +90,47 @@ export const nodeDescription: INodeTypeDescription = { // ---------------------------------- // find // ---------------------------------- + { + displayName: 'Options', + name: 'options', + type: 'collection', + displayOptions: { + show: { + operation: ['find'], + }, + }, + default: {}, + placeholder: 'Add options', + description: 'Add query options', + options: [ + { + displayName: 'Limit', + name: 'limit', + type: "number", + default: 0, + description: 'Use limit to specify the maximum number of documents or 0 for unlimited documents.', + }, + { + displayName: 'Skip', + name: 'skip', + type: "number", + default: 0, + description: 'The number of documents to skip in the results set.', + }, + { + displayName: 'Sort (JSON format)', + name: 'sort', + type: 'json', + typeOptions: { + rows: 2, + }, + default: '{}', + placeholder: '{ "field": -1 }', + required: true, + description: 'A json that defines the sort order of the result set.', + }, + ], + }, { displayName: 'Query (JSON format)', name: 'query', @@ -109,7 +150,6 @@ export const nodeDescription: INodeTypeDescription = { required: true, description: 'MongoDB Find query.', }, - // ---------------------------------- // insert // ---------------------------------- @@ -165,6 +205,18 @@ export const nodeDescription: INodeTypeDescription = { description: 'Comma separated list of the fields to be included into the new document.', }, + { + displayName: 'Upsert', + name: 'upsert', + type: 'boolean', + displayOptions: { + show: { + operation: ['update'], + }, + }, + default: false, + description: `Perform an insert if no documents match the update key`, + }, { displayName: 'Options', name: 'options',