feat(cli): add sidebar icons mapping for topics

This commit is contained in:
Prad Nukala committed 2026-09-24 14:45:09 -04:00
1 parent f0f479d6cf
commit c69582552b
1 file changed
+48 -4
+48 -4
View File
@@ -181,6 +181,45 @@ const TOPIC_ALIASES: Record<string, string> = {
"Hash-Based Lookup": "Hash Table",
};
/**
* Sidebar icon per group, keyed by the (post-alias) topic name — the same key an
* unplanned problem's category group uses, so `Stack` the category and `Stack`
* the topic share one row. Lucide names; Blume resolves them at build time and
* reports a diagnostic for a typo, but an unmapped group is caught here first.
*/
const TOPIC_ICONS: Record<string, string> = {
// README topics, in curriculum order
"Hash Table": "hash",
"Prefix Sum": "sigma",
"Two Pointers": "arrow-left-right",
"Sliding Window": "app-window",
"Binary Search": "search",
Stack: "layers",
"Monotonic Stack": "trending-up",
"Linked List": "link",
"Hybrid Structures": "combine",
"Matrix Index Math": "grid-3x3",
"Tree DFS": "folder-tree",
"Tree BFS": "network",
"Binary Search Tree": "git-fork",
"Heap / Priority Queue": "triangle",
Trie: "spell-check",
"Graph DFS": "waypoints",
"Graph BFS": "radar",
"Topological Sort": "workflow",
"Union-Find": "merge",
Backtracking: "undo-2",
"1-D Dynamic Programming": "columns-3",
"Multi-D / Grid DP": "table",
Greedy: "coins",
Intervals: "calendar-range",
// work/1 categories that can surface as an unplanned group
Array: "brackets",
String: "type",
Tree: "network",
"Depth-First Search": "folder-tree",
};
/** LC number -> topic. A problem listed under two topics keeps the first. */
async function readmeTopics(): Promise<Map<number, Topic>> {
const md = await Bun.file(join(ROOT, "README.md")).text();
@@ -197,12 +236,17 @@ async function readmeTopics(): Promise<Map<number, Topic>> {
}
/**
* Blume folder meta: exact topic label (the folder slug loses `/` and case) and
* curriculum order. An unplanned category group (warm-ups) has no README
* number and sorts at 0, ahead of topic 1, so the sidebar opens on the basics.
* Blume folder meta: exact topic label (the folder slug loses `/` and case),
* curriculum order, and the group's sidebar icon. An unplanned category group
* (warm-ups) has no README number and sorts at 0, ahead of topic 1, so the
* sidebar opens on the basics.
*/
function groupMeta(topic: Topic): string {
return `import { defineMeta } from "blume";\n\nexport default defineMeta({ title: ${JSON.stringify(topic.name)}, order: ${topic.order ?? 0} });\n`;
const icon = TOPIC_ICONS[topic.name];
if (!icon) console.warn(`no icon for group ${JSON.stringify(topic.name)}: add it to TOPIC_ICONS`);
const fields = [`title: ${JSON.stringify(topic.name)}`, `order: ${topic.order ?? 0}`];
if (icon) fields.push(`icon: ${JSON.stringify(icon)}`);
return `import { defineMeta } from "blume";\n\nexport default defineMeta({ ${fields.join(", ")} });\n`;
}
// ── inline-code formatting heuristics ────────────────────────────