From d313f81225790c9d8e9506c3a85261d2710a4aa4 Mon Sep 17 00:00:00 2001 From: "(quasar) nebula" Date: Thu, 7 Mar 2024 10:55:48 -0400 Subject: data: withClonedThings --- src/data/composite/wiki-data/index.js | 1 + src/data/composite/wiki-data/withClonedThings.js | 68 ++++++++++++++++++++++ .../withRecontextualizedContributionList.js | 52 +++++++++-------- 3 files changed, 97 insertions(+), 24 deletions(-) create mode 100644 src/data/composite/wiki-data/withClonedThings.js (limited to 'src/data') diff --git a/src/data/composite/wiki-data/index.js b/src/data/composite/wiki-data/index.js index 9a9a5fa2..10922d72 100644 --- a/src/data/composite/wiki-data/index.js +++ b/src/data/composite/wiki-data/index.js @@ -6,6 +6,7 @@ export {default as exitWithoutContribs} from './exitWithoutContribs.js'; export {default as inputWikiData} from './inputWikiData.js'; +export {default as withClonedThings} from './withClonedThings.js'; export {default as withContributionListSums} from './withContributionListSums.js'; export {default as withDirectory} from './withDirectory.js'; export {default as withDirectoryFromName} from './withDirectoryFromName.js'; diff --git a/src/data/composite/wiki-data/withClonedThings.js b/src/data/composite/wiki-data/withClonedThings.js new file mode 100644 index 00000000..9af6aa84 --- /dev/null +++ b/src/data/composite/wiki-data/withClonedThings.js @@ -0,0 +1,68 @@ +// Clones all the things in a list. If the 'assign' input is provided, +// all new things are assigned the same specified properties. If the +// 'assignEach' input is provided, each new thing is assigned the +// corresponding properties. + +import CacheableObject from '#cacheable-object'; +import {input, templateCompositeFrom} from '#composite'; +import {isObject, sparseArrayOf} from '#validators'; + +import {withMappedList} from '#composite/data'; + +export default templateCompositeFrom({ + annotation: `withClonedThings`, + + inputs: { + things: input({type: 'array'}), + + assign: input({ + type: 'object', + defaultValue: null, + }), + + assignEach: input({ + validate: sparseArrayOf(isObject), + defaultValue: null, + }), + }, + + outputs: ['#clonedThings'], + + steps: () => [ + { + dependencies: [input('assign'), input('assignEach')], + compute: (continuation, { + [input('assign')]: assign, + [input('assignEach')]: assignEach, + }) => continuation({ + ['#assignmentMap']: + (index) => + (assign && assignEach + ? {...assignEach[index] ?? {}, ...assign} + : assignEach + ? assignEach[index] ?? {} + : assign ?? {}), + }), + }, + + { + dependencies: ['#assignmentMap'], + compute: (continuation, { + ['#assignmentMap']: assignmentMap, + }) => continuation({ + ['#cloningMap']: + (thing, index) => + Object.assign( + CacheableObject.clone(thing), + assignmentMap(index)), + }), + }, + + withMappedList({ + list: input('things'), + map: '#cloningMap', + }).outputs({ + '#mappedList': '#clonedThings', + }), + ], +}); diff --git a/src/data/composite/wiki-data/withRecontextualizedContributionList.js b/src/data/composite/wiki-data/withRecontextualizedContributionList.js index 418b346f..1c86c0ab 100644 --- a/src/data/composite/wiki-data/withRecontextualizedContributionList.js +++ b/src/data/composite/wiki-data/withRecontextualizedContributionList.js @@ -2,11 +2,10 @@ // updated to match the current thing. Overwrite the provided dependency. // Doesn't do anything if the provided dependency is null. -import CacheableObject from '#cacheable-object'; import {input, templateCompositeFrom} from '#composite'; import {raiseOutputWithoutDependency} from '#composite/control-flow'; -import {withMappedList} from '#composite/data'; +import {withClonedThings} from '#composite/wiki-data'; export default templateCompositeFrom({ annotation: `withRecontextualizedContributionList`, @@ -23,9 +22,25 @@ export default templateCompositeFrom({ }) => [list], steps: () => [ - raiseOutputWithoutDependency({ - dependency: input('list'), - }), + // TODO: Is raiseOutputWithoutDependency workable here? + // Is it true that not specifying any output wouldn't overwrite + // the provided dependency? + { + dependencies: [ + input.staticDependency('list'), + input('list'), + ], + + compute: (continuation, { + [input.staticDependency('list')]: dependency, + [input('list')]: list, + }) => + (list + ? continuation() + : continuation.raiseOutput({ + [dependency]: list, + })), + }, { dependencies: [input.myself(), input.thisProperty()], @@ -41,29 +56,18 @@ export default templateCompositeFrom({ }), }, - { - dependencies: ['#assignment'], - - compute: (continuation, { - ['#assignment']: assignment, - }) => continuation({ - ['#map']: - contrib => - Object.assign( - CacheableObject.clone(contrib), - assignment), - }), - }, - - withMappedList({ - list: input('list'), - map: '#map', + withClonedThings({ + things: input('list'), + assign: '#assignment', }).outputs({ - '#mappedList': '#newContributions', + '#clonedThings': '#newContributions', }), { - dependencies: [input.staticDependency('list'), '#newContributions'], + dependencies: [ + input.staticDependency('list'), + '#newContributions', + ], compute: (continuation, { [input.staticDependency('list')]: listDependency, -- cgit 1.3.0-6-gf8a5