specra 0.1.13 → 0.2.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 (276) hide show
  1. package/LICENSE.MD +25 -4
  2. package/README.md +67 -58
  3. package/config/specra.config.schema.json +16 -0
  4. package/config/svelte-config.js +63 -0
  5. package/dist/api-parser.types.d.ts +59 -0
  6. package/dist/api-parser.types.js +5 -0
  7. package/dist/api.types.d.ts +137 -0
  8. package/dist/api.types.js +5 -0
  9. package/dist/category.d.ts +21 -0
  10. package/dist/category.js +48 -0
  11. package/dist/components/ConfigProvider.svelte +13 -0
  12. package/dist/components/ConfigProvider.svelte.d.ts +31 -0
  13. package/dist/components/docs/Accordion.svelte +18 -0
  14. package/dist/components/docs/Accordion.svelte.d.ts +10 -0
  15. package/dist/components/docs/AccordionItem.svelte +41 -0
  16. package/dist/components/docs/AccordionItem.svelte.d.ts +10 -0
  17. package/dist/components/docs/Badge.svelte +28 -0
  18. package/dist/components/docs/Badge.svelte.d.ts +9 -0
  19. package/dist/components/docs/Breadcrumb.svelte +80 -0
  20. package/dist/components/docs/Breadcrumb.svelte.d.ts +8 -0
  21. package/dist/components/docs/Callout.svelte +96 -0
  22. package/dist/components/docs/Callout.svelte.d.ts +10 -0
  23. package/dist/components/docs/Card.svelte +63 -0
  24. package/dist/components/docs/Card.svelte.d.ts +12 -0
  25. package/dist/components/docs/CardGrid.svelte +24 -0
  26. package/dist/components/docs/CardGrid.svelte.d.ts +8 -0
  27. package/dist/components/docs/CategoryIndex.svelte +110 -0
  28. package/dist/components/docs/CategoryIndex.svelte.d.ts +29 -0
  29. package/dist/components/docs/CodeBlock.svelte +172 -0
  30. package/dist/components/docs/CodeBlock.svelte.d.ts +8 -0
  31. package/dist/components/docs/Column.svelte +25 -0
  32. package/dist/components/docs/Column.svelte.d.ts +8 -0
  33. package/dist/components/docs/Columns.svelte +38 -0
  34. package/dist/components/docs/Columns.svelte.d.ts +13 -0
  35. package/dist/components/docs/DevModeBadge.svelte +15 -0
  36. package/dist/components/docs/DevModeBadge.svelte.d.ts +18 -0
  37. package/dist/components/docs/DocBadge.svelte +28 -0
  38. package/dist/components/docs/DocBadge.svelte.d.ts +9 -0
  39. package/dist/components/docs/DocLayout.svelte +107 -0
  40. package/dist/components/docs/DocLayout.svelte.d.ts +32 -0
  41. package/dist/components/docs/DocLoading.svelte +53 -0
  42. package/dist/components/docs/DocLoading.svelte.d.ts +18 -0
  43. package/dist/components/docs/DocMetadata.svelte +106 -0
  44. package/dist/components/docs/DocMetadata.svelte.d.ts +18 -0
  45. package/dist/components/docs/DocNavigation.svelte +56 -0
  46. package/dist/components/docs/DocNavigation.svelte.d.ts +12 -0
  47. package/dist/components/docs/DocTags.svelte +22 -0
  48. package/dist/components/docs/DocTags.svelte.d.ts +6 -0
  49. package/dist/components/docs/DraftBadge.svelte +10 -0
  50. package/dist/components/docs/DraftBadge.svelte.d.ts +18 -0
  51. package/dist/components/docs/Footer.svelte +72 -0
  52. package/dist/components/docs/Footer.svelte.d.ts +7 -0
  53. package/dist/components/docs/Frame.svelte +27 -0
  54. package/dist/components/docs/Frame.svelte.d.ts +9 -0
  55. package/dist/components/docs/Header.svelte +123 -0
  56. package/dist/components/docs/Header.svelte.d.ts +9 -0
  57. package/dist/components/docs/HeaderWithMenu.svelte +34 -0
  58. package/dist/components/docs/HeaderWithMenu.svelte.d.ts +17 -0
  59. package/dist/components/docs/HotReloadIndicator.svelte +44 -0
  60. package/dist/components/docs/HotReloadIndicator.svelte.d.ts +3 -0
  61. package/dist/components/docs/Icon.svelte +103 -0
  62. package/dist/components/docs/Icon.svelte.d.ts +11 -0
  63. package/dist/components/docs/Image.svelte +88 -0
  64. package/dist/components/docs/Image.svelte.d.ts +11 -0
  65. package/dist/components/docs/ImageCard.svelte +91 -0
  66. package/dist/components/docs/ImageCard.svelte.d.ts +12 -0
  67. package/dist/components/docs/ImageCardGrid.svelte +25 -0
  68. package/dist/components/docs/ImageCardGrid.svelte.d.ts +8 -0
  69. package/dist/components/docs/LayoutProviders.svelte +57 -0
  70. package/dist/components/docs/LayoutProviders.svelte.d.ts +9 -0
  71. package/dist/components/docs/Logo.svelte +25 -0
  72. package/dist/components/docs/Logo.svelte.d.ts +11 -0
  73. package/dist/components/docs/Math.svelte +54 -0
  74. package/dist/components/docs/Math.svelte.d.ts +7 -0
  75. package/dist/components/docs/MdxContent.svelte +41 -0
  76. package/dist/components/docs/MdxHotReload.svelte +78 -0
  77. package/dist/components/docs/MdxHotReload.svelte.d.ts +9 -0
  78. package/dist/components/docs/MdxLayout.svelte +16 -0
  79. package/dist/components/docs/MdxLayout.svelte.d.ts +6 -0
  80. package/dist/components/docs/Mermaid.svelte +88 -0
  81. package/dist/components/docs/Mermaid.svelte.d.ts +7 -0
  82. package/dist/components/docs/MobileDocLayout.svelte +211 -0
  83. package/dist/components/docs/MobileDocLayout.svelte.d.ts +35 -0
  84. package/dist/components/docs/MobileSidebar.svelte +122 -0
  85. package/dist/components/docs/MobileSidebar.svelte.d.ts +31 -0
  86. package/dist/components/docs/MobileSidebarWrapper.svelte +122 -0
  87. package/dist/components/docs/MobileSidebarWrapper.svelte.d.ts +32 -0
  88. package/dist/components/docs/NotFoundContent.svelte +40 -0
  89. package/dist/components/docs/NotFoundContent.svelte.d.ts +6 -0
  90. package/dist/components/docs/SearchHighlight.svelte +116 -0
  91. package/dist/components/docs/SearchHighlight.svelte.d.ts +3 -0
  92. package/dist/components/docs/SearchModal.svelte +239 -0
  93. package/dist/components/docs/SearchModal.svelte.d.ts +9 -0
  94. package/dist/components/docs/Sidebar.svelte +69 -0
  95. package/dist/components/docs/Sidebar.svelte.d.ts +31 -0
  96. package/dist/components/docs/SidebarMenuItems.svelte +344 -0
  97. package/dist/components/docs/SidebarMenuItems.svelte.d.ts +33 -0
  98. package/dist/components/docs/SidebarSkeleton.svelte +50 -0
  99. package/dist/components/docs/SidebarSkeleton.svelte.d.ts +18 -0
  100. package/dist/components/docs/SiteBanner.svelte +92 -0
  101. package/dist/components/docs/SiteBanner.svelte.d.ts +7 -0
  102. package/dist/components/docs/Step.svelte +44 -0
  103. package/dist/components/docs/Step.svelte.d.ts +8 -0
  104. package/dist/components/docs/Steps.svelte +15 -0
  105. package/dist/components/docs/Steps.svelte.d.ts +7 -0
  106. package/dist/components/docs/Tab.svelte +40 -0
  107. package/dist/components/docs/Tab.svelte.d.ts +8 -0
  108. package/dist/components/docs/TabGroups.svelte +183 -0
  109. package/dist/components/docs/TabGroups.svelte.d.ts +25 -0
  110. package/dist/components/docs/TableOfContents.svelte +100 -0
  111. package/dist/components/docs/TableOfContents.svelte.d.ts +9 -0
  112. package/dist/components/docs/Tabs.svelte +69 -0
  113. package/dist/components/docs/Tabs.svelte.d.ts +8 -0
  114. package/dist/components/docs/ThemeToggle.svelte +16 -0
  115. package/dist/components/docs/ThemeToggle.svelte.d.ts +18 -0
  116. package/dist/components/docs/Tooltip.svelte +44 -0
  117. package/dist/components/docs/Tooltip.svelte.d.ts +10 -0
  118. package/dist/components/docs/VersionSwitcher.svelte +95 -0
  119. package/dist/components/docs/VersionSwitcher.svelte.d.ts +7 -0
  120. package/dist/components/docs/Video.svelte +84 -0
  121. package/dist/components/docs/Video.svelte.d.ts +12 -0
  122. package/dist/components/docs/api/ApiEndpoint.svelte +61 -0
  123. package/dist/components/docs/api/ApiEndpoint.svelte.d.ts +11 -0
  124. package/dist/components/docs/api/ApiParams.svelte +80 -0
  125. package/dist/components/docs/api/ApiParams.svelte.d.ts +14 -0
  126. package/dist/components/docs/api/ApiPlayground.svelte +259 -0
  127. package/dist/components/docs/api/ApiPlayground.svelte.d.ts +16 -0
  128. package/dist/components/docs/api/ApiReference.svelte +278 -0
  129. package/dist/components/docs/api/ApiReference.svelte.d.ts +23 -0
  130. package/dist/components/docs/api/ApiResponse.svelte +66 -0
  131. package/dist/components/docs/api/ApiResponse.svelte.d.ts +9 -0
  132. package/dist/components/docs/api/index.d.ts +5 -0
  133. package/dist/components/docs/api/index.js +5 -0
  134. package/dist/components/docs/componentTextProps.d.ts +3 -0
  135. package/dist/components/docs/componentTextProps.js +61 -0
  136. package/dist/components/docs/index.d.ts +54 -0
  137. package/dist/components/docs/index.js +56 -0
  138. package/dist/components/global/VersionNotFound.svelte +48 -0
  139. package/dist/components/global/VersionNotFound.svelte.d.ts +7 -0
  140. package/dist/components/global/index.d.ts +1 -0
  141. package/dist/components/global/index.js +1 -0
  142. package/dist/components/index.d.ts +6 -822
  143. package/dist/components/index.js +11 -3854
  144. package/dist/components/ui/Badge.svelte +48 -0
  145. package/dist/components/ui/Badge.svelte.d.ts +15 -0
  146. package/dist/components/ui/Button.svelte +58 -0
  147. package/dist/components/ui/Button.svelte.d.ts +17 -0
  148. package/dist/components/ui/Dialog.svelte +16 -0
  149. package/dist/components/ui/Dialog.svelte.d.ts +9 -0
  150. package/dist/components/ui/DialogClose.svelte +16 -0
  151. package/dist/components/ui/DialogClose.svelte.d.ts +9 -0
  152. package/dist/components/ui/DialogContent.svelte +43 -0
  153. package/dist/components/ui/DialogContent.svelte.d.ts +10 -0
  154. package/dist/components/ui/DialogDescription.svelte +21 -0
  155. package/dist/components/ui/DialogDescription.svelte.d.ts +9 -0
  156. package/dist/components/ui/DialogFooter.svelte +20 -0
  157. package/dist/components/ui/DialogFooter.svelte.d.ts +9 -0
  158. package/dist/components/ui/DialogHeader.svelte +20 -0
  159. package/dist/components/ui/DialogHeader.svelte.d.ts +9 -0
  160. package/dist/components/ui/DialogTitle.svelte +21 -0
  161. package/dist/components/ui/DialogTitle.svelte.d.ts +9 -0
  162. package/dist/components/ui/Input.svelte +23 -0
  163. package/dist/components/ui/Input.svelte.d.ts +8 -0
  164. package/dist/components/ui/Textarea.svelte +19 -0
  165. package/dist/components/ui/Textarea.svelte.d.ts +7 -0
  166. package/dist/components/ui/index.d.ts +11 -0
  167. package/dist/components/ui/index.js +11 -0
  168. package/dist/config.d.ts +8 -0
  169. package/dist/config.js +9 -0
  170. package/dist/config.schema.json +471 -0
  171. package/dist/config.server.d.ts +46 -0
  172. package/dist/config.server.js +149 -0
  173. package/dist/{mdx-ColN3Cyg.d.mts → config.types.d.ts} +22 -75
  174. package/dist/config.types.js +39 -0
  175. package/dist/dev-utils.d.ts +29 -0
  176. package/dist/dev-utils.js +63 -0
  177. package/dist/index.d.ts +19 -4
  178. package/dist/index.js +25 -4861
  179. package/dist/mdx-cache.d.ts +41 -0
  180. package/dist/mdx-cache.js +160 -0
  181. package/dist/mdx-components.js +50 -1931
  182. package/dist/mdx-security.d.ts +76 -0
  183. package/dist/mdx-security.js +217 -0
  184. package/dist/mdx.d.ts +73 -0
  185. package/dist/mdx.js +1099 -0
  186. package/dist/middleware/index.d.ts +1 -0
  187. package/dist/middleware/index.js +2 -0
  188. package/dist/middleware/security.d.ts +22 -47
  189. package/dist/middleware/security.js +111 -137
  190. package/dist/parsers/base-parser.d.ts +14 -0
  191. package/dist/parsers/base-parser.js +1 -0
  192. package/dist/parsers/index.d.ts +16 -0
  193. package/dist/parsers/index.js +51 -0
  194. package/dist/parsers/openapi-parser.d.ts +18 -0
  195. package/dist/parsers/openapi-parser.js +209 -0
  196. package/dist/parsers/postman-parser.d.ts +20 -0
  197. package/dist/parsers/postman-parser.js +260 -0
  198. package/dist/parsers/specra-parser.d.ts +10 -0
  199. package/dist/parsers/specra-parser.js +18 -0
  200. package/dist/redirects.d.ts +12 -0
  201. package/dist/redirects.js +30 -0
  202. package/dist/remark-code-meta.d.ts +6 -0
  203. package/dist/remark-code-meta.js +21 -0
  204. package/dist/sidebar-utils.d.ts +59 -0
  205. package/dist/sidebar-utils.js +144 -0
  206. package/dist/stores/config.d.ts +20 -0
  207. package/dist/stores/config.js +45 -0
  208. package/dist/stores/index.d.ts +4 -0
  209. package/dist/stores/index.js +4 -0
  210. package/dist/stores/sidebar.d.ts +7 -0
  211. package/dist/stores/sidebar.js +12 -0
  212. package/dist/stores/tabs.d.ts +6 -0
  213. package/dist/stores/tabs.js +41 -0
  214. package/dist/stores/theme.d.ts +7 -0
  215. package/dist/stores/theme.js +75 -0
  216. package/dist/{styles.css → styles/globals.css} +136 -6
  217. package/dist/toc.d.ts +9 -0
  218. package/dist/toc.js +15 -0
  219. package/dist/utils.d.ts +13 -0
  220. package/dist/utils.js +30 -0
  221. package/package.json +47 -90
  222. package/dist/app/api/mdx-watch/route.d.mts +0 -10
  223. package/dist/app/api/mdx-watch/route.d.ts +0 -10
  224. package/dist/app/api/mdx-watch/route.js +0 -118
  225. package/dist/app/api/mdx-watch/route.js.map +0 -1
  226. package/dist/app/api/mdx-watch/route.mjs +0 -91
  227. package/dist/app/api/mdx-watch/route.mjs.map +0 -1
  228. package/dist/chunk-6S3EJVEO.mjs +0 -259
  229. package/dist/chunk-6S3EJVEO.mjs.map +0 -1
  230. package/dist/chunk-BE7EROIW.mjs +0 -212
  231. package/dist/chunk-BE7EROIW.mjs.map +0 -1
  232. package/dist/chunk-CWHRZHZO.mjs +0 -168
  233. package/dist/chunk-CWHRZHZO.mjs.map +0 -1
  234. package/dist/chunk-D5VDVYFY.mjs +0 -1325
  235. package/dist/chunk-D5VDVYFY.mjs.map +0 -1
  236. package/dist/chunk-WMCO2UX5.mjs +0 -585
  237. package/dist/chunk-WMCO2UX5.mjs.map +0 -1
  238. package/dist/chunk-XEMGCPZZ.mjs +0 -475
  239. package/dist/chunk-XEMGCPZZ.mjs.map +0 -1
  240. package/dist/components/index.d.mts +0 -822
  241. package/dist/components/index.js.map +0 -1
  242. package/dist/components/index.mjs +0 -3741
  243. package/dist/components/index.mjs.map +0 -1
  244. package/dist/index.d.mts +0 -4
  245. package/dist/index.js.map +0 -1
  246. package/dist/index.mjs +0 -1897
  247. package/dist/index.mjs.map +0 -1
  248. package/dist/layouts/index.d.mts +0 -34
  249. package/dist/layouts/index.d.ts +0 -34
  250. package/dist/layouts/index.js +0 -453
  251. package/dist/layouts/index.js.map +0 -1
  252. package/dist/layouts/index.mjs +0 -173
  253. package/dist/layouts/index.mjs.map +0 -1
  254. package/dist/lib/index.d.mts +0 -583
  255. package/dist/lib/index.d.ts +0 -583
  256. package/dist/lib/index.js +0 -1595
  257. package/dist/lib/index.js.map +0 -1
  258. package/dist/lib/index.mjs +0 -111
  259. package/dist/lib/index.mjs.map +0 -1
  260. package/dist/mdx-ColN3Cyg.d.ts +0 -352
  261. package/dist/mdx-components.d.mts +0 -86
  262. package/dist/mdx-components.d.ts +0 -86
  263. package/dist/mdx-components.js.map +0 -1
  264. package/dist/mdx-components.mjs +0 -206
  265. package/dist/mdx-components.mjs.map +0 -1
  266. package/dist/middleware/security.d.mts +0 -82
  267. package/dist/middleware/security.js.map +0 -1
  268. package/dist/middleware/security.mjs +0 -84
  269. package/dist/middleware/security.mjs.map +0 -1
  270. package/dist/styles.css.map +0 -1
  271. package/dist/styles.d.mts +0 -2
  272. package/dist/styles.d.ts +0 -2
  273. package/dist/styles.js +0 -2
  274. package/dist/styles.js.map +0 -1
  275. package/dist/styles.mjs +0 -1
  276. package/dist/styles.mjs.map +0 -1
@@ -0,0 +1,278 @@
1
+ <script lang="ts">
2
+ import type { SpecraApiSpec } from '../../../api-parser.types.js';
3
+ import { parseApiSpec, type ParserType } from '../../../parsers/index.js';
4
+ import Accordion from '../Accordion.svelte';
5
+ import AccordionItem from '../AccordionItem.svelte';
6
+ import ApiParams from './ApiParams.svelte';
7
+ import ApiResponseDisplay from './ApiResponse.svelte';
8
+ import ApiPlayground from './ApiPlayground.svelte';
9
+ import CodeBlock from '../CodeBlock.svelte';
10
+ import { Loader2 } from 'lucide-svelte';
11
+
12
+ interface Props {
13
+ /**
14
+ * Path to the API spec JSON file (relative to /public or /static)
15
+ * Example: "/api-specs/my-api.json"
16
+ */
17
+ spec: string;
18
+
19
+ /**
20
+ * Parser type - auto-detect by default
21
+ * - "auto": Auto-detect format (Specra, OpenAPI, or Postman)
22
+ * - "specra": Native Specra format
23
+ * - "openapi": OpenAPI 3.x / Swagger
24
+ * - "postman": Postman Collection v2.x
25
+ */
26
+ parser?: ParserType;
27
+
28
+ /**
29
+ * Show API playground for testing
30
+ */
31
+ showPlayground?: boolean;
32
+ }
33
+
34
+ let { spec, parser = 'auto', showPlayground = true }: Props = $props();
35
+
36
+ let apiSpec = $state<SpecraApiSpec | null>(null);
37
+ let loading = $state(true);
38
+ let error = $state<string | null>(null);
39
+
40
+ // Replace environment variables in text
41
+ function interpolateEnv(text: string, env?: Record<string, string>): string {
42
+ if (!env) return text;
43
+ return text.replace(/\{(\w+)\}/g, (match, key) => {
44
+ return env[key] || match;
45
+ });
46
+ }
47
+
48
+ // Fetch and parse spec reactively when spec or parser changes
49
+ $effect(() => {
50
+ const currentSpec = spec;
51
+ const currentParser = parser;
52
+
53
+ loading = true;
54
+ error = null;
55
+ apiSpec = null;
56
+
57
+ fetch(currentSpec)
58
+ .then((response) => {
59
+ if (!response.ok) {
60
+ throw new Error(`Failed to load API spec: ${response.statusText}`);
61
+ }
62
+ return response.json();
63
+ })
64
+ .then((data) => {
65
+ apiSpec = parseApiSpec(data, currentParser);
66
+ })
67
+ .catch((err) => {
68
+ error = err instanceof Error ? err.message : 'Failed to load API spec';
69
+ })
70
+ .finally(() => {
71
+ loading = false;
72
+ });
73
+ });
74
+ </script>
75
+
76
+ {#if loading}
77
+ <div class="flex items-center justify-center py-12">
78
+ <Loader2 class="h-6 w-6 animate-spin text-muted-foreground" />
79
+ <span class="ml-2 text-muted-foreground">Loading API specification...</span>
80
+ </div>
81
+ {:else if error}
82
+ <div class="rounded-lg border border-red-500/20 bg-red-500/10 p-4">
83
+ <p class="text-sm text-red-600 dark:text-red-400">Error: {error}</p>
84
+ </div>
85
+ {:else if apiSpec}
86
+ <div class="space-y-6">
87
+ <!-- API Info -->
88
+ {#if apiSpec.title || apiSpec.description}
89
+ <div class="mb-8">
90
+ {#if apiSpec.title}
91
+ <h2 class="text-2xl font-semibold mb-2 text-foreground">{apiSpec.title}</h2>
92
+ {/if}
93
+ {#if apiSpec.description}
94
+ <p class="text-muted-foreground">{apiSpec.description}</p>
95
+ {/if}
96
+ {#if apiSpec.baseUrl}
97
+ <div class="mt-4">
98
+ <p class="text-sm font-semibold text-muted-foreground mb-1">Base URL</p>
99
+ <code class="text-sm px-2 py-1 bg-muted rounded">{apiSpec.baseUrl}</code>
100
+ </div>
101
+ {/if}
102
+ </div>
103
+ {/if}
104
+
105
+ <!-- Authentication -->
106
+ {#if apiSpec.auth}
107
+ <div class="rounded-lg border border-border bg-card/30 p-4 mb-6">
108
+ <h3 class="text-lg font-semibold mb-2 text-foreground">Authentication</h3>
109
+ <p class="text-sm text-muted-foreground mb-2">
110
+ {apiSpec.auth.description || `This API uses ${apiSpec.auth.type} authentication.`}
111
+ </p>
112
+ {#if apiSpec.auth.type === 'bearer'}
113
+ <CodeBlock
114
+ code={`Authorization: ${apiSpec.auth.tokenPrefix || 'Bearer'} {YOUR_TOKEN}`}
115
+ language="bash"
116
+ />
117
+ {/if}
118
+ {#if apiSpec.auth.type === 'apiKey'}
119
+ <CodeBlock
120
+ code={`${apiSpec.auth.headerName || 'X-API-Key'}: {YOUR_API_KEY}`}
121
+ language="bash"
122
+ />
123
+ {/if}
124
+ </div>
125
+ {/if}
126
+
127
+ <!-- Endpoints -->
128
+ <Accordion class="space-y-4">
129
+ {#each apiSpec.endpoints as endpoint, index}
130
+ {@const allHeaders = [
131
+ ...(apiSpec.globalHeaders || []),
132
+ ...(endpoint.headers || []),
133
+ ].map((header) => ({
134
+ ...header,
135
+ value: interpolateEnv(header.value, apiSpec?.env),
136
+ }))}
137
+
138
+ <AccordionItem
139
+ title={`${endpoint.method} ${endpoint.path} - ${endpoint.title || ''}`}
140
+ >
141
+ {#snippet children()}
142
+ <div class="space-y-6 pt-4">
143
+ <!-- Method + Path Badge -->
144
+ <div class="flex items-center gap-3">
145
+ <span
146
+ class="text-xs font-semibold px-2 py-0.5 rounded {endpoint.method === 'GET'
147
+ ? 'bg-blue-500/10 text-blue-600 dark:text-blue-400'
148
+ : endpoint.method === 'POST'
149
+ ? 'bg-green-500/10 text-green-600 dark:text-green-400'
150
+ : endpoint.method === 'PUT'
151
+ ? 'bg-orange-500/10 text-orange-600 dark:text-orange-400'
152
+ : endpoint.method === 'PATCH'
153
+ ? 'bg-purple-500/10 text-purple-600 dark:text-purple-400'
154
+ : 'bg-red-500/10 text-red-600 dark:text-red-400'}"
155
+ >
156
+ {endpoint.method}
157
+ </span>
158
+ <code class="text-sm font-mono">{endpoint.path}</code>
159
+ {#if endpoint.title}
160
+ <span class="text-sm text-muted-foreground ml-auto">{endpoint.title}</span>
161
+ {/if}
162
+ </div>
163
+
164
+ <!-- Description -->
165
+ {#if endpoint.description}
166
+ <p class="text-sm text-muted-foreground">{endpoint.description}</p>
167
+ {/if}
168
+
169
+ <!-- Path Parameters -->
170
+ {#if endpoint.pathParams && endpoint.pathParams.length > 0}
171
+ <ApiParams title="Path Parameters" params={endpoint.pathParams} />
172
+ {/if}
173
+
174
+ <!-- Query Parameters -->
175
+ {#if endpoint.queryParams && endpoint.queryParams.length > 0}
176
+ <ApiParams title="Query Parameters" params={endpoint.queryParams} />
177
+ {/if}
178
+
179
+ <!-- Headers -->
180
+ {#if allHeaders.length > 0}
181
+ <div>
182
+ <h4 class="text-sm font-semibold text-foreground mb-3">Headers</h4>
183
+ <div class="space-y-2">
184
+ {#each allHeaders as header, idx}
185
+ <div class="flex flex-col gap-1">
186
+ <div class="flex items-center gap-2">
187
+ <code class="text-sm font-mono text-foreground">{header.name}</code>
188
+ <span class="text-xs text-muted-foreground">{header.value}</span>
189
+ </div>
190
+ {#if header.description}
191
+ <p class="text-sm text-muted-foreground">{header.description}</p>
192
+ {/if}
193
+ </div>
194
+ {/each}
195
+ </div>
196
+ </div>
197
+ {/if}
198
+
199
+ <!-- Request Body -->
200
+ {#if endpoint.body}
201
+ <div>
202
+ <h4 class="text-sm font-semibold text-foreground mb-3">Request Body</h4>
203
+ {#if endpoint.body.description}
204
+ <p class="text-sm text-muted-foreground mb-2">
205
+ {endpoint.body.description}
206
+ </p>
207
+ {/if}
208
+ {#if endpoint.body.example}
209
+ <CodeBlock
210
+ code={typeof endpoint.body.example === 'string'
211
+ ? endpoint.body.example
212
+ : JSON.stringify(endpoint.body.example, null, 2)}
213
+ language="json"
214
+ />
215
+ {/if}
216
+ </div>
217
+ {/if}
218
+
219
+ <!-- Responses -->
220
+ <div>
221
+ <h4 class="text-sm font-semibold text-foreground mb-3">Responses</h4>
222
+ {#if endpoint.successResponse}
223
+ <ApiResponseDisplay
224
+ status={endpoint.successResponse.status}
225
+ description={endpoint.successResponse.description}
226
+ example={endpoint.successResponse.example}
227
+ schema={endpoint.successResponse.schema}
228
+ />
229
+ {/if}
230
+ {#if endpoint.errorResponses}
231
+ {#each endpoint.errorResponses as response, idx}
232
+ <ApiResponseDisplay
233
+ status={response.status}
234
+ description={response.description}
235
+ example={response.example}
236
+ schema={response.schema}
237
+ />
238
+ {/each}
239
+ {/if}
240
+ </div>
241
+
242
+ <!-- Code Examples -->
243
+ {#if endpoint.examples && endpoint.examples.length > 0}
244
+ <div>
245
+ <h4 class="text-sm font-semibold text-foreground mb-3">Examples</h4>
246
+ {#each endpoint.examples as example, idx}
247
+ <div class="mb-3">
248
+ <p class="text-xs font-semibold text-muted-foreground mb-2">
249
+ {example.title}
250
+ </p>
251
+ <CodeBlock code={example.code} language={example.language} />
252
+ </div>
253
+ {/each}
254
+ </div>
255
+ {/if}
256
+
257
+ <!-- API Playground -->
258
+ {#if showPlayground}
259
+ <ApiPlayground
260
+ method={endpoint.method}
261
+ path={endpoint.path}
262
+ baseUrl={apiSpec?.baseUrl}
263
+ headers={Object.fromEntries(allHeaders.map((h) => [h.name, h.value]))}
264
+ pathParams={endpoint.pathParams}
265
+ defaultBody={endpoint.body?.example
266
+ ? typeof endpoint.body.example === 'string'
267
+ ? endpoint.body.example
268
+ : JSON.stringify(endpoint.body.example, null, 2)
269
+ : undefined}
270
+ />
271
+ {/if}
272
+ </div>
273
+ {/snippet}
274
+ </AccordionItem>
275
+ {/each}
276
+ </Accordion>
277
+ </div>
278
+ {/if}
@@ -0,0 +1,23 @@
1
+ import { type ParserType } from '../../../parsers/index.js';
2
+ interface Props {
3
+ /**
4
+ * Path to the API spec JSON file (relative to /public or /static)
5
+ * Example: "/api-specs/my-api.json"
6
+ */
7
+ spec: string;
8
+ /**
9
+ * Parser type - auto-detect by default
10
+ * - "auto": Auto-detect format (Specra, OpenAPI, or Postman)
11
+ * - "specra": Native Specra format
12
+ * - "openapi": OpenAPI 3.x / Swagger
13
+ * - "postman": Postman Collection v2.x
14
+ */
15
+ parser?: ParserType;
16
+ /**
17
+ * Show API playground for testing
18
+ */
19
+ showPlayground?: boolean;
20
+ }
21
+ declare const ApiReference: import("svelte").Component<Props, {}, "">;
22
+ type ApiReference = ReturnType<typeof ApiReference>;
23
+ export default ApiReference;
@@ -0,0 +1,66 @@
1
+ <script lang="ts">
2
+ import CodeBlock from '../CodeBlock.svelte';
3
+
4
+ interface Props {
5
+ status: number;
6
+ description?: string;
7
+ example?: any;
8
+ schema?: any;
9
+ }
10
+
11
+ let { status, description, example, schema }: Props = $props();
12
+
13
+ const statusColors: Record<string, string> = {
14
+ '2': 'text-green-600 dark:text-green-400',
15
+ '3': 'text-blue-600 dark:text-blue-400',
16
+ '4': 'text-orange-600 dark:text-orange-400',
17
+ '5': 'text-red-600 dark:text-red-400',
18
+ };
19
+
20
+ let statusClass = $derived(statusColors[String(status)[0]] || 'text-muted-foreground');
21
+
22
+ let exampleCode = $derived(
23
+ example
24
+ ? typeof example === 'string'
25
+ ? example
26
+ : JSON.stringify(example, null, 2)
27
+ : ''
28
+ );
29
+
30
+ let schemaCode = $derived(
31
+ schema
32
+ ? typeof schema === 'string'
33
+ ? schema
34
+ : JSON.stringify(schema, null, 2)
35
+ : ''
36
+ );
37
+ </script>
38
+
39
+ <div class="mb-4">
40
+ <div class="flex items-center gap-2 mb-2">
41
+ <span class="text-sm font-semibold {statusClass}">{status}</span>
42
+ {#if description}
43
+ <span class="text-sm text-muted-foreground">{description}</span>
44
+ {/if}
45
+ </div>
46
+
47
+ {#if example}
48
+ <div class="mb-3">
49
+ <p class="text-xs font-semibold text-muted-foreground mb-2">Example Response</p>
50
+ <CodeBlock
51
+ code={exampleCode}
52
+ language="json"
53
+ />
54
+ </div>
55
+ {/if}
56
+
57
+ {#if schema}
58
+ <div>
59
+ <p class="text-xs font-semibold text-muted-foreground mb-2">Schema</p>
60
+ <CodeBlock
61
+ code={schemaCode}
62
+ language="json"
63
+ />
64
+ </div>
65
+ {/if}
66
+ </div>
@@ -0,0 +1,9 @@
1
+ interface Props {
2
+ status: number;
3
+ description?: string;
4
+ example?: any;
5
+ schema?: any;
6
+ }
7
+ declare const ApiResponse: import("svelte").Component<Props, {}, "">;
8
+ type ApiResponse = ReturnType<typeof ApiResponse>;
9
+ export default ApiResponse;
@@ -0,0 +1,5 @@
1
+ export { default as ApiEndpoint } from './ApiEndpoint.svelte';
2
+ export { default as ApiParams } from './ApiParams.svelte';
3
+ export { default as ApiResponse, default as ApiResponseDisplay } from './ApiResponse.svelte';
4
+ export { default as ApiPlayground } from './ApiPlayground.svelte';
5
+ export { default as ApiReference } from './ApiReference.svelte';
@@ -0,0 +1,5 @@
1
+ export { default as ApiEndpoint } from './ApiEndpoint.svelte';
2
+ export { default as ApiParams } from './ApiParams.svelte';
3
+ export { default as ApiResponse, default as ApiResponseDisplay } from './ApiResponse.svelte';
4
+ export { default as ApiPlayground } from './ApiPlayground.svelte';
5
+ export { default as ApiReference } from './ApiReference.svelte';
@@ -0,0 +1,3 @@
1
+ export declare const COMPONENT_TEXT_PROPS: Record<string, string[]>;
2
+ export declare function extractComponentPropsText(mdx: string): string;
3
+ export declare function extractSearchText(mdx: string): string;
@@ -0,0 +1,61 @@
1
+ export const COMPONENT_TEXT_PROPS = {
2
+ // Accordion components
3
+ Accordion: ["title"],
4
+ AccordionItem: ["title"],
5
+ // Alert/Callout components
6
+ Alert: ["title", "description"],
7
+ Banner: ["title"],
8
+ Callout: ["title", "content"],
9
+ Note: ["title"],
10
+ Warning: ["title", "text"],
11
+ // Navigation components
12
+ BreadCrumb: ["title", "slug", "version"],
13
+ // Card components
14
+ Card: ["title", "description"],
15
+ ImageCard: ["title", "description", "alt"],
16
+ // Media components
17
+ Image: ["alt", "caption"],
18
+ Video: ["caption"],
19
+ Frame: ["title"],
20
+ Mermaid: ["caption"],
21
+ // Interactive components
22
+ Tooltip: ["content"],
23
+ // Code components
24
+ CodeBlock: ["filename"],
25
+ // Step components
26
+ Step: ["title"],
27
+ };
28
+ export function extractComponentPropsText(mdx) {
29
+ return mdx.replace(/<([A-Z][\w]*)\b([^/>]*)\/>/g, (_, component, props) => {
30
+ const searchableProps = COMPONENT_TEXT_PROPS[component];
31
+ if (!searchableProps)
32
+ return " ";
33
+ let extracted = "";
34
+ for (const prop of searchableProps) {
35
+ const match = props.match(new RegExp(`${prop}="([^"]+)"`, "i"));
36
+ if (match) {
37
+ extracted += " " + match[1];
38
+ }
39
+ }
40
+ return extracted || " ";
41
+ });
42
+ }
43
+ export function extractSearchText(mdx) {
44
+ return extractComponentPropsText(mdx)
45
+ // 2. Remove fenced code blocks
46
+ .replace(/```[\s\S]*?```/g, " ")
47
+ // 3. Remove JSX blocks with children
48
+ .replace(/<([A-Z][\w]*)\b[^>]*>[\s\S]*?<\/\1>/g, " ")
49
+ // 4. Remove remaining JSX & HTML
50
+ .replace(/<\/?[A-Za-z][^>]*>/g, " ")
51
+ // 5. Remove inline code
52
+ .replace(/`[^`]+`/g, " ")
53
+ // 6. Remove markdown links (keep text)
54
+ .replace(/\[([^\]]+)\]\([^)]+\)/g, "$1")
55
+ // 7. Remove markdown noise
56
+ .replace(/[#>*_~=-]+/g, " ")
57
+ // 8. Normalize whitespace
58
+ .replace(/\s+/g, " ")
59
+ .trim()
60
+ .slice(0, 1000);
61
+ }
@@ -0,0 +1,54 @@
1
+ export { default as Accordion } from './Accordion.svelte';
2
+ export { default as AccordionItem } from './AccordionItem.svelte';
3
+ export { default as Badge } from './Badge.svelte';
4
+ export { default as DocBadge } from './DocBadge.svelte';
5
+ export { default as Breadcrumb } from './Breadcrumb.svelte';
6
+ export { default as Callout } from './Callout.svelte';
7
+ export { default as Card } from './Card.svelte';
8
+ export { default as CardGrid } from './CardGrid.svelte';
9
+ export { default as CategoryIndex } from './CategoryIndex.svelte';
10
+ export { default as CodeBlock } from './CodeBlock.svelte';
11
+ export { default as Column } from './Column.svelte';
12
+ export { default as Columns } from './Columns.svelte';
13
+ export { default as DevModeBadge } from './DevModeBadge.svelte';
14
+ export { default as DocLayout } from './DocLayout.svelte';
15
+ export { default as DocLoading } from './DocLoading.svelte';
16
+ export { default as DocMetadata } from './DocMetadata.svelte';
17
+ export { default as DocNavigation } from './DocNavigation.svelte';
18
+ export { default as DocTags } from './DocTags.svelte';
19
+ export { default as DraftBadge } from './DraftBadge.svelte';
20
+ export { default as Footer } from './Footer.svelte';
21
+ export { default as Frame } from './Frame.svelte';
22
+ export { default as Header } from './Header.svelte';
23
+ export { default as HeaderWithMenu } from './HeaderWithMenu.svelte';
24
+ export { default as HotReloadIndicator } from './HotReloadIndicator.svelte';
25
+ export { default as Icon } from './Icon.svelte';
26
+ export { default as Image } from './Image.svelte';
27
+ export { default as ImageCard } from './ImageCard.svelte';
28
+ export { default as ImageCardGrid } from './ImageCardGrid.svelte';
29
+ export { default as Logo } from './Logo.svelte';
30
+ export { default as Math } from './Math.svelte';
31
+ export { default as MdxContent } from './MdxContent.svelte';
32
+ export { default as MdxHotReload } from './MdxHotReload.svelte';
33
+ export { default as Mermaid } from './Mermaid.svelte';
34
+ export { default as MobileDocLayout } from './MobileDocLayout.svelte';
35
+ export { default as MobileSidebar } from './MobileSidebar.svelte';
36
+ export { default as MobileSidebarWrapper } from './MobileSidebarWrapper.svelte';
37
+ export { default as NotFoundContent } from './NotFoundContent.svelte';
38
+ export { default as SearchHighlight } from './SearchHighlight.svelte';
39
+ export { default as SearchModal } from './SearchModal.svelte';
40
+ export { default as Sidebar } from './Sidebar.svelte';
41
+ export { default as SidebarMenuItems } from './SidebarMenuItems.svelte';
42
+ export { default as SidebarSkeleton } from './SidebarSkeleton.svelte';
43
+ export { default as SiteBanner } from './SiteBanner.svelte';
44
+ export { default as Step } from './Step.svelte';
45
+ export { default as Steps } from './Steps.svelte';
46
+ export { default as Tab } from './Tab.svelte';
47
+ export { default as TabGroups } from './TabGroups.svelte';
48
+ export { default as TableOfContents } from './TableOfContents.svelte';
49
+ export { default as Tabs } from './Tabs.svelte';
50
+ export { default as ThemeToggle } from './ThemeToggle.svelte';
51
+ export { default as Tooltip } from './Tooltip.svelte';
52
+ export { default as VersionSwitcher } from './VersionSwitcher.svelte';
53
+ export { default as Video } from './Video.svelte';
54
+ export { ApiEndpoint, ApiParams, ApiResponse, ApiResponseDisplay, ApiPlayground, ApiReference, } from './api/index.js';
@@ -0,0 +1,56 @@
1
+ // Layout & Content components
2
+ export { default as Accordion } from './Accordion.svelte';
3
+ export { default as AccordionItem } from './AccordionItem.svelte';
4
+ export { default as Badge } from './Badge.svelte';
5
+ export { default as DocBadge } from './DocBadge.svelte';
6
+ export { default as Breadcrumb } from './Breadcrumb.svelte';
7
+ export { default as Callout } from './Callout.svelte';
8
+ export { default as Card } from './Card.svelte';
9
+ export { default as CardGrid } from './CardGrid.svelte';
10
+ export { default as CategoryIndex } from './CategoryIndex.svelte';
11
+ export { default as CodeBlock } from './CodeBlock.svelte';
12
+ export { default as Column } from './Column.svelte';
13
+ export { default as Columns } from './Columns.svelte';
14
+ export { default as DevModeBadge } from './DevModeBadge.svelte';
15
+ export { default as DocLayout } from './DocLayout.svelte';
16
+ export { default as DocLoading } from './DocLoading.svelte';
17
+ export { default as DocMetadata } from './DocMetadata.svelte';
18
+ export { default as DocNavigation } from './DocNavigation.svelte';
19
+ export { default as DocTags } from './DocTags.svelte';
20
+ export { default as DraftBadge } from './DraftBadge.svelte';
21
+ export { default as Footer } from './Footer.svelte';
22
+ export { default as Frame } from './Frame.svelte';
23
+ export { default as Header } from './Header.svelte';
24
+ export { default as HeaderWithMenu } from './HeaderWithMenu.svelte';
25
+ export { default as HotReloadIndicator } from './HotReloadIndicator.svelte';
26
+ export { default as Icon } from './Icon.svelte';
27
+ export { default as Image } from './Image.svelte';
28
+ export { default as ImageCard } from './ImageCard.svelte';
29
+ export { default as ImageCardGrid } from './ImageCardGrid.svelte';
30
+ export { default as Logo } from './Logo.svelte';
31
+ export { default as Math } from './Math.svelte';
32
+ export { default as MdxContent } from './MdxContent.svelte';
33
+ export { default as MdxHotReload } from './MdxHotReload.svelte';
34
+ export { default as Mermaid } from './Mermaid.svelte';
35
+ export { default as MobileDocLayout } from './MobileDocLayout.svelte';
36
+ export { default as MobileSidebar } from './MobileSidebar.svelte';
37
+ export { default as MobileSidebarWrapper } from './MobileSidebarWrapper.svelte';
38
+ export { default as NotFoundContent } from './NotFoundContent.svelte';
39
+ export { default as SearchHighlight } from './SearchHighlight.svelte';
40
+ export { default as SearchModal } from './SearchModal.svelte';
41
+ export { default as Sidebar } from './Sidebar.svelte';
42
+ export { default as SidebarMenuItems } from './SidebarMenuItems.svelte';
43
+ export { default as SidebarSkeleton } from './SidebarSkeleton.svelte';
44
+ export { default as SiteBanner } from './SiteBanner.svelte';
45
+ export { default as Step } from './Step.svelte';
46
+ export { default as Steps } from './Steps.svelte';
47
+ export { default as Tab } from './Tab.svelte';
48
+ export { default as TabGroups } from './TabGroups.svelte';
49
+ export { default as TableOfContents } from './TableOfContents.svelte';
50
+ export { default as Tabs } from './Tabs.svelte';
51
+ export { default as ThemeToggle } from './ThemeToggle.svelte';
52
+ export { default as Tooltip } from './Tooltip.svelte';
53
+ export { default as VersionSwitcher } from './VersionSwitcher.svelte';
54
+ export { default as Video } from './Video.svelte';
55
+ // API components
56
+ export { ApiEndpoint, ApiParams, ApiResponse, ApiResponseDisplay, ApiPlayground, ApiReference, } from './api/index.js';
@@ -0,0 +1,48 @@
1
+ <script lang="ts">
2
+ import { AlertTriangle } from 'lucide-svelte';
3
+
4
+ interface Props {
5
+ version?: string;
6
+ availableVersions?: string[];
7
+ }
8
+
9
+ let { version, availableVersions = [] }: Props = $props();
10
+ </script>
11
+
12
+ <div class="flex min-h-screen items-center justify-center px-4">
13
+ <div class="text-center">
14
+ <div class="mb-4 flex justify-center">
15
+ <AlertTriangle class="h-16 w-16 text-yellow-500" />
16
+ </div>
17
+ <h1 class="mb-2 text-4xl font-bold">Version Not Found</h1>
18
+ <p class="mb-6 text-muted-foreground">
19
+ {#if version}
20
+ The documentation version "{version}" doesn't exist.
21
+ {:else}
22
+ The documentation version you're looking for doesn't exist.
23
+ {/if}
24
+ </p>
25
+ {#if availableVersions.length > 0}
26
+ <div class="mb-6">
27
+ <p class="mb-3 text-sm text-muted-foreground">Available versions:</p>
28
+ <div class="flex flex-wrap justify-center gap-2">
29
+ {#each availableVersions as ver}
30
+ <a
31
+ href="/docs/{ver}"
32
+ class="inline-flex items-center rounded-lg border border-border bg-muted/50 px-3 py-1.5 text-sm font-medium text-foreground hover:bg-muted transition-colors"
33
+ >
34
+ {ver}
35
+ </a>
36
+ {/each}
37
+ </div>
38
+ </div>
39
+ {:else}
40
+ <a
41
+ href="/docs/v1.0.0"
42
+ class="inline-flex items-center rounded-lg bg-primary px-4 py-2 text-sm font-medium text-primary-foreground hover:bg-primary/90"
43
+ >
44
+ Go to Latest Version
45
+ </a>
46
+ {/if}
47
+ </div>
48
+ </div>
@@ -0,0 +1,7 @@
1
+ interface Props {
2
+ version?: string;
3
+ availableVersions?: string[];
4
+ }
5
+ declare const VersionNotFound: import("svelte").Component<Props, {}, "">;
6
+ type VersionNotFound = ReturnType<typeof VersionNotFound>;
7
+ export default VersionNotFound;
@@ -0,0 +1 @@
1
+ export { default as VersionNotFound } from './VersionNotFound.svelte';
@@ -0,0 +1 @@
1
+ export { default as VersionNotFound } from './VersionNotFound.svelte';