« get me outta code hell

search: move from src/data/things to src root - hsmusic-wiki - HSMusic - static wiki software cataloguing collaborative creation
about summary refs log tree commit diff
path: root/src/search.js
diff options
context:
space:
mode:
author(quasar) nebula <qznebula@protonmail.com>2024-03-26 21:25:28 -0300
committer(quasar) nebula <qznebula@protonmail.com>2024-05-31 12:11:44 -0300
commitf0d003c5b33affcc4c25b06b0f0e77a2b267e6a2 (patch)
tree0bd3b4c846ba6d00f3a6170047479a6ed721c31d /src/search.js
parent62af25abcf598c1badc5cf019fb5d217c6f9ae7a (diff)
search: move from src/data/things to src root
Diffstat (limited to 'src/search.js')
-rw-r--r--src/search.js99
1 files changed, 99 insertions, 0 deletions
diff --git a/src/search.js b/src/search.js
new file mode 100644
index 00000000..7dcf5cf9
--- /dev/null
+++ b/src/search.js
@@ -0,0 +1,99 @@
+'use strict';
+
+import {mkdir, writeFile} from 'node:fs/promises';
+import * as path from 'node:path';
+
+import FlexSearch from 'flexsearch';
+
+import {logError, logInfo, logWarn} from '#cli';
+import Thing from '#thing';
+
+export async function writeSearchIndex({
+  wikiCachePath,
+  wikiData,
+}) {
+  if (!wikiCachePath) {
+    throw new Error(`Expected wikiCachePath to write into`);
+  }
+
+  // Basic flow is:
+  // 1. Define schema for type
+  // 2. Add documents to index
+  // 3. Save index to exportable json
+
+  // Copy this block directly into clientSearch.js
+  const indexes = {
+    albums: new FlexSearch.Document({
+      id: "reference",
+      index: ["name", "groups"],
+    }),
+
+    tracks: new FlexSearch.Document({
+      id: "reference",
+      index: ["track", "album", "artists", "directory", "additionalNames"],
+    }),
+
+    artists: new FlexSearch.Document({
+      id: "reference",
+      index: ["names"],
+    }),
+  };
+
+  for (const album of wikiData.albumData) {
+    indexes.albums.add({
+      reference: Thing.getReference(album),
+      name: album.name,
+      groups: album.groups.map(group => group.name),
+    });
+
+    for (const track of album.tracks) {
+      indexes.tracks.add({
+        reference: Thing.getReference(track),
+        album: album.name,
+        track: track.name,
+
+        artists: [
+          track.artistContribs.map(contrib => contrib.artist.name),
+          ...track.artistContribs.map(contrib => contrib.artist.aliasNames)
+        ],
+
+        additionalNames:
+          track.additionalNames.map(entry => entry.name),
+      });
+    }
+  }
+
+  for (const artist of wikiData.artistData) {
+    if (artist.isAlias) {
+      continue;
+    }
+
+    indexes.artists.add({
+      reference: Thing.getReference(artist),
+      names: [artist.name, ...artist.aliasNames],
+    });
+  }
+
+  // Export indexes to json
+  const searchData = {}
+
+  await Promise.all(
+    Object.entries(indexes)
+      .map(([indexName, index]) => {
+        searchData[indexName] = {};
+        return index.export((key, data) => {
+          searchData[indexName][key] = data
+        });
+      }));
+
+  const outputDirectory =
+    path.join(wikiCachePath, 'search');
+
+  const outputFile =
+    path.join(outputDirectory, 'index.json');
+
+  await mkdir(outputDirectory, {recursive: true});
+  await writeFile(outputFile, JSON.stringify(searchData));
+
+  logInfo`Search index successfully written.`;
+}