« get me outta code hell

infra, test: new stubContentFunction utility - hsmusic-wiki - HSMusic - static wiki software cataloguing collaborative creation
about summary refs log tree commit diff
path: root/test/lib
diff options
context:
space:
mode:
author(quasar) nebula <qznebula@protonmail.com>2023-09-05 19:39:51 -0300
committer(quasar) nebula <qznebula@protonmail.com>2023-09-05 20:11:18 -0300
commitae1131e54280da63a678eb3489b02a9fb292ee8b (patch)
tree0aa5a9b069bdb5e62d526e9e743d0240d0d537df /test/lib
parentddaf34d6e97269719107398569716fc1f1e98073 (diff)
infra, test: new stubContentFunction utility
Just like stubTemplate, but the result is ready for passing to
evaluate.load's {mock} option, and the template's content is
formatted to include the content function's provided arguments
as well.
Diffstat (limited to 'test/lib')
-rw-r--r--test/lib/content-function.js109
1 files changed, 78 insertions, 31 deletions
diff --git a/test/lib/content-function.js b/test/lib/content-function.js
index b706cd8..5cb499b 100644
--- a/test/lib/content-function.js
+++ b/test/lib/content-function.js
@@ -91,45 +91,92 @@ export function testContentFunctions(t, message, fn) {
       t.matchSnapshot(result, description);
     };
 
-    evaluate.stubTemplate = name => {
+    evaluate.stubTemplate = name =>
       // Creates a particularly permissable template, allowing any slot values
       // to be stored and just outputting the contents of those slots as-are.
+      _stubTemplate(name, false);
 
-      return new (class extends html.Template {
-        #slotValues = {};
+    evaluate.stubContentFunction = name =>
+      // Like stubTemplate, but instead of a template directly, returns
+      // an object describing a content function - suitable for passing
+      // into evaluate.mock.
+      _stubTemplate(name, true);
 
-        constructor() {
-          super({
-            content: () => this.#getContent(this),
-          });
-        }
-
-        setSlots(slotNamesToValues) {
-          Object.assign(this.#slotValues, slotNamesToValues);
-        }
+    const _stubTemplate = (name, mockContentFunction) => {
+      const inspectNicely = (value, opts = {}) =>
+        inspect(value, {
+          ...opts,
+          colors: false,
+          sort: true,
+        });
 
-        setSlot(slotName, slotValue) {
-          this.#slotValues[slotName] = slotValue;
-        }
+      const makeTemplate = formatContentFn =>
+        new (class extends html.Template {
+          #slotValues = {};
 
-        #getContent() {
-          const toInspect =
-            Object.fromEntries(
-              Object.entries(this.#slotValues)
-                .filter(([key, value]) => value !== null));
-
-          const inspected =
-            inspect(toInspect, {
-              breakLength: Infinity,
-              colors: false,
-              compact: true,
-              depth: Infinity,
-              sort: true,
+          constructor() {
+            super({
+              content: () => this.#getContent(formatContentFn),
             });
+          }
 
-          return `${name}: ${inspected}`;
-        }
-      });
+          setSlots(slotNamesToValues) {
+            Object.assign(this.#slotValues, slotNamesToValues);
+          }
+
+          setSlot(slotName, slotValue) {
+            this.#slotValues[slotName] = slotValue;
+          }
+
+          #getContent(formatContentFn) {
+            const toInspect =
+              Object.fromEntries(
+                Object.entries(this.#slotValues)
+                  .filter(([key, value]) => value !== null));
+
+            const inspected =
+              inspectNicely(toInspect, {
+                breakLength: Infinity,
+                compact: true,
+                depth: Infinity,
+              });
+
+            return formatContentFn(inspected); `${name}: ${inspected}`;
+          }
+        });
+
+      if (mockContentFunction) {
+        return {
+          data: (...args) => ({args}),
+          generate: (data) =>
+            makeTemplate(slots => {
+              const argsLines =
+                (empty(data.args)
+                  ? []
+                  : inspectNicely(data.args, {depth: Infinity})
+                      .split('\n'));
+
+              return (`[mocked: ${name}` +
+
+                (empty(data.args)
+                  ? ``
+               : argsLines.length === 1
+                  ? `\n args: ${argsLines[0]}`
+                  : `\n args: ${argsLines[0]}\n` +
+                    argsLines.slice(1).join('\n').replace(/^/gm, ' ')) +
+
+                (!empty(data.args)
+                  ? `\n `
+                  : ` - `) +
+
+                (slots
+                  ? `slots: ${slots}]`
+                  : `slots: none]`));
+            }),
+        };
+      } else {
+        return makeTemplate(slots => `${name}: ${slots}`);
+      }
     };
 
     evaluate.mock = (...opts) => {