@contember/engine-actions 2.0.0-alpha.14 → 2.0.0-alpha.15
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/development/src/triggers/TriggerPayloadBuilder.cjs +1 -1
- package/dist/development/src/triggers/TriggerPayloadBuilder.cjs.map +1 -1
- package/dist/development/src/triggers/TriggerPayloadBuilder.js +1 -1
- package/dist/development/src/triggers/TriggerPayloadBuilder.js.map +1 -1
- package/dist/production/src/triggers/TriggerPayloadBuilder.cjs +1 -1
- package/dist/production/src/triggers/TriggerPayloadBuilder.cjs.map +1 -1
- package/dist/production/src/triggers/TriggerPayloadBuilder.js +1 -1
- package/dist/production/src/triggers/TriggerPayloadBuilder.js.map +1 -1
- package/dist/types/tsconfig.tsbuildinfo +1 -1
- package/package.json +15 -15
- package/src/triggers/TriggerPayloadBuilder.ts +1 -1
|
@@ -48,7 +48,7 @@ class TriggerPayloadBuilder {
|
|
|
48
48
|
trigger: events[0].listener.trigger.name,
|
|
49
49
|
entity: events[0].entity.name,
|
|
50
50
|
id: eventsByPrimary.primary,
|
|
51
|
-
selection: events[0].selection ?? selections[eventsByPrimary.primary],
|
|
51
|
+
selection: eventsByPrimary.events[0].selection ?? selections[eventsByPrimary.primary],
|
|
52
52
|
events: eventsByPrimary.events.map((it) => this.buildBaseEventPayloads(it))
|
|
53
53
|
});
|
|
54
54
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"TriggerPayloadBuilder.cjs","sources":["../../../../../packages/engine-actions/src/triggers/TriggerPayloadBuilder.ts"],"sourcesContent":["import { ImplementationException } from '../ImplementationException'\nimport { assertNever } from '../utils/assertNever'\nimport { FiredEvent } from './TriggerPayloadManager'\nimport { Actions, ActionsPayload, Input } from '@contember/schema'\nimport { FieldNode, Mapper, ObjectNode } from '@contember/engine-content-api'\n\ntype Selections = Record<Input.PrimaryValue, any>\n\nexport class TriggerPayloadBuilder {\n\tconstructor(\n\t\tprivate readonly mapper: Mapper,\n\t) {\n\t}\n\n\tpublic async build(events: FiredEvent[]): Promise<ActionsPayload.AnyEventPayload[]> {\n\t\tconst filteredEvents = events.filter(it => {\n\t\t\treturn it.cause.type !== 'BeforeUpdateEvent'\n\t\t\t\t|| it.cause.afterEvent?.hasChanges === true\n\t\t})\n\t\tif (filteredEvents.length === 0) {\n\t\t\treturn []\n\t\t}\n\t\tconst selections = await this.fetchSelection(filteredEvents)\n\t\tconst triggerType = filteredEvents[0].listener.trigger.type\n\t\tif (triggerType === 'basic') {\n\t\t\treturn filteredEvents.map(it => ({ trigger: it.listener.trigger.name, ...this.buildBaseEventPayloads(it, selections[it.primary]) }))\n\t\t}\n\t\tif (triggerType === 'watch') {\n\t\t\treturn this.buildWatchEventPayloads(filteredEvents, selections)\n\t\t}\n\t\treturn assertNever(triggerType)\n\t}\n\n\tpublic async preprocessEvent(event: FiredEvent): Promise<FiredEvent> {\n\t\tif (event.listener.type === 'delete' && event.listener.trigger.selection) {\n\t\t\tconst input = this.convertSelectionNode(event.listener.trigger.selection)\n\n\t\t\tconst selection = await this.mapper.selectUnique(event.entity, input.withArg('by', {\n\t\t\t\t[event.entity.primary]: event.primary,\n\t\t\t}), [])\n\t\t\treturn { ...event, selection }\n\t\t}\n\t\treturn event\n\t}\n\n\tprivate buildWatchEventPayloads(events: FiredEvent[], selections: Selections): ActionsPayload.WatchEventPayload[] {\n\t\tconst byPrimary: Record<Input.PrimaryValue, { primary: Input.PrimaryValue; events: FiredEvent[] }> = {}\n\t\tfor (const event of events) {\n\t\t\tbyPrimary[event.primary] ??= { primary: event.primary, events: [] }\n\t\t\tbyPrimary[event.primary].events.push(event)\n\t\t}\n\t\tconst payloads: ActionsPayload.WatchEventPayload[] = []\n\t\tfor (const eventsByPrimary of Object.values(byPrimary)) {\n\t\t\tpayloads.push({\n\t\t\t\toperation: 'watch',\n\t\t\t\ttrigger: events[0].listener.trigger.name,\n\t\t\t\tentity: events[0].entity.name,\n\t\t\t\tid: eventsByPrimary.primary,\n\t\t\t\tselection: events[0].selection ?? selections[eventsByPrimary.primary],\n\t\t\t\tevents: eventsByPrimary.events.map(it => this.buildBaseEventPayloads(it)),\n\t\t\t})\n\t\t}\n\t\treturn payloads\n\t}\n\n\tprivate buildBaseEventPayloads(event: FiredEvent, selection?: any): ActionsPayload.BaseEventPayload {\n\t\tswitch (event.cause.type) {\n\t\t\tcase 'AfterInsertEvent':\n\t\t\t\treturn {\n\t\t\t\t\toperation: 'create',\n\t\t\t\t\tentity: event.cause.entity.name,\n\t\t\t\t\tid: event.cause.id,\n\t\t\t\t\tselection,\n\t\t\t\t\tvalues: Object.fromEntries(event.cause.data.map(it => [it.fieldName, it.resolvedValue])),\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t}\n\t\t\tcase 'AfterUpdateEvent':\n\t\t\tcase 'BeforeUpdateEvent':\n\t\t\t\tconst afterEvent = event.cause.type === 'AfterUpdateEvent' ? event.cause : event.cause.afterEvent\n\t\t\t\tif (!afterEvent) {\n\t\t\t\t\tthrow new ImplementationException()\n\t\t\t\t}\n\t\t\t\treturn {\n\t\t\t\t\toperation: 'update',\n\t\t\t\t\tentity: event.cause.entity.name,\n\t\t\t\t\tid: event.cause.id,\n\t\t\t\t\tselection,\n\t\t\t\t\tvalues: Object.fromEntries(event.cause.data.map(it => [it.fieldName, it.resolvedValue])),\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t\told: Object.fromEntries(afterEvent.data.map(it => [it.fieldName, it.old])),\n\t\t\t\t}\n\t\t\tcase 'BeforeDeleteEvent':\n\t\t\t\treturn {\n\t\t\t\t\toperation: 'delete',\n\t\t\t\t\tentity: event.cause.entity.name,\n\t\t\t\t\tid: event.cause.id,\n\t\t\t\t\tselection,\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t}\n\t\t\tcase 'AfterJunctionUpdateEvent':\n\t\t\t\tif (event.listener.type !== 'junction') {\n\t\t\t\t\tthrow new ImplementationException()\n\t\t\t\t}\n\t\t\t\tconst [id, inverseId] = event.listener.context.type === 'owning'\n\t\t\t\t\t? [event.cause.owningId, event.cause.inverseId]\n\t\t\t\t\t: [event.cause.inverseId, event.cause.owningId]\n\t\t\t\treturn {\n\t\t\t\t\toperation: event.cause.operation === 'connect' ? 'junction_connect' : 'junction_disconnect',\n\t\t\t\t\tentity: event.listener.context.entity.name,\n\t\t\t\t\trelation: event.listener.context.relation.name,\n\t\t\t\t\tid,\n\t\t\t\t\tinverseId,\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t}\n\t\t\tdefault:\n\t\t\t\tassertNever(event.cause, it => it.type)\n\t\t}\n\t}\n\n\tprivate async fetchSelection(events: FiredEvent[]): Promise<Selections> {\n\t\tconst trigger = events[0].listener.trigger\n\t\tif (!trigger.selection) {\n\t\t\treturn {}\n\t\t}\n\n\t\tconst ids = Array.from(new Set(events.filter(it => it.listener.type !== 'delete').map(it => it.primary)))\n\t\tif (ids.length === 0) {\n\t\t\treturn {}\n\t\t}\n\t\tconst entity = events[0].entity\n\t\tconst input = this.convertSelectionNode(trigger.selection).withArg('filter', {\n\t\t\t[entity.primary]: { in: ids },\n\t\t})\n\t\treturn await this.mapper.selectAssoc(entity, input, [], entity.primary)\n\t}\n\n\n\tprivate convertSelectionNode(node: Actions.SelectionNode, nodeName = 'root', path: string[] = []): ObjectNode<Input.ListQueryInput> {\n\t\treturn new ObjectNode(nodeName, nodeName, node.map(it => {\n\t\t\tconst [field, args, selection] = Array.isArray(it) ? it : [it, undefined, undefined]\n\t\t\tif (selection === undefined || selection.length === 0) {\n\t\t\t\treturn new FieldNode(field, field, {})\n\t\t\t}\n\t\t\treturn this.convertSelectionNode(selection, field, [...path, nodeName]).withArgs(args)\n\t\t}), {}, {}, path)\n\t}\n}\n"],"names":["assertNever","ImplementationException","ObjectNode","FieldNode"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"TriggerPayloadBuilder.cjs","sources":["../../../../../packages/engine-actions/src/triggers/TriggerPayloadBuilder.ts"],"sourcesContent":["import { ImplementationException } from '../ImplementationException'\nimport { assertNever } from '../utils/assertNever'\nimport { FiredEvent } from './TriggerPayloadManager'\nimport { Actions, ActionsPayload, Input } from '@contember/schema'\nimport { FieldNode, Mapper, ObjectNode } from '@contember/engine-content-api'\n\ntype Selections = Record<Input.PrimaryValue, any>\n\nexport class TriggerPayloadBuilder {\n\tconstructor(\n\t\tprivate readonly mapper: Mapper,\n\t) {\n\t}\n\n\tpublic async build(events: FiredEvent[]): Promise<ActionsPayload.AnyEventPayload[]> {\n\t\tconst filteredEvents = events.filter(it => {\n\t\t\treturn it.cause.type !== 'BeforeUpdateEvent'\n\t\t\t\t|| it.cause.afterEvent?.hasChanges === true\n\t\t})\n\t\tif (filteredEvents.length === 0) {\n\t\t\treturn []\n\t\t}\n\t\tconst selections = await this.fetchSelection(filteredEvents)\n\t\tconst triggerType = filteredEvents[0].listener.trigger.type\n\t\tif (triggerType === 'basic') {\n\t\t\treturn filteredEvents.map(it => ({ trigger: it.listener.trigger.name, ...this.buildBaseEventPayloads(it, selections[it.primary]) }))\n\t\t}\n\t\tif (triggerType === 'watch') {\n\t\t\treturn this.buildWatchEventPayloads(filteredEvents, selections)\n\t\t}\n\t\treturn assertNever(triggerType)\n\t}\n\n\tpublic async preprocessEvent(event: FiredEvent): Promise<FiredEvent> {\n\t\tif (event.listener.type === 'delete' && event.listener.trigger.selection) {\n\t\t\tconst input = this.convertSelectionNode(event.listener.trigger.selection)\n\n\t\t\tconst selection = await this.mapper.selectUnique(event.entity, input.withArg('by', {\n\t\t\t\t[event.entity.primary]: event.primary,\n\t\t\t}), [])\n\t\t\treturn { ...event, selection }\n\t\t}\n\t\treturn event\n\t}\n\n\tprivate buildWatchEventPayloads(events: FiredEvent[], selections: Selections): ActionsPayload.WatchEventPayload[] {\n\t\tconst byPrimary: Record<Input.PrimaryValue, { primary: Input.PrimaryValue; events: FiredEvent[] }> = {}\n\t\tfor (const event of events) {\n\t\t\tbyPrimary[event.primary] ??= { primary: event.primary, events: [] }\n\t\t\tbyPrimary[event.primary].events.push(event)\n\t\t}\n\t\tconst payloads: ActionsPayload.WatchEventPayload[] = []\n\t\tfor (const eventsByPrimary of Object.values(byPrimary)) {\n\t\t\tpayloads.push({\n\t\t\t\toperation: 'watch',\n\t\t\t\ttrigger: events[0].listener.trigger.name,\n\t\t\t\tentity: events[0].entity.name,\n\t\t\t\tid: eventsByPrimary.primary,\n\t\t\t\tselection: eventsByPrimary.events[0].selection ?? selections[eventsByPrimary.primary],\n\t\t\t\tevents: eventsByPrimary.events.map(it => this.buildBaseEventPayloads(it)),\n\t\t\t})\n\t\t}\n\t\treturn payloads\n\t}\n\n\tprivate buildBaseEventPayloads(event: FiredEvent, selection?: any): ActionsPayload.BaseEventPayload {\n\t\tswitch (event.cause.type) {\n\t\t\tcase 'AfterInsertEvent':\n\t\t\t\treturn {\n\t\t\t\t\toperation: 'create',\n\t\t\t\t\tentity: event.cause.entity.name,\n\t\t\t\t\tid: event.cause.id,\n\t\t\t\t\tselection,\n\t\t\t\t\tvalues: Object.fromEntries(event.cause.data.map(it => [it.fieldName, it.resolvedValue])),\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t}\n\t\t\tcase 'AfterUpdateEvent':\n\t\t\tcase 'BeforeUpdateEvent':\n\t\t\t\tconst afterEvent = event.cause.type === 'AfterUpdateEvent' ? event.cause : event.cause.afterEvent\n\t\t\t\tif (!afterEvent) {\n\t\t\t\t\tthrow new ImplementationException()\n\t\t\t\t}\n\t\t\t\treturn {\n\t\t\t\t\toperation: 'update',\n\t\t\t\t\tentity: event.cause.entity.name,\n\t\t\t\t\tid: event.cause.id,\n\t\t\t\t\tselection,\n\t\t\t\t\tvalues: Object.fromEntries(event.cause.data.map(it => [it.fieldName, it.resolvedValue])),\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t\told: Object.fromEntries(afterEvent.data.map(it => [it.fieldName, it.old])),\n\t\t\t\t}\n\t\t\tcase 'BeforeDeleteEvent':\n\t\t\t\treturn {\n\t\t\t\t\toperation: 'delete',\n\t\t\t\t\tentity: event.cause.entity.name,\n\t\t\t\t\tid: event.cause.id,\n\t\t\t\t\tselection,\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t}\n\t\t\tcase 'AfterJunctionUpdateEvent':\n\t\t\t\tif (event.listener.type !== 'junction') {\n\t\t\t\t\tthrow new ImplementationException()\n\t\t\t\t}\n\t\t\t\tconst [id, inverseId] = event.listener.context.type === 'owning'\n\t\t\t\t\t? [event.cause.owningId, event.cause.inverseId]\n\t\t\t\t\t: [event.cause.inverseId, event.cause.owningId]\n\t\t\t\treturn {\n\t\t\t\t\toperation: event.cause.operation === 'connect' ? 'junction_connect' : 'junction_disconnect',\n\t\t\t\t\tentity: event.listener.context.entity.name,\n\t\t\t\t\trelation: event.listener.context.relation.name,\n\t\t\t\t\tid,\n\t\t\t\t\tinverseId,\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t}\n\t\t\tdefault:\n\t\t\t\tassertNever(event.cause, it => it.type)\n\t\t}\n\t}\n\n\tprivate async fetchSelection(events: FiredEvent[]): Promise<Selections> {\n\t\tconst trigger = events[0].listener.trigger\n\t\tif (!trigger.selection) {\n\t\t\treturn {}\n\t\t}\n\n\t\tconst ids = Array.from(new Set(events.filter(it => it.listener.type !== 'delete').map(it => it.primary)))\n\t\tif (ids.length === 0) {\n\t\t\treturn {}\n\t\t}\n\t\tconst entity = events[0].entity\n\t\tconst input = this.convertSelectionNode(trigger.selection).withArg('filter', {\n\t\t\t[entity.primary]: { in: ids },\n\t\t})\n\t\treturn await this.mapper.selectAssoc(entity, input, [], entity.primary)\n\t}\n\n\n\tprivate convertSelectionNode(node: Actions.SelectionNode, nodeName = 'root', path: string[] = []): ObjectNode<Input.ListQueryInput> {\n\t\treturn new ObjectNode(nodeName, nodeName, node.map(it => {\n\t\t\tconst [field, args, selection] = Array.isArray(it) ? it : [it, undefined, undefined]\n\t\t\tif (selection === undefined || selection.length === 0) {\n\t\t\t\treturn new FieldNode(field, field, {})\n\t\t\t}\n\t\t\treturn this.convertSelectionNode(selection, field, [...path, nodeName]).withArgs(args)\n\t\t}), {}, {}, path)\n\t}\n}\n"],"names":["assertNever","ImplementationException","ObjectNode","FieldNode"],"mappings":"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"}
|
|
@@ -46,7 +46,7 @@ class TriggerPayloadBuilder {
|
|
|
46
46
|
trigger: events[0].listener.trigger.name,
|
|
47
47
|
entity: events[0].entity.name,
|
|
48
48
|
id: eventsByPrimary.primary,
|
|
49
|
-
selection: events[0].selection ?? selections[eventsByPrimary.primary],
|
|
49
|
+
selection: eventsByPrimary.events[0].selection ?? selections[eventsByPrimary.primary],
|
|
50
50
|
events: eventsByPrimary.events.map((it) => this.buildBaseEventPayloads(it))
|
|
51
51
|
});
|
|
52
52
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"TriggerPayloadBuilder.js","sources":["../../../../../packages/engine-actions/src/triggers/TriggerPayloadBuilder.ts"],"sourcesContent":["import { ImplementationException } from '../ImplementationException'\nimport { assertNever } from '../utils/assertNever'\nimport { FiredEvent } from './TriggerPayloadManager'\nimport { Actions, ActionsPayload, Input } from '@contember/schema'\nimport { FieldNode, Mapper, ObjectNode } from '@contember/engine-content-api'\n\ntype Selections = Record<Input.PrimaryValue, any>\n\nexport class TriggerPayloadBuilder {\n\tconstructor(\n\t\tprivate readonly mapper: Mapper,\n\t) {\n\t}\n\n\tpublic async build(events: FiredEvent[]): Promise<ActionsPayload.AnyEventPayload[]> {\n\t\tconst filteredEvents = events.filter(it => {\n\t\t\treturn it.cause.type !== 'BeforeUpdateEvent'\n\t\t\t\t|| it.cause.afterEvent?.hasChanges === true\n\t\t})\n\t\tif (filteredEvents.length === 0) {\n\t\t\treturn []\n\t\t}\n\t\tconst selections = await this.fetchSelection(filteredEvents)\n\t\tconst triggerType = filteredEvents[0].listener.trigger.type\n\t\tif (triggerType === 'basic') {\n\t\t\treturn filteredEvents.map(it => ({ trigger: it.listener.trigger.name, ...this.buildBaseEventPayloads(it, selections[it.primary]) }))\n\t\t}\n\t\tif (triggerType === 'watch') {\n\t\t\treturn this.buildWatchEventPayloads(filteredEvents, selections)\n\t\t}\n\t\treturn assertNever(triggerType)\n\t}\n\n\tpublic async preprocessEvent(event: FiredEvent): Promise<FiredEvent> {\n\t\tif (event.listener.type === 'delete' && event.listener.trigger.selection) {\n\t\t\tconst input = this.convertSelectionNode(event.listener.trigger.selection)\n\n\t\t\tconst selection = await this.mapper.selectUnique(event.entity, input.withArg('by', {\n\t\t\t\t[event.entity.primary]: event.primary,\n\t\t\t}), [])\n\t\t\treturn { ...event, selection }\n\t\t}\n\t\treturn event\n\t}\n\n\tprivate buildWatchEventPayloads(events: FiredEvent[], selections: Selections): ActionsPayload.WatchEventPayload[] {\n\t\tconst byPrimary: Record<Input.PrimaryValue, { primary: Input.PrimaryValue; events: FiredEvent[] }> = {}\n\t\tfor (const event of events) {\n\t\t\tbyPrimary[event.primary] ??= { primary: event.primary, events: [] }\n\t\t\tbyPrimary[event.primary].events.push(event)\n\t\t}\n\t\tconst payloads: ActionsPayload.WatchEventPayload[] = []\n\t\tfor (const eventsByPrimary of Object.values(byPrimary)) {\n\t\t\tpayloads.push({\n\t\t\t\toperation: 'watch',\n\t\t\t\ttrigger: events[0].listener.trigger.name,\n\t\t\t\tentity: events[0].entity.name,\n\t\t\t\tid: eventsByPrimary.primary,\n\t\t\t\tselection: events[0].selection ?? selections[eventsByPrimary.primary],\n\t\t\t\tevents: eventsByPrimary.events.map(it => this.buildBaseEventPayloads(it)),\n\t\t\t})\n\t\t}\n\t\treturn payloads\n\t}\n\n\tprivate buildBaseEventPayloads(event: FiredEvent, selection?: any): ActionsPayload.BaseEventPayload {\n\t\tswitch (event.cause.type) {\n\t\t\tcase 'AfterInsertEvent':\n\t\t\t\treturn {\n\t\t\t\t\toperation: 'create',\n\t\t\t\t\tentity: event.cause.entity.name,\n\t\t\t\t\tid: event.cause.id,\n\t\t\t\t\tselection,\n\t\t\t\t\tvalues: Object.fromEntries(event.cause.data.map(it => [it.fieldName, it.resolvedValue])),\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t}\n\t\t\tcase 'AfterUpdateEvent':\n\t\t\tcase 'BeforeUpdateEvent':\n\t\t\t\tconst afterEvent = event.cause.type === 'AfterUpdateEvent' ? event.cause : event.cause.afterEvent\n\t\t\t\tif (!afterEvent) {\n\t\t\t\t\tthrow new ImplementationException()\n\t\t\t\t}\n\t\t\t\treturn {\n\t\t\t\t\toperation: 'update',\n\t\t\t\t\tentity: event.cause.entity.name,\n\t\t\t\t\tid: event.cause.id,\n\t\t\t\t\tselection,\n\t\t\t\t\tvalues: Object.fromEntries(event.cause.data.map(it => [it.fieldName, it.resolvedValue])),\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t\told: Object.fromEntries(afterEvent.data.map(it => [it.fieldName, it.old])),\n\t\t\t\t}\n\t\t\tcase 'BeforeDeleteEvent':\n\t\t\t\treturn {\n\t\t\t\t\toperation: 'delete',\n\t\t\t\t\tentity: event.cause.entity.name,\n\t\t\t\t\tid: event.cause.id,\n\t\t\t\t\tselection,\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t}\n\t\t\tcase 'AfterJunctionUpdateEvent':\n\t\t\t\tif (event.listener.type !== 'junction') {\n\t\t\t\t\tthrow new ImplementationException()\n\t\t\t\t}\n\t\t\t\tconst [id, inverseId] = event.listener.context.type === 'owning'\n\t\t\t\t\t? [event.cause.owningId, event.cause.inverseId]\n\t\t\t\t\t: [event.cause.inverseId, event.cause.owningId]\n\t\t\t\treturn {\n\t\t\t\t\toperation: event.cause.operation === 'connect' ? 'junction_connect' : 'junction_disconnect',\n\t\t\t\t\tentity: event.listener.context.entity.name,\n\t\t\t\t\trelation: event.listener.context.relation.name,\n\t\t\t\t\tid,\n\t\t\t\t\tinverseId,\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t}\n\t\t\tdefault:\n\t\t\t\tassertNever(event.cause, it => it.type)\n\t\t}\n\t}\n\n\tprivate async fetchSelection(events: FiredEvent[]): Promise<Selections> {\n\t\tconst trigger = events[0].listener.trigger\n\t\tif (!trigger.selection) {\n\t\t\treturn {}\n\t\t}\n\n\t\tconst ids = Array.from(new Set(events.filter(it => it.listener.type !== 'delete').map(it => it.primary)))\n\t\tif (ids.length === 0) {\n\t\t\treturn {}\n\t\t}\n\t\tconst entity = events[0].entity\n\t\tconst input = this.convertSelectionNode(trigger.selection).withArg('filter', {\n\t\t\t[entity.primary]: { in: ids },\n\t\t})\n\t\treturn await this.mapper.selectAssoc(entity, input, [], entity.primary)\n\t}\n\n\n\tprivate convertSelectionNode(node: Actions.SelectionNode, nodeName = 'root', path: string[] = []): ObjectNode<Input.ListQueryInput> {\n\t\treturn new ObjectNode(nodeName, nodeName, node.map(it => {\n\t\t\tconst [field, args, selection] = Array.isArray(it) ? it : [it, undefined, undefined]\n\t\t\tif (selection === undefined || selection.length === 0) {\n\t\t\t\treturn new FieldNode(field, field, {})\n\t\t\t}\n\t\t\treturn this.convertSelectionNode(selection, field, [...path, nodeName]).withArgs(args)\n\t\t}), {}, {}, path)\n\t}\n}\n"],"names":[],"mappings":";;;AAQO,MAAM,sBAAsB;AAAA,EAClC,YACkB,QAChB;AADgB,SAAA,SAAA;AAAA,EAElB;AAAA,EAEA,MAAa,MAAM,QAAiE;AAC7E,UAAA,iBAAiB,OAAO,OAAO,CAAM,OAAA;AAC1C,aAAO,GAAG,MAAM,SAAS,uBACrB,GAAG,MAAM,YAAY,eAAe;AAAA,IAAA,CACxC;AACG,QAAA,eAAe,WAAW,GAAG;AAChC,aAAO;IACR;AACA,UAAM,aAAa,MAAM,KAAK,eAAe,cAAc;AAC3D,UAAM,cAAc,eAAe,CAAC,EAAE,SAAS,QAAQ;AACvD,QAAI,gBAAgB,SAAS;AAC5B,aAAO,eAAe,IAAI,CAAA,QAAO,EAAE,SAAS,GAAG,SAAS,QAAQ,MAAM,GAAG,KAAK,uBAAuB,IAAI,WAAW,GAAG,OAAO,CAAC,EAAI,EAAA;AAAA,IACpI;AACA,QAAI,gBAAgB,SAAS;AACrB,aAAA,KAAK,wBAAwB,gBAAgB,UAAU;AAAA,IAC/D;AACA,WAAO,YAAY,WAAW;AAAA,EAC/B;AAAA,EAEA,MAAa,gBAAgB,OAAwC;AACpE,QAAI,MAAM,SAAS,SAAS,YAAY,MAAM,SAAS,QAAQ,WAAW;AACzE,YAAM,QAAQ,KAAK,qBAAqB,MAAM,SAAS,QAAQ,SAAS;AAElE,YAAA,YAAY,MAAM,KAAK,OAAO,aAAa,MAAM,QAAQ,MAAM,QAAQ,MAAM;AAAA,QAClF,CAAC,MAAM,OAAO,OAAO,GAAG,MAAM;AAAA,MAAA,CAC9B,GAAG,CAAE,CAAA;AACC,aAAA,EAAE,GAAG,OAAO;IACpB;AACO,WAAA;AAAA,EACR;AAAA,EAEQ,wBAAwB,QAAsB,YAA4D;AA7CnH,QAAA;AA8CE,UAAM,YAA+F,CAAA;AACrG,eAAW,SAAS,QAAQ;AACjB,gBAAA,KAAA,MAAM,aAAhB,UAA6B,EAAA,IAAA,EAAE,SAAS,MAAM,SAAS,QAAQ,CAAA,EAAG;AAClE,gBAAU,MAAM,OAAO,EAAE,OAAO,KAAK,KAAK;AAAA,IAC3C;AACA,UAAM,WAA+C,CAAA;AACrD,eAAW,mBAAmB,OAAO,OAAO,SAAS,GAAG;AACvD,eAAS,KAAK;AAAA,QACb,WAAW;AAAA,QACX,SAAS,OAAO,CAAC,EAAE,SAAS,QAAQ;AAAA,QACpC,QAAQ,OAAO,CAAC,EAAE,OAAO;AAAA,QACzB,IAAI,gBAAgB;AAAA,QACpB,WAAW,OAAO,CAAC,EAAE,aAAa,WAAW,gBAAgB,OAAO;AAAA,
|
|
1
|
+
{"version":3,"file":"TriggerPayloadBuilder.js","sources":["../../../../../packages/engine-actions/src/triggers/TriggerPayloadBuilder.ts"],"sourcesContent":["import { ImplementationException } from '../ImplementationException'\nimport { assertNever } from '../utils/assertNever'\nimport { FiredEvent } from './TriggerPayloadManager'\nimport { Actions, ActionsPayload, Input } from '@contember/schema'\nimport { FieldNode, Mapper, ObjectNode } from '@contember/engine-content-api'\n\ntype Selections = Record<Input.PrimaryValue, any>\n\nexport class TriggerPayloadBuilder {\n\tconstructor(\n\t\tprivate readonly mapper: Mapper,\n\t) {\n\t}\n\n\tpublic async build(events: FiredEvent[]): Promise<ActionsPayload.AnyEventPayload[]> {\n\t\tconst filteredEvents = events.filter(it => {\n\t\t\treturn it.cause.type !== 'BeforeUpdateEvent'\n\t\t\t\t|| it.cause.afterEvent?.hasChanges === true\n\t\t})\n\t\tif (filteredEvents.length === 0) {\n\t\t\treturn []\n\t\t}\n\t\tconst selections = await this.fetchSelection(filteredEvents)\n\t\tconst triggerType = filteredEvents[0].listener.trigger.type\n\t\tif (triggerType === 'basic') {\n\t\t\treturn filteredEvents.map(it => ({ trigger: it.listener.trigger.name, ...this.buildBaseEventPayloads(it, selections[it.primary]) }))\n\t\t}\n\t\tif (triggerType === 'watch') {\n\t\t\treturn this.buildWatchEventPayloads(filteredEvents, selections)\n\t\t}\n\t\treturn assertNever(triggerType)\n\t}\n\n\tpublic async preprocessEvent(event: FiredEvent): Promise<FiredEvent> {\n\t\tif (event.listener.type === 'delete' && event.listener.trigger.selection) {\n\t\t\tconst input = this.convertSelectionNode(event.listener.trigger.selection)\n\n\t\t\tconst selection = await this.mapper.selectUnique(event.entity, input.withArg('by', {\n\t\t\t\t[event.entity.primary]: event.primary,\n\t\t\t}), [])\n\t\t\treturn { ...event, selection }\n\t\t}\n\t\treturn event\n\t}\n\n\tprivate buildWatchEventPayloads(events: FiredEvent[], selections: Selections): ActionsPayload.WatchEventPayload[] {\n\t\tconst byPrimary: Record<Input.PrimaryValue, { primary: Input.PrimaryValue; events: FiredEvent[] }> = {}\n\t\tfor (const event of events) {\n\t\t\tbyPrimary[event.primary] ??= { primary: event.primary, events: [] }\n\t\t\tbyPrimary[event.primary].events.push(event)\n\t\t}\n\t\tconst payloads: ActionsPayload.WatchEventPayload[] = []\n\t\tfor (const eventsByPrimary of Object.values(byPrimary)) {\n\t\t\tpayloads.push({\n\t\t\t\toperation: 'watch',\n\t\t\t\ttrigger: events[0].listener.trigger.name,\n\t\t\t\tentity: events[0].entity.name,\n\t\t\t\tid: eventsByPrimary.primary,\n\t\t\t\tselection: eventsByPrimary.events[0].selection ?? selections[eventsByPrimary.primary],\n\t\t\t\tevents: eventsByPrimary.events.map(it => this.buildBaseEventPayloads(it)),\n\t\t\t})\n\t\t}\n\t\treturn payloads\n\t}\n\n\tprivate buildBaseEventPayloads(event: FiredEvent, selection?: any): ActionsPayload.BaseEventPayload {\n\t\tswitch (event.cause.type) {\n\t\t\tcase 'AfterInsertEvent':\n\t\t\t\treturn {\n\t\t\t\t\toperation: 'create',\n\t\t\t\t\tentity: event.cause.entity.name,\n\t\t\t\t\tid: event.cause.id,\n\t\t\t\t\tselection,\n\t\t\t\t\tvalues: Object.fromEntries(event.cause.data.map(it => [it.fieldName, it.resolvedValue])),\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t}\n\t\t\tcase 'AfterUpdateEvent':\n\t\t\tcase 'BeforeUpdateEvent':\n\t\t\t\tconst afterEvent = event.cause.type === 'AfterUpdateEvent' ? event.cause : event.cause.afterEvent\n\t\t\t\tif (!afterEvent) {\n\t\t\t\t\tthrow new ImplementationException()\n\t\t\t\t}\n\t\t\t\treturn {\n\t\t\t\t\toperation: 'update',\n\t\t\t\t\tentity: event.cause.entity.name,\n\t\t\t\t\tid: event.cause.id,\n\t\t\t\t\tselection,\n\t\t\t\t\tvalues: Object.fromEntries(event.cause.data.map(it => [it.fieldName, it.resolvedValue])),\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t\told: Object.fromEntries(afterEvent.data.map(it => [it.fieldName, it.old])),\n\t\t\t\t}\n\t\t\tcase 'BeforeDeleteEvent':\n\t\t\t\treturn {\n\t\t\t\t\toperation: 'delete',\n\t\t\t\t\tentity: event.cause.entity.name,\n\t\t\t\t\tid: event.cause.id,\n\t\t\t\t\tselection,\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t}\n\t\t\tcase 'AfterJunctionUpdateEvent':\n\t\t\t\tif (event.listener.type !== 'junction') {\n\t\t\t\t\tthrow new ImplementationException()\n\t\t\t\t}\n\t\t\t\tconst [id, inverseId] = event.listener.context.type === 'owning'\n\t\t\t\t\t? [event.cause.owningId, event.cause.inverseId]\n\t\t\t\t\t: [event.cause.inverseId, event.cause.owningId]\n\t\t\t\treturn {\n\t\t\t\t\toperation: event.cause.operation === 'connect' ? 'junction_connect' : 'junction_disconnect',\n\t\t\t\t\tentity: event.listener.context.entity.name,\n\t\t\t\t\trelation: event.listener.context.relation.name,\n\t\t\t\t\tid,\n\t\t\t\t\tinverseId,\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t}\n\t\t\tdefault:\n\t\t\t\tassertNever(event.cause, it => it.type)\n\t\t}\n\t}\n\n\tprivate async fetchSelection(events: FiredEvent[]): Promise<Selections> {\n\t\tconst trigger = events[0].listener.trigger\n\t\tif (!trigger.selection) {\n\t\t\treturn {}\n\t\t}\n\n\t\tconst ids = Array.from(new Set(events.filter(it => it.listener.type !== 'delete').map(it => it.primary)))\n\t\tif (ids.length === 0) {\n\t\t\treturn {}\n\t\t}\n\t\tconst entity = events[0].entity\n\t\tconst input = this.convertSelectionNode(trigger.selection).withArg('filter', {\n\t\t\t[entity.primary]: { in: ids },\n\t\t})\n\t\treturn await this.mapper.selectAssoc(entity, input, [], entity.primary)\n\t}\n\n\n\tprivate convertSelectionNode(node: Actions.SelectionNode, nodeName = 'root', path: string[] = []): ObjectNode<Input.ListQueryInput> {\n\t\treturn new ObjectNode(nodeName, nodeName, node.map(it => {\n\t\t\tconst [field, args, selection] = Array.isArray(it) ? it : [it, undefined, undefined]\n\t\t\tif (selection === undefined || selection.length === 0) {\n\t\t\t\treturn new FieldNode(field, field, {})\n\t\t\t}\n\t\t\treturn this.convertSelectionNode(selection, field, [...path, nodeName]).withArgs(args)\n\t\t}), {}, {}, path)\n\t}\n}\n"],"names":[],"mappings":"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"}
|
|
@@ -48,7 +48,7 @@ class TriggerPayloadBuilder {
|
|
|
48
48
|
trigger: events[0].listener.trigger.name,
|
|
49
49
|
entity: events[0].entity.name,
|
|
50
50
|
id: eventsByPrimary.primary,
|
|
51
|
-
selection: events[0].selection ?? selections[eventsByPrimary.primary],
|
|
51
|
+
selection: eventsByPrimary.events[0].selection ?? selections[eventsByPrimary.primary],
|
|
52
52
|
events: eventsByPrimary.events.map((it) => this.buildBaseEventPayloads(it))
|
|
53
53
|
});
|
|
54
54
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"TriggerPayloadBuilder.cjs","sources":["../../../../../packages/engine-actions/src/triggers/TriggerPayloadBuilder.ts"],"sourcesContent":["import { ImplementationException } from '../ImplementationException'\nimport { assertNever } from '../utils/assertNever'\nimport { FiredEvent } from './TriggerPayloadManager'\nimport { Actions, ActionsPayload, Input } from '@contember/schema'\nimport { FieldNode, Mapper, ObjectNode } from '@contember/engine-content-api'\n\ntype Selections = Record<Input.PrimaryValue, any>\n\nexport class TriggerPayloadBuilder {\n\tconstructor(\n\t\tprivate readonly mapper: Mapper,\n\t) {\n\t}\n\n\tpublic async build(events: FiredEvent[]): Promise<ActionsPayload.AnyEventPayload[]> {\n\t\tconst filteredEvents = events.filter(it => {\n\t\t\treturn it.cause.type !== 'BeforeUpdateEvent'\n\t\t\t\t|| it.cause.afterEvent?.hasChanges === true\n\t\t})\n\t\tif (filteredEvents.length === 0) {\n\t\t\treturn []\n\t\t}\n\t\tconst selections = await this.fetchSelection(filteredEvents)\n\t\tconst triggerType = filteredEvents[0].listener.trigger.type\n\t\tif (triggerType === 'basic') {\n\t\t\treturn filteredEvents.map(it => ({ trigger: it.listener.trigger.name, ...this.buildBaseEventPayloads(it, selections[it.primary]) }))\n\t\t}\n\t\tif (triggerType === 'watch') {\n\t\t\treturn this.buildWatchEventPayloads(filteredEvents, selections)\n\t\t}\n\t\treturn assertNever(triggerType)\n\t}\n\n\tpublic async preprocessEvent(event: FiredEvent): Promise<FiredEvent> {\n\t\tif (event.listener.type === 'delete' && event.listener.trigger.selection) {\n\t\t\tconst input = this.convertSelectionNode(event.listener.trigger.selection)\n\n\t\t\tconst selection = await this.mapper.selectUnique(event.entity, input.withArg('by', {\n\t\t\t\t[event.entity.primary]: event.primary,\n\t\t\t}), [])\n\t\t\treturn { ...event, selection }\n\t\t}\n\t\treturn event\n\t}\n\n\tprivate buildWatchEventPayloads(events: FiredEvent[], selections: Selections): ActionsPayload.WatchEventPayload[] {\n\t\tconst byPrimary: Record<Input.PrimaryValue, { primary: Input.PrimaryValue; events: FiredEvent[] }> = {}\n\t\tfor (const event of events) {\n\t\t\tbyPrimary[event.primary] ??= { primary: event.primary, events: [] }\n\t\t\tbyPrimary[event.primary].events.push(event)\n\t\t}\n\t\tconst payloads: ActionsPayload.WatchEventPayload[] = []\n\t\tfor (const eventsByPrimary of Object.values(byPrimary)) {\n\t\t\tpayloads.push({\n\t\t\t\toperation: 'watch',\n\t\t\t\ttrigger: events[0].listener.trigger.name,\n\t\t\t\tentity: events[0].entity.name,\n\t\t\t\tid: eventsByPrimary.primary,\n\t\t\t\tselection: events[0].selection ?? selections[eventsByPrimary.primary],\n\t\t\t\tevents: eventsByPrimary.events.map(it => this.buildBaseEventPayloads(it)),\n\t\t\t})\n\t\t}\n\t\treturn payloads\n\t}\n\n\tprivate buildBaseEventPayloads(event: FiredEvent, selection?: any): ActionsPayload.BaseEventPayload {\n\t\tswitch (event.cause.type) {\n\t\t\tcase 'AfterInsertEvent':\n\t\t\t\treturn {\n\t\t\t\t\toperation: 'create',\n\t\t\t\t\tentity: event.cause.entity.name,\n\t\t\t\t\tid: event.cause.id,\n\t\t\t\t\tselection,\n\t\t\t\t\tvalues: Object.fromEntries(event.cause.data.map(it => [it.fieldName, it.resolvedValue])),\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t}\n\t\t\tcase 'AfterUpdateEvent':\n\t\t\tcase 'BeforeUpdateEvent':\n\t\t\t\tconst afterEvent = event.cause.type === 'AfterUpdateEvent' ? event.cause : event.cause.afterEvent\n\t\t\t\tif (!afterEvent) {\n\t\t\t\t\tthrow new ImplementationException()\n\t\t\t\t}\n\t\t\t\treturn {\n\t\t\t\t\toperation: 'update',\n\t\t\t\t\tentity: event.cause.entity.name,\n\t\t\t\t\tid: event.cause.id,\n\t\t\t\t\tselection,\n\t\t\t\t\tvalues: Object.fromEntries(event.cause.data.map(it => [it.fieldName, it.resolvedValue])),\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t\told: Object.fromEntries(afterEvent.data.map(it => [it.fieldName, it.old])),\n\t\t\t\t}\n\t\t\tcase 'BeforeDeleteEvent':\n\t\t\t\treturn {\n\t\t\t\t\toperation: 'delete',\n\t\t\t\t\tentity: event.cause.entity.name,\n\t\t\t\t\tid: event.cause.id,\n\t\t\t\t\tselection,\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t}\n\t\t\tcase 'AfterJunctionUpdateEvent':\n\t\t\t\tif (event.listener.type !== 'junction') {\n\t\t\t\t\tthrow new ImplementationException()\n\t\t\t\t}\n\t\t\t\tconst [id, inverseId] = event.listener.context.type === 'owning'\n\t\t\t\t\t? [event.cause.owningId, event.cause.inverseId]\n\t\t\t\t\t: [event.cause.inverseId, event.cause.owningId]\n\t\t\t\treturn {\n\t\t\t\t\toperation: event.cause.operation === 'connect' ? 'junction_connect' : 'junction_disconnect',\n\t\t\t\t\tentity: event.listener.context.entity.name,\n\t\t\t\t\trelation: event.listener.context.relation.name,\n\t\t\t\t\tid,\n\t\t\t\t\tinverseId,\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t}\n\t\t\tdefault:\n\t\t\t\tassertNever(event.cause, it => it.type)\n\t\t}\n\t}\n\n\tprivate async fetchSelection(events: FiredEvent[]): Promise<Selections> {\n\t\tconst trigger = events[0].listener.trigger\n\t\tif (!trigger.selection) {\n\t\t\treturn {}\n\t\t}\n\n\t\tconst ids = Array.from(new Set(events.filter(it => it.listener.type !== 'delete').map(it => it.primary)))\n\t\tif (ids.length === 0) {\n\t\t\treturn {}\n\t\t}\n\t\tconst entity = events[0].entity\n\t\tconst input = this.convertSelectionNode(trigger.selection).withArg('filter', {\n\t\t\t[entity.primary]: { in: ids },\n\t\t})\n\t\treturn await this.mapper.selectAssoc(entity, input, [], entity.primary)\n\t}\n\n\n\tprivate convertSelectionNode(node: Actions.SelectionNode, nodeName = 'root', path: string[] = []): ObjectNode<Input.ListQueryInput> {\n\t\treturn new ObjectNode(nodeName, nodeName, node.map(it => {\n\t\t\tconst [field, args, selection] = Array.isArray(it) ? it : [it, undefined, undefined]\n\t\t\tif (selection === undefined || selection.length === 0) {\n\t\t\t\treturn new FieldNode(field, field, {})\n\t\t\t}\n\t\t\treturn this.convertSelectionNode(selection, field, [...path, nodeName]).withArgs(args)\n\t\t}), {}, {}, path)\n\t}\n}\n"],"names":["assertNever","ImplementationException","ObjectNode","FieldNode"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"TriggerPayloadBuilder.cjs","sources":["../../../../../packages/engine-actions/src/triggers/TriggerPayloadBuilder.ts"],"sourcesContent":["import { ImplementationException } from '../ImplementationException'\nimport { assertNever } from '../utils/assertNever'\nimport { FiredEvent } from './TriggerPayloadManager'\nimport { Actions, ActionsPayload, Input } from '@contember/schema'\nimport { FieldNode, Mapper, ObjectNode } from '@contember/engine-content-api'\n\ntype Selections = Record<Input.PrimaryValue, any>\n\nexport class TriggerPayloadBuilder {\n\tconstructor(\n\t\tprivate readonly mapper: Mapper,\n\t) {\n\t}\n\n\tpublic async build(events: FiredEvent[]): Promise<ActionsPayload.AnyEventPayload[]> {\n\t\tconst filteredEvents = events.filter(it => {\n\t\t\treturn it.cause.type !== 'BeforeUpdateEvent'\n\t\t\t\t|| it.cause.afterEvent?.hasChanges === true\n\t\t})\n\t\tif (filteredEvents.length === 0) {\n\t\t\treturn []\n\t\t}\n\t\tconst selections = await this.fetchSelection(filteredEvents)\n\t\tconst triggerType = filteredEvents[0].listener.trigger.type\n\t\tif (triggerType === 'basic') {\n\t\t\treturn filteredEvents.map(it => ({ trigger: it.listener.trigger.name, ...this.buildBaseEventPayloads(it, selections[it.primary]) }))\n\t\t}\n\t\tif (triggerType === 'watch') {\n\t\t\treturn this.buildWatchEventPayloads(filteredEvents, selections)\n\t\t}\n\t\treturn assertNever(triggerType)\n\t}\n\n\tpublic async preprocessEvent(event: FiredEvent): Promise<FiredEvent> {\n\t\tif (event.listener.type === 'delete' && event.listener.trigger.selection) {\n\t\t\tconst input = this.convertSelectionNode(event.listener.trigger.selection)\n\n\t\t\tconst selection = await this.mapper.selectUnique(event.entity, input.withArg('by', {\n\t\t\t\t[event.entity.primary]: event.primary,\n\t\t\t}), [])\n\t\t\treturn { ...event, selection }\n\t\t}\n\t\treturn event\n\t}\n\n\tprivate buildWatchEventPayloads(events: FiredEvent[], selections: Selections): ActionsPayload.WatchEventPayload[] {\n\t\tconst byPrimary: Record<Input.PrimaryValue, { primary: Input.PrimaryValue; events: FiredEvent[] }> = {}\n\t\tfor (const event of events) {\n\t\t\tbyPrimary[event.primary] ??= { primary: event.primary, events: [] }\n\t\t\tbyPrimary[event.primary].events.push(event)\n\t\t}\n\t\tconst payloads: ActionsPayload.WatchEventPayload[] = []\n\t\tfor (const eventsByPrimary of Object.values(byPrimary)) {\n\t\t\tpayloads.push({\n\t\t\t\toperation: 'watch',\n\t\t\t\ttrigger: events[0].listener.trigger.name,\n\t\t\t\tentity: events[0].entity.name,\n\t\t\t\tid: eventsByPrimary.primary,\n\t\t\t\tselection: eventsByPrimary.events[0].selection ?? selections[eventsByPrimary.primary],\n\t\t\t\tevents: eventsByPrimary.events.map(it => this.buildBaseEventPayloads(it)),\n\t\t\t})\n\t\t}\n\t\treturn payloads\n\t}\n\n\tprivate buildBaseEventPayloads(event: FiredEvent, selection?: any): ActionsPayload.BaseEventPayload {\n\t\tswitch (event.cause.type) {\n\t\t\tcase 'AfterInsertEvent':\n\t\t\t\treturn {\n\t\t\t\t\toperation: 'create',\n\t\t\t\t\tentity: event.cause.entity.name,\n\t\t\t\t\tid: event.cause.id,\n\t\t\t\t\tselection,\n\t\t\t\t\tvalues: Object.fromEntries(event.cause.data.map(it => [it.fieldName, it.resolvedValue])),\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t}\n\t\t\tcase 'AfterUpdateEvent':\n\t\t\tcase 'BeforeUpdateEvent':\n\t\t\t\tconst afterEvent = event.cause.type === 'AfterUpdateEvent' ? event.cause : event.cause.afterEvent\n\t\t\t\tif (!afterEvent) {\n\t\t\t\t\tthrow new ImplementationException()\n\t\t\t\t}\n\t\t\t\treturn {\n\t\t\t\t\toperation: 'update',\n\t\t\t\t\tentity: event.cause.entity.name,\n\t\t\t\t\tid: event.cause.id,\n\t\t\t\t\tselection,\n\t\t\t\t\tvalues: Object.fromEntries(event.cause.data.map(it => [it.fieldName, it.resolvedValue])),\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t\told: Object.fromEntries(afterEvent.data.map(it => [it.fieldName, it.old])),\n\t\t\t\t}\n\t\t\tcase 'BeforeDeleteEvent':\n\t\t\t\treturn {\n\t\t\t\t\toperation: 'delete',\n\t\t\t\t\tentity: event.cause.entity.name,\n\t\t\t\t\tid: event.cause.id,\n\t\t\t\t\tselection,\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t}\n\t\t\tcase 'AfterJunctionUpdateEvent':\n\t\t\t\tif (event.listener.type !== 'junction') {\n\t\t\t\t\tthrow new ImplementationException()\n\t\t\t\t}\n\t\t\t\tconst [id, inverseId] = event.listener.context.type === 'owning'\n\t\t\t\t\t? [event.cause.owningId, event.cause.inverseId]\n\t\t\t\t\t: [event.cause.inverseId, event.cause.owningId]\n\t\t\t\treturn {\n\t\t\t\t\toperation: event.cause.operation === 'connect' ? 'junction_connect' : 'junction_disconnect',\n\t\t\t\t\tentity: event.listener.context.entity.name,\n\t\t\t\t\trelation: event.listener.context.relation.name,\n\t\t\t\t\tid,\n\t\t\t\t\tinverseId,\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t}\n\t\t\tdefault:\n\t\t\t\tassertNever(event.cause, it => it.type)\n\t\t}\n\t}\n\n\tprivate async fetchSelection(events: FiredEvent[]): Promise<Selections> {\n\t\tconst trigger = events[0].listener.trigger\n\t\tif (!trigger.selection) {\n\t\t\treturn {}\n\t\t}\n\n\t\tconst ids = Array.from(new Set(events.filter(it => it.listener.type !== 'delete').map(it => it.primary)))\n\t\tif (ids.length === 0) {\n\t\t\treturn {}\n\t\t}\n\t\tconst entity = events[0].entity\n\t\tconst input = this.convertSelectionNode(trigger.selection).withArg('filter', {\n\t\t\t[entity.primary]: { in: ids },\n\t\t})\n\t\treturn await this.mapper.selectAssoc(entity, input, [], entity.primary)\n\t}\n\n\n\tprivate convertSelectionNode(node: Actions.SelectionNode, nodeName = 'root', path: string[] = []): ObjectNode<Input.ListQueryInput> {\n\t\treturn new ObjectNode(nodeName, nodeName, node.map(it => {\n\t\t\tconst [field, args, selection] = Array.isArray(it) ? it : [it, undefined, undefined]\n\t\t\tif (selection === undefined || selection.length === 0) {\n\t\t\t\treturn new FieldNode(field, field, {})\n\t\t\t}\n\t\t\treturn this.convertSelectionNode(selection, field, [...path, nodeName]).withArgs(args)\n\t\t}), {}, {}, path)\n\t}\n}\n"],"names":["assertNever","ImplementationException","ObjectNode","FieldNode"],"mappings":"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"}
|
|
@@ -46,7 +46,7 @@ class TriggerPayloadBuilder {
|
|
|
46
46
|
trigger: events[0].listener.trigger.name,
|
|
47
47
|
entity: events[0].entity.name,
|
|
48
48
|
id: eventsByPrimary.primary,
|
|
49
|
-
selection: events[0].selection ?? selections[eventsByPrimary.primary],
|
|
49
|
+
selection: eventsByPrimary.events[0].selection ?? selections[eventsByPrimary.primary],
|
|
50
50
|
events: eventsByPrimary.events.map((it) => this.buildBaseEventPayloads(it))
|
|
51
51
|
});
|
|
52
52
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"TriggerPayloadBuilder.js","sources":["../../../../../packages/engine-actions/src/triggers/TriggerPayloadBuilder.ts"],"sourcesContent":["import { ImplementationException } from '../ImplementationException'\nimport { assertNever } from '../utils/assertNever'\nimport { FiredEvent } from './TriggerPayloadManager'\nimport { Actions, ActionsPayload, Input } from '@contember/schema'\nimport { FieldNode, Mapper, ObjectNode } from '@contember/engine-content-api'\n\ntype Selections = Record<Input.PrimaryValue, any>\n\nexport class TriggerPayloadBuilder {\n\tconstructor(\n\t\tprivate readonly mapper: Mapper,\n\t) {\n\t}\n\n\tpublic async build(events: FiredEvent[]): Promise<ActionsPayload.AnyEventPayload[]> {\n\t\tconst filteredEvents = events.filter(it => {\n\t\t\treturn it.cause.type !== 'BeforeUpdateEvent'\n\t\t\t\t|| it.cause.afterEvent?.hasChanges === true\n\t\t})\n\t\tif (filteredEvents.length === 0) {\n\t\t\treturn []\n\t\t}\n\t\tconst selections = await this.fetchSelection(filteredEvents)\n\t\tconst triggerType = filteredEvents[0].listener.trigger.type\n\t\tif (triggerType === 'basic') {\n\t\t\treturn filteredEvents.map(it => ({ trigger: it.listener.trigger.name, ...this.buildBaseEventPayloads(it, selections[it.primary]) }))\n\t\t}\n\t\tif (triggerType === 'watch') {\n\t\t\treturn this.buildWatchEventPayloads(filteredEvents, selections)\n\t\t}\n\t\treturn assertNever(triggerType)\n\t}\n\n\tpublic async preprocessEvent(event: FiredEvent): Promise<FiredEvent> {\n\t\tif (event.listener.type === 'delete' && event.listener.trigger.selection) {\n\t\t\tconst input = this.convertSelectionNode(event.listener.trigger.selection)\n\n\t\t\tconst selection = await this.mapper.selectUnique(event.entity, input.withArg('by', {\n\t\t\t\t[event.entity.primary]: event.primary,\n\t\t\t}), [])\n\t\t\treturn { ...event, selection }\n\t\t}\n\t\treturn event\n\t}\n\n\tprivate buildWatchEventPayloads(events: FiredEvent[], selections: Selections): ActionsPayload.WatchEventPayload[] {\n\t\tconst byPrimary: Record<Input.PrimaryValue, { primary: Input.PrimaryValue; events: FiredEvent[] }> = {}\n\t\tfor (const event of events) {\n\t\t\tbyPrimary[event.primary] ??= { primary: event.primary, events: [] }\n\t\t\tbyPrimary[event.primary].events.push(event)\n\t\t}\n\t\tconst payloads: ActionsPayload.WatchEventPayload[] = []\n\t\tfor (const eventsByPrimary of Object.values(byPrimary)) {\n\t\t\tpayloads.push({\n\t\t\t\toperation: 'watch',\n\t\t\t\ttrigger: events[0].listener.trigger.name,\n\t\t\t\tentity: events[0].entity.name,\n\t\t\t\tid: eventsByPrimary.primary,\n\t\t\t\tselection: events[0].selection ?? selections[eventsByPrimary.primary],\n\t\t\t\tevents: eventsByPrimary.events.map(it => this.buildBaseEventPayloads(it)),\n\t\t\t})\n\t\t}\n\t\treturn payloads\n\t}\n\n\tprivate buildBaseEventPayloads(event: FiredEvent, selection?: any): ActionsPayload.BaseEventPayload {\n\t\tswitch (event.cause.type) {\n\t\t\tcase 'AfterInsertEvent':\n\t\t\t\treturn {\n\t\t\t\t\toperation: 'create',\n\t\t\t\t\tentity: event.cause.entity.name,\n\t\t\t\t\tid: event.cause.id,\n\t\t\t\t\tselection,\n\t\t\t\t\tvalues: Object.fromEntries(event.cause.data.map(it => [it.fieldName, it.resolvedValue])),\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t}\n\t\t\tcase 'AfterUpdateEvent':\n\t\t\tcase 'BeforeUpdateEvent':\n\t\t\t\tconst afterEvent = event.cause.type === 'AfterUpdateEvent' ? event.cause : event.cause.afterEvent\n\t\t\t\tif (!afterEvent) {\n\t\t\t\t\tthrow new ImplementationException()\n\t\t\t\t}\n\t\t\t\treturn {\n\t\t\t\t\toperation: 'update',\n\t\t\t\t\tentity: event.cause.entity.name,\n\t\t\t\t\tid: event.cause.id,\n\t\t\t\t\tselection,\n\t\t\t\t\tvalues: Object.fromEntries(event.cause.data.map(it => [it.fieldName, it.resolvedValue])),\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t\told: Object.fromEntries(afterEvent.data.map(it => [it.fieldName, it.old])),\n\t\t\t\t}\n\t\t\tcase 'BeforeDeleteEvent':\n\t\t\t\treturn {\n\t\t\t\t\toperation: 'delete',\n\t\t\t\t\tentity: event.cause.entity.name,\n\t\t\t\t\tid: event.cause.id,\n\t\t\t\t\tselection,\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t}\n\t\t\tcase 'AfterJunctionUpdateEvent':\n\t\t\t\tif (event.listener.type !== 'junction') {\n\t\t\t\t\tthrow new ImplementationException()\n\t\t\t\t}\n\t\t\t\tconst [id, inverseId] = event.listener.context.type === 'owning'\n\t\t\t\t\t? [event.cause.owningId, event.cause.inverseId]\n\t\t\t\t\t: [event.cause.inverseId, event.cause.owningId]\n\t\t\t\treturn {\n\t\t\t\t\toperation: event.cause.operation === 'connect' ? 'junction_connect' : 'junction_disconnect',\n\t\t\t\t\tentity: event.listener.context.entity.name,\n\t\t\t\t\trelation: event.listener.context.relation.name,\n\t\t\t\t\tid,\n\t\t\t\t\tinverseId,\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t}\n\t\t\tdefault:\n\t\t\t\tassertNever(event.cause, it => it.type)\n\t\t}\n\t}\n\n\tprivate async fetchSelection(events: FiredEvent[]): Promise<Selections> {\n\t\tconst trigger = events[0].listener.trigger\n\t\tif (!trigger.selection) {\n\t\t\treturn {}\n\t\t}\n\n\t\tconst ids = Array.from(new Set(events.filter(it => it.listener.type !== 'delete').map(it => it.primary)))\n\t\tif (ids.length === 0) {\n\t\t\treturn {}\n\t\t}\n\t\tconst entity = events[0].entity\n\t\tconst input = this.convertSelectionNode(trigger.selection).withArg('filter', {\n\t\t\t[entity.primary]: { in: ids },\n\t\t})\n\t\treturn await this.mapper.selectAssoc(entity, input, [], entity.primary)\n\t}\n\n\n\tprivate convertSelectionNode(node: Actions.SelectionNode, nodeName = 'root', path: string[] = []): ObjectNode<Input.ListQueryInput> {\n\t\treturn new ObjectNode(nodeName, nodeName, node.map(it => {\n\t\t\tconst [field, args, selection] = Array.isArray(it) ? it : [it, undefined, undefined]\n\t\t\tif (selection === undefined || selection.length === 0) {\n\t\t\t\treturn new FieldNode(field, field, {})\n\t\t\t}\n\t\t\treturn this.convertSelectionNode(selection, field, [...path, nodeName]).withArgs(args)\n\t\t}), {}, {}, path)\n\t}\n}\n"],"names":[],"mappings":";;;AAQO,MAAM,sBAAsB;AAAA,EAClC,YACkB,QAChB;AADgB,SAAA,SAAA;AAAA,EAElB;AAAA,EAEA,MAAa,MAAM,QAAiE;AAC7E,UAAA,iBAAiB,OAAO,OAAO,CAAM,OAAA;AAC1C,aAAO,GAAG,MAAM,SAAS,uBACrB,GAAG,MAAM,YAAY,eAAe;AAAA,IAAA,CACxC;AACG,QAAA,eAAe,WAAW,GAAG;AAChC,aAAO;IACR;AACA,UAAM,aAAa,MAAM,KAAK,eAAe,cAAc;AAC3D,UAAM,cAAc,eAAe,CAAC,EAAE,SAAS,QAAQ;AACvD,QAAI,gBAAgB,SAAS;AAC5B,aAAO,eAAe,IAAI,CAAA,QAAO,EAAE,SAAS,GAAG,SAAS,QAAQ,MAAM,GAAG,KAAK,uBAAuB,IAAI,WAAW,GAAG,OAAO,CAAC,EAAI,EAAA;AAAA,IACpI;AACA,QAAI,gBAAgB,SAAS;AACrB,aAAA,KAAK,wBAAwB,gBAAgB,UAAU;AAAA,IAC/D;AACA,WAAO,YAAY,WAAW;AAAA,EAC/B;AAAA,EAEA,MAAa,gBAAgB,OAAwC;AACpE,QAAI,MAAM,SAAS,SAAS,YAAY,MAAM,SAAS,QAAQ,WAAW;AACzE,YAAM,QAAQ,KAAK,qBAAqB,MAAM,SAAS,QAAQ,SAAS;AAElE,YAAA,YAAY,MAAM,KAAK,OAAO,aAAa,MAAM,QAAQ,MAAM,QAAQ,MAAM;AAAA,QAClF,CAAC,MAAM,OAAO,OAAO,GAAG,MAAM;AAAA,MAAA,CAC9B,GAAG,CAAE,CAAA;AACC,aAAA,EAAE,GAAG,OAAO;IACpB;AACO,WAAA;AAAA,EACR;AAAA,EAEQ,wBAAwB,QAAsB,YAA4D;AA7CnH,QAAA;AA8CE,UAAM,YAA+F,CAAA;AACrG,eAAW,SAAS,QAAQ;AACjB,gBAAA,KAAA,MAAM,aAAhB,UAA6B,EAAA,IAAA,EAAE,SAAS,MAAM,SAAS,QAAQ,CAAA,EAAG;AAClE,gBAAU,MAAM,OAAO,EAAE,OAAO,KAAK,KAAK;AAAA,IAC3C;AACA,UAAM,WAA+C,CAAA;AACrD,eAAW,mBAAmB,OAAO,OAAO,SAAS,GAAG;AACvD,eAAS,KAAK;AAAA,QACb,WAAW;AAAA,QACX,SAAS,OAAO,CAAC,EAAE,SAAS,QAAQ;AAAA,QACpC,QAAQ,OAAO,CAAC,EAAE,OAAO;AAAA,QACzB,IAAI,gBAAgB;AAAA,QACpB,WAAW,OAAO,CAAC,EAAE,aAAa,WAAW,gBAAgB,OAAO;AAAA,
|
|
1
|
+
{"version":3,"file":"TriggerPayloadBuilder.js","sources":["../../../../../packages/engine-actions/src/triggers/TriggerPayloadBuilder.ts"],"sourcesContent":["import { ImplementationException } from '../ImplementationException'\nimport { assertNever } from '../utils/assertNever'\nimport { FiredEvent } from './TriggerPayloadManager'\nimport { Actions, ActionsPayload, Input } from '@contember/schema'\nimport { FieldNode, Mapper, ObjectNode } from '@contember/engine-content-api'\n\ntype Selections = Record<Input.PrimaryValue, any>\n\nexport class TriggerPayloadBuilder {\n\tconstructor(\n\t\tprivate readonly mapper: Mapper,\n\t) {\n\t}\n\n\tpublic async build(events: FiredEvent[]): Promise<ActionsPayload.AnyEventPayload[]> {\n\t\tconst filteredEvents = events.filter(it => {\n\t\t\treturn it.cause.type !== 'BeforeUpdateEvent'\n\t\t\t\t|| it.cause.afterEvent?.hasChanges === true\n\t\t})\n\t\tif (filteredEvents.length === 0) {\n\t\t\treturn []\n\t\t}\n\t\tconst selections = await this.fetchSelection(filteredEvents)\n\t\tconst triggerType = filteredEvents[0].listener.trigger.type\n\t\tif (triggerType === 'basic') {\n\t\t\treturn filteredEvents.map(it => ({ trigger: it.listener.trigger.name, ...this.buildBaseEventPayloads(it, selections[it.primary]) }))\n\t\t}\n\t\tif (triggerType === 'watch') {\n\t\t\treturn this.buildWatchEventPayloads(filteredEvents, selections)\n\t\t}\n\t\treturn assertNever(triggerType)\n\t}\n\n\tpublic async preprocessEvent(event: FiredEvent): Promise<FiredEvent> {\n\t\tif (event.listener.type === 'delete' && event.listener.trigger.selection) {\n\t\t\tconst input = this.convertSelectionNode(event.listener.trigger.selection)\n\n\t\t\tconst selection = await this.mapper.selectUnique(event.entity, input.withArg('by', {\n\t\t\t\t[event.entity.primary]: event.primary,\n\t\t\t}), [])\n\t\t\treturn { ...event, selection }\n\t\t}\n\t\treturn event\n\t}\n\n\tprivate buildWatchEventPayloads(events: FiredEvent[], selections: Selections): ActionsPayload.WatchEventPayload[] {\n\t\tconst byPrimary: Record<Input.PrimaryValue, { primary: Input.PrimaryValue; events: FiredEvent[] }> = {}\n\t\tfor (const event of events) {\n\t\t\tbyPrimary[event.primary] ??= { primary: event.primary, events: [] }\n\t\t\tbyPrimary[event.primary].events.push(event)\n\t\t}\n\t\tconst payloads: ActionsPayload.WatchEventPayload[] = []\n\t\tfor (const eventsByPrimary of Object.values(byPrimary)) {\n\t\t\tpayloads.push({\n\t\t\t\toperation: 'watch',\n\t\t\t\ttrigger: events[0].listener.trigger.name,\n\t\t\t\tentity: events[0].entity.name,\n\t\t\t\tid: eventsByPrimary.primary,\n\t\t\t\tselection: eventsByPrimary.events[0].selection ?? selections[eventsByPrimary.primary],\n\t\t\t\tevents: eventsByPrimary.events.map(it => this.buildBaseEventPayloads(it)),\n\t\t\t})\n\t\t}\n\t\treturn payloads\n\t}\n\n\tprivate buildBaseEventPayloads(event: FiredEvent, selection?: any): ActionsPayload.BaseEventPayload {\n\t\tswitch (event.cause.type) {\n\t\t\tcase 'AfterInsertEvent':\n\t\t\t\treturn {\n\t\t\t\t\toperation: 'create',\n\t\t\t\t\tentity: event.cause.entity.name,\n\t\t\t\t\tid: event.cause.id,\n\t\t\t\t\tselection,\n\t\t\t\t\tvalues: Object.fromEntries(event.cause.data.map(it => [it.fieldName, it.resolvedValue])),\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t}\n\t\t\tcase 'AfterUpdateEvent':\n\t\t\tcase 'BeforeUpdateEvent':\n\t\t\t\tconst afterEvent = event.cause.type === 'AfterUpdateEvent' ? event.cause : event.cause.afterEvent\n\t\t\t\tif (!afterEvent) {\n\t\t\t\t\tthrow new ImplementationException()\n\t\t\t\t}\n\t\t\t\treturn {\n\t\t\t\t\toperation: 'update',\n\t\t\t\t\tentity: event.cause.entity.name,\n\t\t\t\t\tid: event.cause.id,\n\t\t\t\t\tselection,\n\t\t\t\t\tvalues: Object.fromEntries(event.cause.data.map(it => [it.fieldName, it.resolvedValue])),\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t\told: Object.fromEntries(afterEvent.data.map(it => [it.fieldName, it.old])),\n\t\t\t\t}\n\t\t\tcase 'BeforeDeleteEvent':\n\t\t\t\treturn {\n\t\t\t\t\toperation: 'delete',\n\t\t\t\t\tentity: event.cause.entity.name,\n\t\t\t\t\tid: event.cause.id,\n\t\t\t\t\tselection,\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t}\n\t\t\tcase 'AfterJunctionUpdateEvent':\n\t\t\t\tif (event.listener.type !== 'junction') {\n\t\t\t\t\tthrow new ImplementationException()\n\t\t\t\t}\n\t\t\t\tconst [id, inverseId] = event.listener.context.type === 'owning'\n\t\t\t\t\t? [event.cause.owningId, event.cause.inverseId]\n\t\t\t\t\t: [event.cause.inverseId, event.cause.owningId]\n\t\t\t\treturn {\n\t\t\t\t\toperation: event.cause.operation === 'connect' ? 'junction_connect' : 'junction_disconnect',\n\t\t\t\t\tentity: event.listener.context.entity.name,\n\t\t\t\t\trelation: event.listener.context.relation.name,\n\t\t\t\t\tid,\n\t\t\t\t\tinverseId,\n\t\t\t\t\tpath: 'path' in event.listener ? event.listener.path : undefined,\n\t\t\t\t}\n\t\t\tdefault:\n\t\t\t\tassertNever(event.cause, it => it.type)\n\t\t}\n\t}\n\n\tprivate async fetchSelection(events: FiredEvent[]): Promise<Selections> {\n\t\tconst trigger = events[0].listener.trigger\n\t\tif (!trigger.selection) {\n\t\t\treturn {}\n\t\t}\n\n\t\tconst ids = Array.from(new Set(events.filter(it => it.listener.type !== 'delete').map(it => it.primary)))\n\t\tif (ids.length === 0) {\n\t\t\treturn {}\n\t\t}\n\t\tconst entity = events[0].entity\n\t\tconst input = this.convertSelectionNode(trigger.selection).withArg('filter', {\n\t\t\t[entity.primary]: { in: ids },\n\t\t})\n\t\treturn await this.mapper.selectAssoc(entity, input, [], entity.primary)\n\t}\n\n\n\tprivate convertSelectionNode(node: Actions.SelectionNode, nodeName = 'root', path: string[] = []): ObjectNode<Input.ListQueryInput> {\n\t\treturn new ObjectNode(nodeName, nodeName, node.map(it => {\n\t\t\tconst [field, args, selection] = Array.isArray(it) ? it : [it, undefined, undefined]\n\t\t\tif (selection === undefined || selection.length === 0) {\n\t\t\t\treturn new FieldNode(field, field, {})\n\t\t\t}\n\t\t\treturn this.convertSelectionNode(selection, field, [...path, nodeName]).withArgs(args)\n\t\t}), {}, {}, path)\n\t}\n}\n"],"names":[],"mappings":"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"}
|