« get me outta code hell

data: Language: chop withStrings - hsmusic-wiki - HSMusic - static wiki software cataloguing collaborative creation
about summary refs log tree commit diff
diff options
context:
space:
mode:
author(quasar) nebula <qznebula@protonmail.com>2025-11-27 17:36:06 -0400
committer(quasar) nebula <qznebula@protonmail.com>2025-11-27 17:36:06 -0400
commitd08cb46607d19326cb4021a26fc9c8a20a6ae6d7 (patch)
tree43249378821d1a97f2671c145f2a516969bee9d0
parent112cf48c3877e35a6fd41fc613c33cc46eaf719d (diff)
data: Language: chop withStrings
-rw-r--r--package.json1
-rw-r--r--src/data/composite/things/language/index.js1
-rw-r--r--src/data/composite/things/language/withStrings.js111
-rw-r--r--src/data/things/language.js73
4 files changed, 57 insertions, 129 deletions
diff --git a/package.json b/package.json
index ea370a1c..34ed337e 100644
--- a/package.json
+++ b/package.json
@@ -23,7 +23,6 @@
         "#composite/things/artwork": "./src/data/composite/things/artwork/index.js",
         "#composite/things/content": "./src/data/composite/things/content/index.js",
         "#composite/things/contribution": "./src/data/composite/things/contribution/index.js",
-        "#composite/things/language": "./src/data/composite/things/language/index.js",
         "#composite/things/track": "./src/data/composite/things/track/index.js",
         "#content-dependencies": "./src/content/dependencies/index.js",
         "#content-function": "./src/content-function.js",
diff --git a/src/data/composite/things/language/index.js b/src/data/composite/things/language/index.js
deleted file mode 100644
index f22cdaf6..00000000
--- a/src/data/composite/things/language/index.js
+++ /dev/null
@@ -1 +0,0 @@
-export {default as withStrings} from './withStrings.js';
diff --git a/src/data/composite/things/language/withStrings.js b/src/data/composite/things/language/withStrings.js
deleted file mode 100644
index 20782905..00000000
--- a/src/data/composite/things/language/withStrings.js
+++ /dev/null
@@ -1,111 +0,0 @@
-import {logWarn} from '#cli';
-import {input, templateCompositeFrom} from '#composite';
-import {empty} from '#sugar';
-import {languageOptionRegex} from '#wiki-data';
-
-import {withResultOfAvailabilityCheck} from '#composite/control-flow';
-
-export default templateCompositeFrom({
-  annotation: `withStrings`,
-
-  inputs: {
-    from: input({defaultDependency: '_strings'}),
-  },
-
-  outputs: ['#strings'],
-
-  steps: () => [
-    withResultOfAvailabilityCheck({
-      from: input('from'),
-    }).outputs({
-      '#availability': '#stringsAvailability',
-    }),
-
-    withResultOfAvailabilityCheck({
-      from: 'inheritedStrings',
-    }).outputs({
-      '#availability': '#inheritedStringsAvailability',
-    }),
-
-    {
-      dependencies: [
-        '#stringsAvailability',
-        '#inheritedStringsAvailability',
-      ],
-
-      compute: (continuation, {
-        ['#stringsAvailability']: stringsAvailability,
-        ['#inheritedStringsAvailability']: inheritedStringsAvailability,
-      }) =>
-        (stringsAvailability || inheritedStringsAvailability
-          ? continuation()
-          : continuation.raiseOutput({'#strings': null})),
-    },
-
-    {
-      dependencies: [input('from'), '#inheritedStringsAvailability'],
-      compute: (continuation, {
-        [input('from')]: strings,
-        ['#inheritedStringsAvailability']: inheritedStringsAvailability,
-      }) =>
-        (inheritedStringsAvailability
-          ? continuation()
-          : continuation.raiseOutput({'#strings': strings})),
-    },
-
-    {
-      dependencies: ['inheritedStrings', '#stringsAvailability'],
-      compute: (continuation, {
-        ['inheritedStrings']: inheritedStrings,
-        ['#stringsAvailability']: stringsAvailability,
-      }) =>
-        (stringsAvailability
-          ? continuation()
-          : continuation.raiseOutput({'#strings': inheritedStrings})),
-    },
-
-    {
-      dependencies: [input('from'), 'inheritedStrings', 'code'],
-      compute(continuation, {
-        [input('from')]: strings,
-        ['inheritedStrings']: inheritedStrings,
-        ['code']: code,
-      }) {
-        const validStrings = {
-          ...inheritedStrings,
-          ...strings,
-        };
-
-        const optionsFromTemplate = template =>
-          Array.from(template.matchAll(languageOptionRegex))
-            .map(({groups}) => groups.name);
-
-        for (const [key, providedTemplate] of Object.entries(strings)) {
-          const inheritedTemplate = inheritedStrings[key];
-          if (!inheritedTemplate) continue;
-
-          const providedOptions = optionsFromTemplate(providedTemplate);
-          const inheritedOptions = optionsFromTemplate(inheritedTemplate);
-
-          const missingOptionNames =
-            inheritedOptions.filter(name => !providedOptions.includes(name));
-
-          const misplacedOptionNames =
-            providedOptions.filter(name => !inheritedOptions.includes(name));
-
-          if (!empty(missingOptionNames) || !empty(misplacedOptionNames)) {
-            logWarn`Not using ${code ?? '(no code)'} string ${key}:`;
-            if (!empty(missingOptionNames))
-              logWarn`- Missing options: ${missingOptionNames.join(', ')}`;
-            if (!empty(misplacedOptionNames))
-              logWarn`- Unexpected options: ${misplacedOptionNames.join(', ')}`;
-
-            validStrings[key] = inheritedStrings[key];
-          }
-        }
-
-        return continuation({'#strings': validStrings});
-      },
-    },
-  ],
-});
diff --git a/src/data/things/language.js b/src/data/things/language.js
index 1fa72def..afda258c 100644
--- a/src/data/things/language.js
+++ b/src/data/things/language.js
@@ -4,7 +4,7 @@ import {withAggregate} from '#aggregate';
 import {input} from '#composite';
 import * as html from '#html';
 import {accumulateSum, empty, withEntries} from '#sugar';
-import {isLanguageCode} from '#validators';
+import {isLanguageCode, isObject} from '#validators';
 import Thing from '#thing';
 import {languageOptionRegex} from '#wiki-data';
 
@@ -20,8 +20,6 @@ import {exitWithoutDependency, exposeConstant, exposeDependency}
   from '#composite/control-flow';
 import {flag, name} from '#composite/wiki-properties';
 
-import {withStrings} from '#composite/things/language';
-
 export class Language extends Thing {
   static [Thing.getPropertyDescriptors] = () => ({
     // Update & expose
@@ -63,15 +61,60 @@ export class Language extends Thing {
     // Mapping of translation keys to values (strings). Generally, don't
     // access this object directly - use methods instead.
     strings: [
-      withStrings({
-        from: input.updateValue({
-          validate: t => typeof t === 'object',
-        }),
-      }),
+      {
+        dependencies: [
+          input.updateValue({validate: isObject}),
+          'inheritedStrings',
+        ],
+
+        compute: (continuation, {
+          [input.updateValue()]: strings,
+          ['inheritedStrings']: inheritedStrings,
+        }) =>
+          (strings && inheritedStrings
+            ? continuation()
+            : strings ?? inheritedStrings),
+      },
 
-      exposeDependency({
-        dependency: '#strings',
-      }),
+      {
+        dependencies: ['inheritedStrings', 'code'],
+        transform(strings, {inheritedStrings, code}) {
+          const validStrings = {
+            ...inheritedStrings,
+            ...strings,
+          };
+
+          const optionsFromTemplate = template =>
+            Array.from(template.matchAll(languageOptionRegex))
+              .map(({groups}) => groups.name);
+
+          for (const [key, providedTemplate] of Object.entries(strings)) {
+            const inheritedTemplate = inheritedStrings[key];
+            if (!inheritedTemplate) continue;
+
+            const providedOptions = optionsFromTemplate(providedTemplate);
+            const inheritedOptions = optionsFromTemplate(inheritedTemplate);
+
+            const missingOptionNames =
+              inheritedOptions.filter(name => !providedOptions.includes(name));
+
+            const misplacedOptionNames =
+              providedOptions.filter(name => !inheritedOptions.includes(name));
+
+            if (!empty(missingOptionNames) || !empty(misplacedOptionNames)) {
+              logWarn`Not using ${code ?? '(no code)'} string ${key}:`;
+              if (!empty(missingOptionNames))
+                logWarn`- Missing options: ${missingOptionNames.join(', ')}`;
+              if (!empty(misplacedOptionNames))
+                logWarn`- Unexpected options: ${misplacedOptionNames.join(', ')}`;
+
+              validStrings[key] = inheritedStrings[key];
+            }
+          }
+
+          return validStrings;
+        },
+      },
     ],
 
     // May be provided to specify "default" strings, generally (but not
@@ -124,15 +167,13 @@ export class Language extends Thing {
 
     // TODO: This currently isn't used. Is it still needed?
     strings_htmlEscaped: [
-      withStrings(),
-
       exitWithoutDependency({
-        dependency: '#strings',
+        dependency: 'strings',
       }),
 
       {
-        dependencies: ['#strings'],
-        compute: ({'#strings': strings}) =>
+        dependencies: ['strings'],
+        compute: ({strings}) =>
           withEntries(strings, entries => entries
             .map(([key, value]) => [key, html.escape(value)])),
       },