@czi-sds/mcp 0.16.0 → 0.17.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (164) hide show
  1. package/README.md +2 -1
  2. package/data/component-docs/Accordion.md +291 -0
  3. package/data/component-docs/Autocomplete.md +525 -0
  4. package/data/component-docs/Banner.md +231 -0
  5. package/data/component-docs/Button.md +224 -0
  6. package/data/component-docs/ButtonDropdown.md +256 -0
  7. package/data/component-docs/ButtonGroup.md +320 -0
  8. package/data/component-docs/ButtonToggle.md +397 -0
  9. package/data/component-docs/Callout.md +268 -0
  10. package/data/component-docs/CellBasic.md +122 -0
  11. package/data/component-docs/CellComponent.md +63 -0
  12. package/data/component-docs/CellHeader.md +128 -0
  13. package/data/component-docs/ComplexFilter.md +294 -0
  14. package/data/component-docs/ContentCard.md +406 -0
  15. package/data/component-docs/Dialog.md +651 -0
  16. package/data/component-docs/Dropdown.md +155 -0
  17. package/data/component-docs/DropdownMenu.md +949 -0
  18. package/data/component-docs/HeatmapChart.md +782 -0
  19. package/data/component-docs/Hero.md +363 -0
  20. package/data/component-docs/Icon.md +283 -0
  21. package/data/component-docs/InputCheckbox.md +205 -0
  22. package/data/component-docs/InputDropdown.md +482 -0
  23. package/data/component-docs/InputRadio.md +173 -0
  24. package/data/component-docs/InputSearch.md +81 -0
  25. package/data/component-docs/InputSlider.md +189 -0
  26. package/data/component-docs/InputText.md +110 -0
  27. package/data/component-docs/InputToggle.md +141 -0
  28. package/data/component-docs/IntentMessage.md +293 -0
  29. package/data/component-docs/Legend.md +442 -0
  30. package/data/component-docs/Link.md +23 -0
  31. package/data/component-docs/List.md +300 -0
  32. package/data/component-docs/LoadingIndicator.md +198 -0
  33. package/data/component-docs/Menu.md +298 -0
  34. package/data/component-docs/MenuItem.md +100 -0
  35. package/data/component-docs/NavigationFooter.md +165 -0
  36. package/data/component-docs/NavigationHeader.md +500 -0
  37. package/data/component-docs/NavigationJumpTo.md +414 -0
  38. package/data/component-docs/Notification.md +288 -0
  39. package/data/component-docs/Pagination.md +67 -0
  40. package/data/component-docs/Panel.md +636 -0
  41. package/data/component-docs/Popover.md +448 -0
  42. package/data/component-docs/PreComposedTable.md +2947 -0
  43. package/data/component-docs/SegmentedControl.md +396 -0
  44. package/data/component-docs/StackedBarChart.md +475 -0
  45. package/data/component-docs/Table.md +2000 -0
  46. package/data/component-docs/TableHeader.md +53 -0
  47. package/data/component-docs/TableRow.md +74 -0
  48. package/data/component-docs/Tabs.md +455 -0
  49. package/data/component-docs/Tag.md +647 -0
  50. package/data/component-docs/TagFilter.md +131 -0
  51. package/data/component-docs/Tooltip.md +561 -0
  52. package/data/component-docs/TooltipCondensed.md +203 -0
  53. package/data/component-docs/TooltipTable.md +145 -0
  54. package/data/component-docs/index.json +262 -0
  55. package/data/component-list.json +2 -5
  56. package/data/component-props/Accordion.json +31 -11
  57. package/data/component-props/Alert.json +3 -3
  58. package/data/component-props/Autocomplete.json +150 -15
  59. package/data/component-props/Banner.json +31 -17
  60. package/data/component-props/Button.json +45 -20
  61. package/data/component-props/ButtonDropdown.json +36 -17
  62. package/data/component-props/ButtonDropdownLegacy.json +11 -11
  63. package/data/component-props/ButtonGroup.json +32 -11
  64. package/data/component-props/ButtonIcon.json +10 -10
  65. package/data/component-props/ButtonLegacy.json +19 -19
  66. package/data/component-props/ButtonToggle.json +32 -19
  67. package/data/component-props/ButtonToggleLegacy.json +11 -11
  68. package/data/component-props/Callout.json +58 -17
  69. package/data/component-props/CellBasic.json +94 -41
  70. package/data/component-props/CellComponent.json +23 -7
  71. package/data/component-props/CellHeader.json +62 -19
  72. package/data/component-props/ComplexFilter.json +52 -21
  73. package/data/component-props/ContentCard.json +70 -47
  74. package/data/component-props/Dialog.json +47 -14
  75. package/data/component-props/Dropdown.json +68 -31
  76. package/data/component-props/DropdownMenu.json +128 -23
  77. package/data/component-props/HeatmapChart.json +88 -12
  78. package/data/component-props/Hero.json +80 -39
  79. package/data/component-props/Icon.json +20 -9
  80. package/data/component-props/InputCheckbox.json +36 -14
  81. package/data/component-props/InputDropdown.json +75 -27
  82. package/data/component-props/InputRadio.json +31 -13
  83. package/data/component-props/InputSearch.json +41 -18
  84. package/data/component-props/InputSlider.json +46 -19
  85. package/data/component-props/InputText.json +26 -19
  86. package/data/component-props/InputToggle.json +26 -9
  87. package/data/component-props/IntentMessage.json +38 -9
  88. package/data/component-props/Link.json +13 -7
  89. package/data/component-props/LoadingIndicator.json +11 -3
  90. package/data/component-props/MenuItem.json +38 -19
  91. package/data/component-props/MenuSelect.json +8 -8
  92. package/data/component-props/NavigationFooter.json +49 -19
  93. package/data/component-props/NavigationHeader.json +150 -37
  94. package/data/component-props/NavigationJumpTo.json +33 -7
  95. package/data/component-props/Notification.json +39 -21
  96. package/data/component-props/Pagination.json +39 -11
  97. package/data/component-props/Panel.json +62 -9
  98. package/data/component-props/Popover.json +80 -7
  99. package/data/component-props/PreComposedTable.json +99 -27
  100. package/data/component-props/SegmentedControl.json +42 -3
  101. package/data/component-props/StackedBarChart.json +116 -42
  102. package/data/component-props/TableRow.json +38 -19
  103. package/data/component-props/Tabs.json +66 -9
  104. package/data/component-props/Tag.json +34 -17
  105. package/data/component-props/TagFilter.json +10 -3
  106. package/data/component-props/Tooltip.json +49 -18
  107. package/data/component-props/TooltipCondensed.json +18 -9
  108. package/data/component-props/TooltipTable.json +17 -7
  109. package/data/resources/{zeroheight-rules.md → documentation-rules.md} +43 -30
  110. package/data/resources/figma-rules.md +2 -2
  111. package/dist/stdio.js +112 -208
  112. package/package.json +9 -5
  113. package/data/component-props/ButtonDropdownV2.json +0 -34
  114. package/data/component-props/ButtonNew.json +0 -47
  115. package/data/component-props/ButtonToggleV2.json +0 -44
  116. package/data/component-props/ButtonV2.json +0 -43
  117. package/data/zeroheight-cache.json +0 -10259
  118. package/data/zeroheight-exports/Accordion.md +0 -774
  119. package/data/zeroheight-exports/Banner.md +0 -691
  120. package/data/zeroheight-exports/Borders.md +0 -117
  121. package/data/zeroheight-exports/Buttons.md +0 -1854
  122. package/data/zeroheight-exports/Callout.md +0 -931
  123. package/data/zeroheight-exports/Colors.md +0 -1755
  124. package/data/zeroheight-exports/Content-Card.md +0 -309
  125. package/data/zeroheight-exports/Contributing-to-SDS.md +0 -98
  126. package/data/zeroheight-exports/Control-Inputs.md +0 -2818
  127. package/data/zeroheight-exports/Corners.md +0 -104
  128. package/data/zeroheight-exports/Cover-page.md +0 -3
  129. package/data/zeroheight-exports/Dialog.md +0 -1367
  130. package/data/zeroheight-exports/Downloads.md +0 -236
  131. package/data/zeroheight-exports/Drop-Shadows.md +0 -79
  132. package/data/zeroheight-exports/Dropdown-Input.md +0 -1776
  133. package/data/zeroheight-exports/Dropdown-Menus.md +0 -913
  134. package/data/zeroheight-exports/Element-Status-Tracker.md +0 -267
  135. package/data/zeroheight-exports/Field-Inputs.md +0 -1405
  136. package/data/zeroheight-exports/Filters.md +0 -1111
  137. package/data/zeroheight-exports/Getting-Started.md +0 -1157
  138. package/data/zeroheight-exports/Hero.md +0 -414
  139. package/data/zeroheight-exports/Icons.md +0 -2067
  140. package/data/zeroheight-exports/Intent.md +0 -86
  141. package/data/zeroheight-exports/Introduction-to-Bases.md +0 -35
  142. package/data/zeroheight-exports/Introduction-to-Cells.md +0 -35
  143. package/data/zeroheight-exports/Introduction-to-DNA.md +0 -35
  144. package/data/zeroheight-exports/Introduction-to-Genes.md +0 -35
  145. package/data/zeroheight-exports/Introduction.md +0 -115
  146. package/data/zeroheight-exports/Link.md +0 -432
  147. package/data/zeroheight-exports/Lists.md +0 -986
  148. package/data/zeroheight-exports/Loading-Indicator.md +0 -41
  149. package/data/zeroheight-exports/Navigation.md +0 -1190
  150. package/data/zeroheight-exports/Notification.md +0 -1038
  151. package/data/zeroheight-exports/Panel.md +0 -1030
  152. package/data/zeroheight-exports/README.md +0 -122
  153. package/data/zeroheight-exports/Responsive-Design.md +0 -330
  154. package/data/zeroheight-exports/Search-Input.md +0 -91
  155. package/data/zeroheight-exports/Search.md +0 -822
  156. package/data/zeroheight-exports/Segmented-Control.md +0 -609
  157. package/data/zeroheight-exports/Spacing.md +0 -297
  158. package/data/zeroheight-exports/Table.md +0 -5345
  159. package/data/zeroheight-exports/Tabs.md +0 -1324
  160. package/data/zeroheight-exports/Tags.md +0 -1545
  161. package/data/zeroheight-exports/Text-Link.md +0 -268
  162. package/data/zeroheight-exports/Theming.md +0 -362
  163. package/data/zeroheight-exports/Tooltips.md +0 -2015
  164. package/data/zeroheight-exports/Typography.md +0 -800
package/dist/stdio.js CHANGED
@@ -20,70 +20,73 @@ const server = new McpServer({
20
20
  });
21
21
  //#endregion
22
22
  //#region src/lib/fetch.ts
23
- const filename$1 = fileURLToPath(import.meta.url);
24
- const dirname$2 = path.dirname(filename$1);
23
+ const filename = fileURLToPath(import.meta.url);
24
+ const dirname$1 = path.dirname(filename);
25
+ /**
26
+ * Locates a file under `data/`. The server runs both from source via tsx and
27
+ * from the bundle in `dist/`, which sit at different depths, and may also be
28
+ * started from the package root.
29
+ */
30
+ function resolveDataPath(relativePath) {
31
+ return [
32
+ path.join(dirname$1, "../../data", relativePath),
33
+ path.join(dirname$1, "../data", relativePath),
34
+ path.join(process.cwd(), "data", relativePath)
35
+ ].find((candidate) => fs.existsSync(candidate)) ?? null;
36
+ }
37
+ function readDataFile(relativePath, missingHint) {
38
+ const dataPath = resolveDataPath(relativePath);
39
+ if (!dataPath) throw new Error(`${relativePath} not found in any expected location. ${missingHint}`);
40
+ return fs.readFileSync(dataPath, "utf-8");
41
+ }
25
42
  /**
26
43
  * Gets all component names from both packages
27
44
  */
28
45
  async function getAllComponentNames() {
29
46
  try {
30
- const possiblePaths = [
31
- path.join(dirname$2, "../../data/component-list.json"),
32
- path.join(dirname$2, "../data/component-list.json"),
33
- path.join(process.cwd(), "data/component-list.json")
34
- ];
35
- let dataPath = "";
36
- for (const p of possiblePaths) if (fs.existsSync(p)) {
37
- dataPath = p;
38
- break;
39
- }
40
- if (!dataPath) throw new Error("Component list not found in any expected location. Please run 'yarn generate:components-list' first.");
41
- const fileContent = fs.readFileSync(dataPath, "utf-8");
42
- return JSON.parse(fileContent);
47
+ return JSON.parse(readDataFile("component-list.json", "Please run 'yarn generate:components-list' first."));
43
48
  } catch (error) {
44
49
  throw new Error(`Failed to load component list: ${error instanceof Error ? error.message : `Unknown error ${error}`}`);
45
50
  }
46
51
  }
47
52
  async function fetchComponentProps(component) {
48
53
  try {
49
- const propsPaths = [
50
- path.join(dirname$2, `../../data/component-props/${component}.json`),
51
- path.join(dirname$2, `../data/component-props/${component}.json`),
52
- path.join(process.cwd(), `data/component-props/${component}.json`)
53
- ];
54
- let propsPath = "";
55
- for (const p of propsPaths) if (fs.existsSync(p)) {
56
- propsPath = p;
57
- break;
58
- }
54
+ const propsPath = resolveDataPath(`component-props/${component}.json`);
59
55
  if (!propsPath) return { [component]: {
60
56
  message: "Props information not available for this component. Run 'yarn generate:component-props' to generate props data.",
61
57
  props: {}
62
58
  } };
63
- const fileContent = fs.readFileSync(propsPath, "utf-8");
64
- return JSON.parse(fileContent);
59
+ return JSON.parse(fs.readFileSync(propsPath, "utf-8"));
65
60
  } catch (error) {
66
61
  throw new Error(`Failed to load props for ${component}: ${error instanceof Error ? error.message : "Unknown error"}`);
67
62
  }
68
63
  }
69
64
  /**
65
+ * Gets the index of components that have generated documentation
66
+ */
67
+ async function getComponentDocsIndex() {
68
+ try {
69
+ return JSON.parse(readDataFile("component-docs/index.json", "Please run 'yarn generate:component-docs' first."));
70
+ } catch (error) {
71
+ throw new Error(`Failed to load component docs index: ${error instanceof Error ? error.message : `Unknown error ${error}`}`);
72
+ }
73
+ }
74
+ /**
75
+ * Fetches the generated documentation markdown for a specific component
76
+ */
77
+ async function fetchComponentDocs(file) {
78
+ try {
79
+ return readDataFile(`component-docs/${file}`, "Please run 'yarn generate:component-docs' first.");
80
+ } catch (error) {
81
+ throw new Error(`Failed to load documentation from ${file}: ${error instanceof Error ? error.message : "Unknown error"}`);
82
+ }
83
+ }
84
+ /**
70
85
  * Gets all component names from both packages
71
86
  */
72
87
  async function fetchTailwindTokens() {
73
88
  try {
74
- const possiblePaths = [
75
- path.join(dirname$2, "../../data/tailwind.json"),
76
- path.join(dirname$2, "../data/tailwind.json"),
77
- path.join(process.cwd(), "data/tailwind.json")
78
- ];
79
- let dataPath = "";
80
- for (const p of possiblePaths) if (fs.existsSync(p)) {
81
- dataPath = p;
82
- break;
83
- }
84
- if (!dataPath) throw new Error("Component list not found in any expected location. Please run 'yarn generate:tailwind-tokens' first.");
85
- const fileContent = fs.readFileSync(dataPath, "utf-8");
86
- return JSON.parse(fileContent);
89
+ return JSON.parse(readDataFile("tailwind.json", "Please run 'yarn generate:tailwind-tokens' first."));
87
90
  } catch (error) {
88
91
  throw new Error(`Failed to load tailwind tokens: ${error instanceof Error ? error.message : `Unknown error ${error}`}`);
89
92
  }
@@ -396,199 +399,100 @@ colors: This category can be used for formatting colors in the tailwind.config.j
396
399
  return output;
397
400
  }
398
401
  //#endregion
399
- //#region src/tools/get-tailwind-tokens.ts
400
- const getTailwindTokensTool = {
401
- name: "get_tailwind_tokens",
402
- description: "Get all available Tailwind tokens from the SDS design system. Available design tokens include fontFamily, fontSize, fontVariantNumeric, letterSpacing, lineHeight, textDecoration, textTransform, typography, height, width, borderRadius, boxShadow, breakpoints, colors, spacing, and more.",
403
- async ctx() {
404
- try {
405
- return { tailwindTokens: await fetchTailwindTokens() };
406
- } catch (error) {
407
- throw new Error(`Failed to initialize tailwind tokens tool: ${error instanceof Error ? error.message : "Unknown error"}`);
408
- }
409
- },
410
- exec(server, { ctx, name, description }) {
411
- server.tool(name, description, { category: z.enum([
412
- "all",
413
- "fontFamily",
414
- "fontSize",
415
- "fontVariantNumeric",
416
- "letterSpacing",
417
- "lineHeight",
418
- "textDecoration",
419
- "textTransform",
420
- "typography",
421
- "height",
422
- "width",
423
- "borderRadius",
424
- "boxShadow",
425
- "breakpoints",
426
- "colors",
427
- "spacing"
428
- ]).optional().describe("Optional category of tokens to retrieve. If not specified, returns all tokens.") }, async ({ category }) => {
429
- try {
430
- const tokens = ctx.tailwindTokens;
431
- let result;
432
- if (!category || category === "all") result = tokens;
433
- else result = tokens[category] || {};
434
- const responseContent = [];
435
- const guidance = getTokenGuidance(category);
436
- responseContent.push({
437
- type: "text",
438
- text: guidance
439
- });
440
- responseContent.push({
441
- type: "text",
442
- text: JSON.stringify(result, null, 2)
443
- });
444
- return { content: responseContent };
445
- } catch (error) {
446
- return { content: [{
447
- type: "text",
448
- text: `Failed to get Tailwind tokens: ${error instanceof Error ? error.message : "Unknown error"}`
449
- }] };
450
- }
451
- });
452
- }
453
- };
454
- //#endregion
455
- //#region src/tools/get-component-docs.ts
456
- const filename = fileURLToPath(import.meta.url);
457
- const dirname$1 = path.dirname(filename);
458
- /**
459
- * Maps a component name to the corresponding Zeroheight file using manual mapping
460
- */
461
- function mapComponentToFile(componentName, exportedFiles) {
462
- const mappedFile = {
463
- Button: "Buttons",
464
- ButtonDropdown: "Buttons",
465
- ButtonIcon: "Buttons",
466
- ButtonToggle: "Buttons",
467
- TableHeader: "Table",
468
- TableRow: "Table",
469
- InputCheckbox: "Control-Inputs",
470
- InputRadio: "Control-Inputs",
471
- InputToggle: "Control-Inputs",
472
- InputText: "Field-Inputs",
473
- InputDropdown: "Dropdown-Input",
474
- InputSearch: "Search-Input",
475
- InputSlider: "Control-Inputs",
476
- Dropdown: "Dropdown-Menu",
477
- DropdownMenu: "Dropdown-Menu",
478
- ContentCard: "Content-Card",
479
- LoadingIndicator: "Loading-Indicator",
480
- NavigationFooter: "Navigation",
481
- NavigationHeader: "Navigation",
482
- NavigationJumpTo: "Navigation",
483
- SegmentedControl: "Segmented-Control",
484
- List: "Lists",
485
- Menu: "Dropdown-Menu",
486
- MenuItem: "Dropdown-Menu",
487
- MenuSelect: "Dropdown-Menu",
488
- Tag: "Tags",
489
- TagFilter: "Tags",
490
- Tooltip: "Tooltips",
491
- TooltipCondensed: "Tooltips",
492
- TooltipTable: "Tooltips",
493
- CellBasic: "Table",
494
- CellComponent: "Table",
495
- CellHeader: "Table",
496
- ComplexFilter: "Filters",
497
- Icon: "Icons",
498
- Chip: "Tags",
499
- Pagination: "Navigation"
500
- }[componentName];
501
- if (mappedFile && exportedFiles.includes(mappedFile)) return `${mappedFile}.md`;
502
- if (exportedFiles.includes(componentName)) return `${componentName}.md`;
503
- return null;
504
- }
505
- /**
506
- * Get list of exported documentation files
507
- */
508
- function getExportedFiles() {
509
- try {
510
- const possiblePaths = [
511
- path.join(dirname$1, "../../data/zeroheight-exports"),
512
- path.join(dirname$1, "../data/zeroheight-exports"),
513
- path.join(process.cwd(), "data/zeroheight-exports")
514
- ];
515
- let exportDir = "";
516
- for (const p of possiblePaths) if (fs.existsSync(p)) {
517
- exportDir = p;
518
- break;
519
- }
520
- if (!exportDir) {
521
- console.warn("Export directory not found in any expected location. Please run Zeroheight export first.");
522
- return [];
523
- }
524
- return fs.readdirSync(exportDir).filter((file) => file.endsWith(".md") && file !== "README.md").map((file) => file.replace(".md", ""));
525
- } catch (error) {
526
- console.warn("Could not read exported files:", error);
527
- return [];
528
- }
529
- }
530
- /**
531
- * Get list of components that have documentation available
532
- */
533
- function getComponentsWithDocs(allComponents, exportedFiles) {
534
- return allComponents.filter((component) => {
535
- return mapComponentToFile(component, exportedFiles) !== null;
536
- });
537
- }
538
- //#endregion
539
402
  //#region src/tools/index.ts
540
403
  const tools = [
541
404
  getComponentPropsTool,
542
405
  {
543
406
  name: "get_component_docs",
544
- description: "Get design system documentation for a specific component. Retrieves the corresponding Zeroheight documentation file for the given component name. Supports all SDS components and maps them to their appropriate documentation files.",
407
+ description: "Get design system documentation for a specific SDS component. Returns the component's full documentation, including how it differs from the underlying MUI component, its props, and runnable code examples for each supported variation.",
545
408
  async ctx() {
546
409
  try {
547
- const componentList = await getAllComponentNames();
548
- const allComponents = [...componentList.components, ...componentList["data-viz"]];
549
- const exportedFiles = getExportedFiles();
410
+ const index = await getComponentDocsIndex();
550
411
  return {
551
- componentsWithDocs: getComponentsWithDocs(allComponents, exportedFiles),
552
- exportedFiles
412
+ index,
413
+ documented: Object.keys(index)
553
414
  };
554
415
  } catch (error) {
555
416
  throw new Error(`Failed to initialize get component docs tool: ${error instanceof Error ? error.message : "Unknown error"}`);
556
417
  }
557
418
  },
558
419
  exec(server, { ctx, name, description }) {
559
- server.tool(name, description, { component: z.enum(ctx.componentsWithDocs).describe("The name of the SDS component to get documentation for") }, async ({ component }) => {
420
+ server.tool(name, description, { component: z.enum(ctx.documented).describe("The name of the SDS component to get documentation for") }, async ({ component }) => {
560
421
  try {
561
- const mappedFile = mapComponentToFile(component, ctx.exportedFiles);
562
- if (!mappedFile) return { content: [{
422
+ const entry = ctx.index[component];
423
+ if (!entry) return { content: [{
563
424
  type: "text",
564
425
  text: `No documentation found for component '${component}'. This component may not have design system documentation available.`
565
426
  }] };
566
- const possiblePaths = [
567
- path.join(dirname$1, "../../data/zeroheight-exports", mappedFile),
568
- path.join(dirname$1, "../data/zeroheight-exports", mappedFile),
569
- path.join(process.cwd(), "data/zeroheight-exports", mappedFile)
570
- ];
571
- let filePath = "";
572
- for (const p of possiblePaths) if (fs.existsSync(p)) {
573
- filePath = p;
574
- break;
575
- }
576
- if (!filePath) throw new Error(`Documentation file ${mappedFile} not found`);
427
+ const documentation = await fetchComponentDocs(entry.file);
577
428
  return { content: [{
578
429
  type: "text",
579
- text: `# Documentation for ${component}\n\nSource: ${mappedFile}\n\n${fs.readFileSync(filePath, "utf8")}`
430
+ text: `Package: ${entry.package}\nSource: ${entry.source}\n\n${documentation}`
580
431
  }] };
581
432
  } catch (error) {
582
433
  return { content: [{
583
434
  type: "text",
584
- text: `Error reading documentation file for '${component}': ${error instanceof Error ? error.message : "Unknown error"}`
435
+ text: `Error reading documentation for '${component}': ${error instanceof Error ? error.message : "Unknown error"}`
585
436
  }] };
586
437
  }
587
438
  });
588
439
  }
589
440
  },
590
441
  listComponentsTool,
591
- getTailwindTokensTool
442
+ {
443
+ name: "get_tailwind_tokens",
444
+ description: "Get all available Tailwind tokens from the SDS design system. Available design tokens include fontFamily, fontSize, fontVariantNumeric, letterSpacing, lineHeight, textDecoration, textTransform, typography, height, width, borderRadius, boxShadow, breakpoints, colors, spacing, and more.",
445
+ async ctx() {
446
+ try {
447
+ return { tailwindTokens: await fetchTailwindTokens() };
448
+ } catch (error) {
449
+ throw new Error(`Failed to initialize tailwind tokens tool: ${error instanceof Error ? error.message : "Unknown error"}`);
450
+ }
451
+ },
452
+ exec(server, { ctx, name, description }) {
453
+ server.tool(name, description, { category: z.enum([
454
+ "all",
455
+ "fontFamily",
456
+ "fontSize",
457
+ "fontVariantNumeric",
458
+ "letterSpacing",
459
+ "lineHeight",
460
+ "textDecoration",
461
+ "textTransform",
462
+ "typography",
463
+ "height",
464
+ "width",
465
+ "borderRadius",
466
+ "boxShadow",
467
+ "breakpoints",
468
+ "colors",
469
+ "spacing"
470
+ ]).optional().describe("Optional category of tokens to retrieve. If not specified, returns all tokens.") }, async ({ category }) => {
471
+ try {
472
+ const tokens = ctx.tailwindTokens;
473
+ let result;
474
+ if (!category || category === "all") result = tokens;
475
+ else result = tokens[category] || {};
476
+ const responseContent = [];
477
+ const guidance = getTokenGuidance(category);
478
+ responseContent.push({
479
+ type: "text",
480
+ text: guidance
481
+ });
482
+ responseContent.push({
483
+ type: "text",
484
+ text: JSON.stringify(result, null, 2)
485
+ });
486
+ return { content: responseContent };
487
+ } catch (error) {
488
+ return { content: [{
489
+ type: "text",
490
+ text: `Failed to get Tailwind tokens: ${error instanceof Error ? error.message : "Unknown error"}`
491
+ }] };
492
+ }
493
+ });
494
+ }
495
+ }
592
496
  ];
593
497
  const registeredToolCache = /* @__PURE__ */ new Map();
594
498
  const initializeTools = async (server, config) => {
@@ -654,19 +558,19 @@ function initializeResources(server) {
654
558
  throw new Error("Failed to read component rules: " + message);
655
559
  }
656
560
  });
657
- server.resource("Zeroheight Documentation Rules", "sds://rules/zeroheight", {
561
+ server.resource("SDS Documentation Rules", "sds://rules/documentation", {
658
562
  mimeType: MIME_TYPE_MARKDOWN,
659
- description: "Rules for following Zeroheight documentation"
563
+ description: "Rules for following the SDS component documentation"
660
564
  }, async () => {
661
565
  try {
662
566
  return { contents: [{
663
- uri: "sds://rules/zeroheight",
567
+ uri: "sds://rules/documentation",
664
568
  mimeType: MIME_TYPE_MARKDOWN,
665
- text: readFileSync(findResourceFile("zeroheight-rules.md"), "utf-8")
569
+ text: readFileSync(findResourceFile("documentation-rules.md"), "utf-8")
666
570
  }] };
667
571
  } catch (err) {
668
572
  const message = err instanceof Error ? err.message : UNKNOWN_ERROR;
669
- throw new Error("Failed to read Zeroheight rules: " + message);
573
+ throw new Error("Failed to read documentation rules: " + message);
670
574
  }
671
575
  });
672
576
  }
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@czi-sds/mcp",
3
3
  "description": "The official MCP server for SDS",
4
- "version": "0.16.0",
4
+ "version": "0.17.0",
5
5
  "main": "dist/stdio.js",
6
6
  "files": [
7
7
  "dist",
@@ -22,13 +22,14 @@
22
22
  "generate:tailwind-tokens": "mkdir -p data && cp ../components/src/common/styles-dictionary/json/tailwind.json data/tailwind.json && echo '✓ Copied tailwind.json to data folder'",
23
23
  "generate:components-list": "tsx scripts/generate-component-list.ts",
24
24
  "generate:component-props": "tsx scripts/generate-component-props.ts",
25
- "generate:zeroheight-export": "tsx scripts/export-zeroheight-pages.ts",
26
- "generate:all": "yarn generate:tailwind-tokens && yarn generate:components-list && yarn generate:component-props",
25
+ "generate:component-docs": "tsx scripts/generate-component-docs.ts",
26
+ "generate:all": "yarn generate:tailwind-tokens && yarn generate:components-list && yarn generate:component-props && yarn generate:component-docs && npx prettier --write 'data/**/*.{md,json}'",
27
+ "audit:docs": "tsx scripts/audit-docs.ts",
27
28
  "prebuild": "yarn generate:all",
28
29
  "build": "yarn prebuild && rolldown -c && chmod 755 dist/stdio.js",
29
30
  "dev": "rolldown -c --watch",
30
31
  "inspect": "node scripts/inspect.js",
31
- "inspect:dev": "npx @modelcontextprotocol/inspector npx tsx src/stdio.ts",
32
+ "inspect:dev": "npx -y @modelcontextprotocol/inspector@latest npx tsx src/stdio.ts",
32
33
  "serve": "tsx --watch src/http.ts"
33
34
  },
34
35
  "bin": {
@@ -57,10 +58,13 @@
57
58
  "@tsconfig/node22": "^22.0.1",
58
59
  "@types/express": "^5.0.3",
59
60
  "@types/fs-extra": "^11.0.4",
61
+ "@types/turndown": "^5.0.6",
62
+ "node-html-parser": "^9.0.1",
60
63
  "react-docgen-typescript": "^2.4.0",
61
64
  "rolldown": "^1.0.1",
62
65
  "tsx": "^4.20.3",
66
+ "turndown": "^7.2.4",
63
67
  "typescript": "^5.9.2"
64
68
  },
65
- "gitHead": "ccf2cae77a8b5748a247f2349d06be28d3097ade"
69
+ "gitHead": "86ab08f76d3b95b09ac6709b17f6c6d65b10d9e5"
66
70
  }
@@ -1,34 +0,0 @@
1
- {
2
- "ButtonDropdownV2": {
3
- "props": {
4
- "backgroundOnHover": {
5
- "type": "any",
6
- "isRequired": false
7
- },
8
- "children": {
9
- "type": "any",
10
- "isRequired": false
11
- },
12
- "disabled": {
13
- "type": "any",
14
- "isRequired": false
15
- },
16
- "startIcon": {
17
- "type": "any",
18
- "isRequired": false
19
- },
20
- "size": {
21
- "type": "any",
22
- "isRequired": false
23
- },
24
- "sdsStyle": {
25
- "type": "any",
26
- "isRequired": false
27
- },
28
- "sdsType": {
29
- "type": "any",
30
- "isRequired": false
31
- }
32
- }
33
- }
34
- }
@@ -1,47 +0,0 @@
1
- {
2
- "ButtonNew": {
3
- "props": {
4
- "backgroundOnHover": {
5
- "type": "\"false\" | \"true\"",
6
- "isRequired": false
7
- },
8
- "children": {
9
- "type": "ReactNode",
10
- "isRequired": false,
11
- "description": "The content of the component."
12
- },
13
- "endIcon": {
14
- "type": "ReactNode",
15
- "isRequired": false,
16
- "description": "Element placed after the children."
17
- },
18
- "icon": {
19
- "type": "any",
20
- "isRequired": false
21
- },
22
- "onClick": {
23
- "type": "function",
24
- "isRequired": false
25
- },
26
- "size": {
27
- "type": "\"small\" | \"medium\" | \"large\"",
28
- "isRequired": false,
29
- "description": "The size of the component.\n`small` is equivalent to the dense button styling.",
30
- "defaultValue": "medium"
31
- },
32
- "sdsStyle": {
33
- "type": "\"outline\" | \"solid\" | \"minimal\"",
34
- "isRequired": false
35
- },
36
- "sdsType": {
37
- "type": "\"primary\" | \"secondary\" | \"destructive\"",
38
- "isRequired": false
39
- },
40
- "startIcon": {
41
- "type": "ReactNode",
42
- "isRequired": false,
43
- "description": "Element placed before the children."
44
- }
45
- }
46
- }
47
- }
@@ -1,44 +0,0 @@
1
- {
2
- "ButtonToggleV2": {
3
- "props": {
4
- "backgroundOnHover": {
5
- "type": "\"false\" | \"true\"",
6
- "isRequired": false
7
- },
8
- "children": {
9
- "type": "ReactNode",
10
- "isRequired": false,
11
- "description": "The content of the component."
12
- },
13
- "disabled": {
14
- "type": "\"false\" | \"true\"",
15
- "isRequired": false,
16
- "description": "If `true`, the component is disabled.",
17
- "defaultValue": "false\nfalse"
18
- },
19
- "startIcon": {
20
- "type": "ReactElement",
21
- "isRequired": true,
22
- "description": "Element placed before the children."
23
- },
24
- "size": {
25
- "type": "\"small\" | \"medium\" | \"large\"",
26
- "isRequired": false,
27
- "description": "The size of the component.\n`small` is equivalent to the dense button styling.",
28
- "defaultValue": "medium"
29
- },
30
- "sdsType": {
31
- "type": "\"primary\" | \"secondary\" | \"destructive\"",
32
- "isRequired": false
33
- },
34
- "sdsStyle": {
35
- "type": "\"outline\" | \"solid\" | \"minimal\"",
36
- "isRequired": false
37
- },
38
- "sdsStage": {
39
- "type": "\"off\" | \"on\"",
40
- "isRequired": false
41
- }
42
- }
43
- }
44
- }
@@ -1,43 +0,0 @@
1
- {
2
- "ButtonV2": {
3
- "props": {
4
- "backgroundOnHover": {
5
- "type": "\"false\" | \"true\"",
6
- "isRequired": false
7
- },
8
- "children": {
9
- "type": "ReactNode",
10
- "isRequired": false,
11
- "description": "The content of the component."
12
- },
13
- "endIcon": {
14
- "type": "ReactNode",
15
- "isRequired": false,
16
- "description": "Element placed after the children."
17
- },
18
- "onClick": {
19
- "type": "function",
20
- "isRequired": false
21
- },
22
- "size": {
23
- "type": "\"small\" | \"medium\" | \"large\"",
24
- "isRequired": false,
25
- "description": "The size of the component.\n`small` is equivalent to the dense button styling.",
26
- "defaultValue": "medium"
27
- },
28
- "sdsStyle": {
29
- "type": "\"outline\" | \"solid\" | \"minimal\"",
30
- "isRequired": false
31
- },
32
- "sdsType": {
33
- "type": "\"primary\" | \"secondary\" | \"destructive\"",
34
- "isRequired": false
35
- },
36
- "startIcon": {
37
- "type": "ReactNode",
38
- "isRequired": false,
39
- "description": "Element placed before the children."
40
- }
41
- }
42
- }
43
- }