mirror of
https://github.com/n8n-io/n8n.git
synced 2025-02-21 02:56:40 -08:00
feat(Item List Node): Add operation for creating array from input items (#3149)
* 🔨 create array operation * 🔨 removed semicolumn * 🔨 updated UI * ⚡ display option fix * ⚡ aggregate operation description update, default aggregate item
This commit is contained in:
parent
2fb590e844
commit
553b14a13c
|
@ -13,6 +13,7 @@ import {
|
||||||
|
|
||||||
import {
|
import {
|
||||||
get,
|
get,
|
||||||
|
isEmpty,
|
||||||
isEqual,
|
isEqual,
|
||||||
isObject,
|
isObject,
|
||||||
lt,
|
lt,
|
||||||
|
@ -64,8 +65,8 @@ export class ItemLists implements INodeType {
|
||||||
{
|
{
|
||||||
name: 'Aggregate Items',
|
name: 'Aggregate Items',
|
||||||
value: 'aggregateItems',
|
value: 'aggregateItems',
|
||||||
description: 'Merge fields into a single new item',
|
description: 'Combine fields into a single new item',
|
||||||
action: 'Merge fields into a single new item',
|
action: 'Combine fields into a single new item',
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: 'Limit',
|
name: 'Limit',
|
||||||
|
@ -183,6 +184,34 @@ export class ItemLists implements INodeType {
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
},
|
},
|
||||||
|
// Aggregate Items
|
||||||
|
{
|
||||||
|
displayName: 'Aggregate',
|
||||||
|
name: 'aggregate',
|
||||||
|
type: 'options',
|
||||||
|
default: 'aggregateIndividualFields',
|
||||||
|
options: [
|
||||||
|
{
|
||||||
|
name: 'Individual Fields',
|
||||||
|
value: 'aggregateIndividualFields',
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: 'All Item Data (Into a Single List)',
|
||||||
|
value: 'aggregateAllItemData',
|
||||||
|
},
|
||||||
|
],
|
||||||
|
displayOptions: {
|
||||||
|
show: {
|
||||||
|
resource: [
|
||||||
|
'itemList',
|
||||||
|
],
|
||||||
|
operation: [
|
||||||
|
'aggregateItems',
|
||||||
|
],
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
// Aggregate Individual Fields
|
||||||
{
|
{
|
||||||
displayName: 'Fields To Aggregate',
|
displayName: 'Fields To Aggregate',
|
||||||
name: 'fieldsToAggregate',
|
name: 'fieldsToAggregate',
|
||||||
|
@ -191,7 +220,7 @@ export class ItemLists implements INodeType {
|
||||||
multipleValues: true,
|
multipleValues: true,
|
||||||
},
|
},
|
||||||
placeholder: 'Add Field To Aggregate',
|
placeholder: 'Add Field To Aggregate',
|
||||||
default: {},
|
default: {fieldToAggregate: [{fieldToAggregate: '', renameField: false}]},
|
||||||
displayOptions: {
|
displayOptions: {
|
||||||
show: {
|
show: {
|
||||||
resource: [
|
resource: [
|
||||||
|
@ -200,6 +229,9 @@ export class ItemLists implements INodeType {
|
||||||
operation: [
|
operation: [
|
||||||
'aggregateItems',
|
'aggregateItems',
|
||||||
],
|
],
|
||||||
|
aggregate: [
|
||||||
|
'aggregateIndividualFields',
|
||||||
|
],
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
options: [
|
options: [
|
||||||
|
@ -239,7 +271,142 @@ export class ItemLists implements INodeType {
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
},
|
},
|
||||||
|
// Aggregate All Item Data
|
||||||
|
{
|
||||||
|
displayName: 'Put Output in Field',
|
||||||
|
name: 'destinationFieldName',
|
||||||
|
type: 'string',
|
||||||
|
displayOptions: {
|
||||||
|
show: {
|
||||||
|
resource: [
|
||||||
|
'itemList',
|
||||||
|
],
|
||||||
|
'operation': [
|
||||||
|
'aggregateItems',
|
||||||
|
],
|
||||||
|
aggregate: [
|
||||||
|
'aggregateAllItemData',
|
||||||
|
],
|
||||||
|
},
|
||||||
|
},
|
||||||
|
default: 'data',
|
||||||
|
description: 'The name of the output field to put the data in',
|
||||||
|
},
|
||||||
|
{
|
||||||
|
displayName: 'Include',
|
||||||
|
name: 'include',
|
||||||
|
type: 'options',
|
||||||
|
default: 'allFields',
|
||||||
|
options: [
|
||||||
|
{
|
||||||
|
name: 'All Fields',
|
||||||
|
value: 'allFields',
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: 'Specified Fields',
|
||||||
|
value: 'specifiedFields',
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: 'All Fields Except',
|
||||||
|
value: 'allFieldsExcept',
|
||||||
|
},
|
||||||
|
],
|
||||||
|
displayOptions: {
|
||||||
|
show: {
|
||||||
|
resource: [
|
||||||
|
'itemList',
|
||||||
|
],
|
||||||
|
operation: [
|
||||||
|
'aggregateItems',
|
||||||
|
],
|
||||||
|
aggregate: [
|
||||||
|
'aggregateAllItemData',
|
||||||
|
],
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
displayName: 'Fields To Exclude',
|
||||||
|
name: 'fieldsToExclude',
|
||||||
|
type: 'fixedCollection',
|
||||||
|
typeOptions: {
|
||||||
|
multipleValues: true,
|
||||||
|
},
|
||||||
|
placeholder: 'Add Field To Exclude',
|
||||||
|
default: {},
|
||||||
|
options: [
|
||||||
|
{
|
||||||
|
displayName: '',
|
||||||
|
name: 'fields',
|
||||||
|
values: [
|
||||||
|
{
|
||||||
|
displayName: 'Field Name',
|
||||||
|
name: 'fieldName',
|
||||||
|
type: 'string',
|
||||||
|
default: '',
|
||||||
|
description: 'A field in the input to exclude from the object in output array',
|
||||||
|
},
|
||||||
|
],
|
||||||
|
},
|
||||||
|
],
|
||||||
|
displayOptions: {
|
||||||
|
show: {
|
||||||
|
resource: [
|
||||||
|
'itemList',
|
||||||
|
],
|
||||||
|
operation: [
|
||||||
|
'aggregateItems',
|
||||||
|
],
|
||||||
|
aggregate: [
|
||||||
|
'aggregateAllItemData',
|
||||||
|
],
|
||||||
|
include: [
|
||||||
|
'allFieldsExcept',
|
||||||
|
],
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
displayName: 'Fields To Include',
|
||||||
|
name: 'fieldsToInclude',
|
||||||
|
type: 'fixedCollection',
|
||||||
|
typeOptions: {
|
||||||
|
multipleValues: true,
|
||||||
|
},
|
||||||
|
placeholder: 'Add Field To Include',
|
||||||
|
default: {},
|
||||||
|
options: [
|
||||||
|
{
|
||||||
|
displayName: '',
|
||||||
|
name: 'fields',
|
||||||
|
values: [
|
||||||
|
{
|
||||||
|
displayName: 'Field Name',
|
||||||
|
name: 'fieldName',
|
||||||
|
type: 'string',
|
||||||
|
default: '',
|
||||||
|
description: 'Specify fields that will be included in output array',
|
||||||
|
},
|
||||||
|
],
|
||||||
|
},
|
||||||
|
],
|
||||||
|
displayOptions: {
|
||||||
|
show: {
|
||||||
|
resource: [
|
||||||
|
'itemList',
|
||||||
|
],
|
||||||
|
operation: [
|
||||||
|
'aggregateItems',
|
||||||
|
],
|
||||||
|
aggregate: [
|
||||||
|
'aggregateAllItemData',
|
||||||
|
],
|
||||||
|
include: [
|
||||||
|
'specifiedFields',
|
||||||
|
],
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
// Remove duplicates - Fields
|
// Remove duplicates - Fields
|
||||||
{
|
{
|
||||||
displayName: 'Compare',
|
displayName: 'Compare',
|
||||||
|
@ -606,6 +773,11 @@ return 0;`,
|
||||||
'aggregateItems',
|
'aggregateItems',
|
||||||
],
|
],
|
||||||
},
|
},
|
||||||
|
hide: {
|
||||||
|
'aggregate': [
|
||||||
|
'aggregateAllItemData',
|
||||||
|
],
|
||||||
|
},
|
||||||
},
|
},
|
||||||
options: [
|
options: [
|
||||||
{
|
{
|
||||||
|
@ -770,7 +942,9 @@ return 0;`,
|
||||||
return this.prepareOutputData(returnData);
|
return this.prepareOutputData(returnData);
|
||||||
|
|
||||||
} else if (operation === 'aggregateItems') {
|
} else if (operation === 'aggregateItems') {
|
||||||
|
const aggregate = this.getNodeParameter('aggregate', 0, '') as string;
|
||||||
|
|
||||||
|
if ( aggregate === 'aggregateIndividualFields') {
|
||||||
const disableDotNotation = this.getNodeParameter('options.disableDotNotation', 0, false) as boolean;
|
const disableDotNotation = this.getNodeParameter('options.disableDotNotation', 0, false) as boolean;
|
||||||
const mergeLists = this.getNodeParameter('options.mergeLists', 0, false) as boolean;
|
const mergeLists = this.getNodeParameter('options.mergeLists', 0, false) as boolean;
|
||||||
const fieldsToAggregate = this.getNodeParameter('fieldsToAggregate.fieldToAggregate', 0, []) as [{ fieldToAggregate: string, renameField: boolean, outputFieldName: string }];
|
const fieldsToAggregate = this.getNodeParameter('fieldsToAggregate.fieldToAggregate', 0, []) as [{ fieldToAggregate: string, renameField: boolean, outputFieldName: string }];
|
||||||
|
@ -882,6 +1056,41 @@ return 0;`,
|
||||||
|
|
||||||
return this.prepareOutputData(returnData);
|
return this.prepareOutputData(returnData);
|
||||||
|
|
||||||
|
} else {
|
||||||
|
let newItems: IDataObject[] = items.map(item => item.json);
|
||||||
|
const destinationFieldName = this.getNodeParameter('destinationFieldName', 0) as string;
|
||||||
|
const fieldsToExclude = (this.getNodeParameter('fieldsToExclude.fields', 0, []) as IDataObject[]).map(entry => entry.fieldName);
|
||||||
|
const fieldsToInclude = (this.getNodeParameter('fieldsToInclude.fields', 0, []) as IDataObject[]).map(entry => entry.fieldName);
|
||||||
|
|
||||||
|
|
||||||
|
if (fieldsToExclude.length || fieldsToInclude.length) {
|
||||||
|
newItems = newItems.reduce((acc, item) => {
|
||||||
|
const newItem:IDataObject = {};
|
||||||
|
let outputFields = Object.keys(item);
|
||||||
|
|
||||||
|
if (fieldsToExclude.length) {
|
||||||
|
outputFields = outputFields.filter(key => !fieldsToExclude.includes(key));
|
||||||
|
}
|
||||||
|
if (fieldsToInclude.length) {
|
||||||
|
outputFields = outputFields.filter(key => fieldsToInclude.length ? fieldsToInclude.includes(key) : true);
|
||||||
|
}
|
||||||
|
|
||||||
|
outputFields.forEach( key => {
|
||||||
|
newItem[key] = item[key];
|
||||||
|
});
|
||||||
|
|
||||||
|
if (isEmpty(newItem)) {
|
||||||
|
return acc;
|
||||||
|
}
|
||||||
|
return acc.concat([newItem]);
|
||||||
|
}, [] as IDataObject[]);
|
||||||
|
}
|
||||||
|
|
||||||
|
const output: INodeExecutionData = { json: {[destinationFieldName]: newItems} };
|
||||||
|
|
||||||
|
return this.prepareOutputData([output]);
|
||||||
|
}
|
||||||
|
|
||||||
} else if (operation === 'removeDuplicates') {
|
} else if (operation === 'removeDuplicates') {
|
||||||
|
|
||||||
const compare = this.getNodeParameter('compare', 0) as string;
|
const compare = this.getNodeParameter('compare', 0) as string;
|
||||||
|
|
Loading…
Reference in a new issue