@heyo-sh/create-heyo-docs 0.2.3 → 0.4.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 (67) hide show
  1. package/deployments/cloudflare/astro/package.json +1 -1
  2. package/package.json +1 -1
  3. package/templates/astro/content/api-overview.mdx +20 -0
  4. package/templates/astro/content/assets/local-architecture.svg +22 -0
  5. package/templates/astro/content/assets/quick-reference.txt +5 -0
  6. package/templates/astro/content/changelog.mdx +38 -0
  7. package/templates/astro/content/configuration.mdx +34 -0
  8. package/templates/astro/content/essentials/callouts.mdx +16 -18
  9. package/templates/astro/content/essentials/code-blocks.mdx +7 -15
  10. package/templates/astro/content/essentials/lists.mdx +9 -13
  11. package/templates/astro/content/essentials/tables.mdx +7 -14
  12. package/templates/astro/content/essentials/tabs.mdx +10 -12
  13. package/templates/astro/content/essentials/text-styling.mdx +14 -21
  14. package/templates/astro/content/openapi-petstore.json +160 -0
  15. package/templates/astro/content/openapi.json +278 -0
  16. package/templates/astro/heyo-docs.config.ts +20 -10
  17. package/templates/astro/package.json +1 -1
  18. package/templates/astro/src/components/docs-app.tsx +1 -1
  19. package/templates/astro/src/layouts/docs-layout.astro +494 -8
  20. package/templates/astro/src/pages/[...slug].astro +1 -4
  21. package/templates/astro/src/pages/heyo-docs-internal/ai-chat.ts +20 -0
  22. package/templates/astro/src/pages/index.astro +13 -0
  23. package/templates/astro/src/styles/app.css +12 -2
  24. package/templates/astro/src/virtual.d.ts +7 -0
  25. package/templates/next/app/[[...slug]]/page.tsx +26 -5
  26. package/templates/next/app/app.css +12 -2
  27. package/templates/next/app/components/docs-app.tsx +1 -2
  28. package/templates/next/app/heyo-docs-internal/ai-chat/route.ts +15 -0
  29. package/templates/next/app/layout.tsx +411 -0
  30. package/templates/next/content/api-overview.mdx +20 -0
  31. package/templates/next/content/assets/local-architecture.svg +22 -0
  32. package/templates/next/content/assets/quick-reference.txt +5 -0
  33. package/templates/next/content/changelog.mdx +38 -0
  34. package/templates/next/content/configuration.mdx +34 -0
  35. package/templates/next/content/essentials/callouts.mdx +16 -18
  36. package/templates/next/content/essentials/code-blocks.mdx +7 -15
  37. package/templates/next/content/essentials/lists.mdx +9 -13
  38. package/templates/next/content/essentials/tables.mdx +7 -14
  39. package/templates/next/content/essentials/tabs.mdx +10 -12
  40. package/templates/next/content/essentials/text-styling.mdx +14 -21
  41. package/templates/next/content/openapi-petstore.json +160 -0
  42. package/templates/next/content/openapi.json +278 -0
  43. package/templates/next/heyo-docs.config.ts +20 -10
  44. package/templates/react-router/app/app.css +12 -2
  45. package/templates/react-router/app/root.tsx +412 -1
  46. package/templates/react-router/app/routes/ai-chat.ts +21 -0
  47. package/templates/react-router/app/routes/docs.tsx +1 -1
  48. package/templates/react-router/app/routes/home.tsx +20 -1
  49. package/templates/react-router/app/routes.ts +1 -0
  50. package/templates/react-router/app/virtual.d.ts +7 -0
  51. package/templates/react-router/content/api-overview.mdx +20 -0
  52. package/templates/react-router/content/assets/local-architecture.svg +22 -0
  53. package/templates/react-router/content/assets/quick-reference.txt +5 -0
  54. package/templates/react-router/content/changelog.mdx +38 -0
  55. package/templates/react-router/content/configuration.mdx +34 -0
  56. package/templates/react-router/content/essentials/callouts.mdx +16 -18
  57. package/templates/react-router/content/essentials/code-blocks.mdx +7 -15
  58. package/templates/react-router/content/essentials/lists.mdx +9 -13
  59. package/templates/react-router/content/essentials/tables.mdx +7 -14
  60. package/templates/react-router/content/essentials/tabs.mdx +10 -12
  61. package/templates/react-router/content/essentials/text-styling.mdx +14 -21
  62. package/templates/react-router/content/openapi-petstore.json +160 -0
  63. package/templates/react-router/content/openapi.json +278 -0
  64. package/templates/react-router/heyo-docs.config.ts +20 -10
  65. package/templates/astro/content/index.mdx +0 -22
  66. package/templates/next/content/index.mdx +0 -22
  67. package/templates/react-router/content/index.mdx +0 -22
@@ -9,12 +9,72 @@ import {
9
9
  type MetaFunction,
10
10
  } from "react-router";
11
11
  import { pathnameFromMarkdownPath } from "@heyo-sh/heyo-docs";
12
+ import { adobeAnalyticsScript } from "@heyo-sh/heyo-docs/integrations/analytics/adobe";
13
+ import { amplitudeAnalyticsScript } from "@heyo-sh/heyo-docs/integrations/analytics/amplitude";
14
+ import { clarityBootstrapScript } from "@heyo-sh/heyo-docs/integrations/analytics/clarity";
15
+ import { clearbitAnalyticsScript } from "@heyo-sh/heyo-docs/integrations/analytics/clearbit";
16
+ import { fathomAnalyticsScript } from "@heyo-sh/heyo-docs/integrations/analytics/fathom";
17
+ import {
18
+ googleAnalyticsBootstrapScript,
19
+ googleAnalyticsScript,
20
+ } from "@heyo-sh/heyo-docs/integrations/analytics/google-analytics";
21
+ import {
22
+ googleTagManagerBootstrapScript,
23
+ googleTagManagerNoScriptUrl,
24
+ } from "@heyo-sh/heyo-docs/integrations/analytics/google-tag-manager";
25
+ import { heapBootstrapScript } from "@heyo-sh/heyo-docs/integrations/analytics/heap";
26
+ import { hotjarBootstrapScript } from "@heyo-sh/heyo-docs/integrations/analytics/hotjar";
27
+ import {
28
+ logRocketBootstrapScript,
29
+ logRocketScript,
30
+ } from "@heyo-sh/heyo-docs/integrations/analytics/logrocket";
31
+ import {
32
+ mixpanelBootstrapScript,
33
+ mixpanelScript,
34
+ } from "@heyo-sh/heyo-docs/integrations/analytics/mixpanel";
35
+ import {
36
+ openpanelBootstrapScript,
37
+ openpanelScript,
38
+ } from "@heyo-sh/heyo-docs/integrations/analytics/openpanel";
39
+ import { openReplayBootstrapScript } from "@heyo-sh/heyo-docs/integrations/analytics/openreplay";
40
+ import { osanoConsentScript } from "@heyo-sh/heyo-docs/integrations/consent/osano";
41
+ import {
42
+ transcendConsentScript,
43
+ transcendGoogleConsentModeDefaultsScript,
44
+ } from "@heyo-sh/heyo-docs/integrations/consent/transcend";
45
+ import { pirschAnalyticsScript } from "@heyo-sh/heyo-docs/integrations/analytics/pirsch";
46
+ import { plausibleAnalyticsScript } from "@heyo-sh/heyo-docs/integrations/analytics/plausible";
47
+ import {
48
+ posthogApiHost,
49
+ posthogBootstrapScript,
50
+ posthogScript,
51
+ } from "@heyo-sh/heyo-docs/integrations/analytics/posthog";
52
+ import { rybbitAnalyticsScript } from "@heyo-sh/heyo-docs/integrations/analytics/rybbit";
53
+ import {
54
+ swetrixBootstrapScript,
55
+ swetrixScript,
56
+ } from "@heyo-sh/heyo-docs/integrations/analytics/swetrix";
57
+ import { chaskiqBootstrapScript } from "@heyo-sh/heyo-docs/integrations/support/chaskiq";
58
+ import { chatwootBootstrapScript } from "@heyo-sh/heyo-docs/integrations/support/chatwoot";
59
+ import {
60
+ frontChatBootstrapScript,
61
+ frontChatScript,
62
+ } from "@heyo-sh/heyo-docs/integrations/support/front";
63
+ import { intercomBootstrapScript } from "@heyo-sh/heyo-docs/integrations/support/intercom";
64
+ import { papercupsBootstrapScript } from "@heyo-sh/heyo-docs/integrations/support/papercups";
65
+ import { typebotBootstrapScript } from "@heyo-sh/heyo-docs/integrations/support/typebot";
66
+ import { umamiAnalyticsScript } from "@heyo-sh/heyo-docs/integrations/analytics/umami";
67
+ import {
68
+ zammadBootstrapScript,
69
+ zammadChatScript,
70
+ } from "@heyo-sh/heyo-docs/integrations/support/zammad";
12
71
  import type { Route } from "./+types/root";
13
72
 
14
73
  import "./app.css";
74
+ import "virtual:heyo-docs-theme.css";
15
75
  import { ThemeProvider } from "./components/theme-provider";
16
- import config from "../heyo-docs.config";
17
76
  import { getThemeScript, THEME_STORAGE_KEY } from "./lib/theme";
77
+ import { config } from "virtual:heyo-docs-config";
18
78
 
19
79
  export const meta: MetaFunction = () => {
20
80
  const canonical = config.siteUrl ? `${config.siteUrl}/` : undefined;
@@ -80,22 +140,321 @@ export const links: LinksFunction = () => [
80
140
  : []),
81
141
  ];
82
142
 
143
+ const osano = config.integrations.consent.osano
144
+ ? osanoConsentScript(config.integrations.consent.osano)
145
+ : undefined;
146
+ const transcend = config.integrations.consent.transcend
147
+ ? transcendConsentScript(config.integrations.consent.transcend)
148
+ : undefined;
149
+ const transcendGoogleConsentDefaults =
150
+ transcend &&
151
+ (config.integrations.analytics.ga4 || config.integrations.analytics.gtm)
152
+ ? transcendGoogleConsentModeDefaultsScript()
153
+ : undefined;
154
+ const adobe = config.integrations.analytics.adobe
155
+ ? adobeAnalyticsScript(config.integrations.analytics.adobe)
156
+ : undefined;
157
+ const amplitude = config.integrations.analytics.amplitude
158
+ ? amplitudeAnalyticsScript(config.integrations.analytics.amplitude)
159
+ : undefined;
160
+ const clarity = config.integrations.analytics.clarity
161
+ ? clarityBootstrapScript()
162
+ : undefined;
163
+ const clearbit = config.integrations.analytics.clearbit
164
+ ? clearbitAnalyticsScript(config.integrations.analytics.clearbit)
165
+ : undefined;
166
+ const fathom = config.integrations.analytics.fathom
167
+ ? fathomAnalyticsScript(config.integrations.analytics.fathom)
168
+ : undefined;
169
+ const googleAnalytics = config.integrations.analytics.ga4
170
+ ? googleAnalyticsScript(config.integrations.analytics.ga4)
171
+ : undefined;
172
+ const googleAnalyticsBootstrap = googleAnalytics
173
+ ? googleAnalyticsBootstrapScript()
174
+ : undefined;
175
+ const googleTagManager = config.integrations.analytics.gtm
176
+ ? googleTagManagerBootstrapScript()
177
+ : undefined;
178
+ const googleTagManagerNoScript = config.integrations.analytics.gtm
179
+ ? googleTagManagerNoScriptUrl(config.integrations.analytics.gtm)
180
+ : undefined;
181
+ const heap = config.integrations.analytics.heap
182
+ ? heapBootstrapScript()
183
+ : undefined;
184
+ const hotjar = config.integrations.analytics.hotjar
185
+ ? hotjarBootstrapScript()
186
+ : undefined;
187
+ const logRocket = config.integrations.analytics.logrocket
188
+ ? logRocketScript()
189
+ : undefined;
190
+ const logRocketBootstrap = logRocket ? logRocketBootstrapScript() : undefined;
191
+ const mixpanel = config.integrations.analytics.mixpanel
192
+ ? mixpanelScript()
193
+ : undefined;
194
+ const mixpanelBootstrap = mixpanel ? mixpanelBootstrapScript() : undefined;
195
+ const openpanel = config.integrations.analytics.openpanel
196
+ ? openpanelScript()
197
+ : undefined;
198
+ const openpanelBootstrap = openpanel ? openpanelBootstrapScript() : undefined;
199
+ const openReplay = config.integrations.analytics.openreplay
200
+ ? openReplayBootstrapScript()
201
+ : undefined;
202
+ const pirsch = config.integrations.analytics.pirsch
203
+ ? pirschAnalyticsScript(config.integrations.analytics.pirsch)
204
+ : undefined;
205
+ const plausible = config.integrations.analytics.plausible
206
+ ? plausibleAnalyticsScript(config.integrations.analytics.plausible)
207
+ : undefined;
208
+ const posthog = config.integrations.analytics.posthog
209
+ ? posthogScript(config.integrations.analytics.posthog)
210
+ : undefined;
211
+ const posthogBootstrap = posthog ? posthogBootstrapScript() : undefined;
212
+ const posthogHost = config.integrations.analytics.posthog
213
+ ? posthogApiHost(config.integrations.analytics.posthog)
214
+ : undefined;
215
+ const rybbit = config.integrations.analytics.rybbit
216
+ ? rybbitAnalyticsScript(config.integrations.analytics.rybbit)
217
+ : undefined;
218
+ const swetrix = config.integrations.analytics.swetrix
219
+ ? swetrixScript()
220
+ : undefined;
221
+ const swetrixBootstrap = swetrix ? swetrixBootstrapScript() : undefined;
222
+ const umami = config.integrations.analytics.umami
223
+ ? umamiAnalyticsScript(config.integrations.analytics.umami)
224
+ : undefined;
225
+ const intercom = config.integrations.support.intercom
226
+ ? intercomBootstrapScript()
227
+ : undefined;
228
+ const front = config.integrations.support.front ? frontChatScript() : undefined;
229
+ const frontBootstrap = front ? frontChatBootstrapScript() : undefined;
230
+ const chatwoot = config.integrations.support.chatwoot
231
+ ? chatwootBootstrapScript()
232
+ : undefined;
233
+ const chaskiq = config.integrations.support.chaskiq
234
+ ? chaskiqBootstrapScript()
235
+ : undefined;
236
+ const papercups = config.integrations.support.papercups
237
+ ? papercupsBootstrapScript()
238
+ : undefined;
239
+ const typebot = config.integrations.support.typebot
240
+ ? typebotBootstrapScript()
241
+ : undefined;
242
+ const zammad = config.integrations.support.zammad
243
+ ? zammadChatScript(config.integrations.support.zammad)
244
+ : undefined;
245
+ const zammadBootstrap = zammad ? zammadBootstrapScript() : undefined;
246
+
83
247
  export function Layout({ children }: { children: ReactNode }) {
84
248
  return (
85
249
  <html lang="en" suppressHydrationWarning>
86
250
  <head>
251
+ {transcendGoogleConsentDefaults && (
252
+ <script
253
+ dangerouslySetInnerHTML={{
254
+ __html: transcendGoogleConsentDefaults,
255
+ }}
256
+ />
257
+ )}
258
+ {transcend && (
259
+ <script data-cfasync={transcend.dataCfasync} src={transcend.src} />
260
+ )}
87
261
  <meta charSet="utf-8" />
88
262
  <meta name="viewport" content="width=device-width, initial-scale=1" />
89
263
  <meta name="color-scheme" content="light dark" />
264
+ {osano && <script src={osano.src} />}
265
+ {googleTagManager && (
266
+ <script
267
+ data-google-tag-manager-container-id={
268
+ config.integrations.analytics.gtm?.containerId
269
+ }
270
+ dangerouslySetInnerHTML={{ __html: googleTagManager }}
271
+ />
272
+ )}
90
273
  <script
91
274
  dangerouslySetInnerHTML={{
92
275
  __html: getThemeScript(THEME_STORAGE_KEY, config.mode),
93
276
  }}
94
277
  />
278
+ {adobe && <script async={adobe.async} src={adobe.src} />}
279
+ {amplitude && <script src={amplitude.src} />}
280
+ {clarity && (
281
+ <script
282
+ data-clarity-project-id={
283
+ config.integrations.analytics.clarity?.projectId
284
+ }
285
+ dangerouslySetInnerHTML={{ __html: clarity }}
286
+ />
287
+ )}
288
+ {clearbit && <script src={clearbit.src} />}
289
+ {fathom && (
290
+ <script
291
+ data-site={fathom.siteId}
292
+ data-spa={fathom.spa}
293
+ defer={fathom.defer}
294
+ src={fathom.src}
295
+ />
296
+ )}
297
+ {googleAnalytics && googleAnalyticsBootstrap && (
298
+ <>
299
+ <script async={googleAnalytics.async} src={googleAnalytics.src} />
300
+ <script
301
+ data-google-analytics-measurement-id={
302
+ config.integrations.analytics.ga4?.measurementId
303
+ }
304
+ dangerouslySetInnerHTML={{ __html: googleAnalyticsBootstrap }}
305
+ />
306
+ </>
307
+ )}
308
+ {heap && (
309
+ <script
310
+ data-heap-environment-id={
311
+ config.integrations.analytics.heap?.environmentId
312
+ }
313
+ dangerouslySetInnerHTML={{ __html: heap }}
314
+ />
315
+ )}
316
+ {hotjar && (
317
+ <script
318
+ data-hotjar-site-id={config.integrations.analytics.hotjar?.siteId}
319
+ data-hotjar-snippet-version={
320
+ config.integrations.analytics.hotjar?.snippetVersion
321
+ }
322
+ dangerouslySetInnerHTML={{ __html: hotjar }}
323
+ />
324
+ )}
325
+ {logRocket && logRocketBootstrap && (
326
+ <>
327
+ <script crossOrigin={logRocket.crossOrigin} src={logRocket.src} />
328
+ <script
329
+ data-logrocket-app-id={
330
+ config.integrations.analytics.logrocket?.appId
331
+ }
332
+ dangerouslySetInnerHTML={{ __html: logRocketBootstrap }}
333
+ />
334
+ </>
335
+ )}
336
+ {mixpanel && mixpanelBootstrap && (
337
+ <>
338
+ <script src={mixpanel.src} />
339
+ <script
340
+ data-mixpanel-project-token={
341
+ config.integrations.analytics.mixpanel?.projectToken
342
+ }
343
+ dangerouslySetInnerHTML={{ __html: mixpanelBootstrap }}
344
+ />
345
+ </>
346
+ )}
347
+ {openpanel && openpanelBootstrap && (
348
+ <>
349
+ <script
350
+ data-openpanel-api-url={
351
+ config.integrations.analytics.openpanel?.apiUrl
352
+ }
353
+ data-openpanel-client-id={
354
+ config.integrations.analytics.openpanel?.clientId
355
+ }
356
+ dangerouslySetInnerHTML={{ __html: openpanelBootstrap }}
357
+ />
358
+ <script
359
+ async={openpanel.async}
360
+ defer={openpanel.defer}
361
+ src={openpanel.src}
362
+ />
363
+ </>
364
+ )}
365
+ {openReplay && (
366
+ <script
367
+ data-openreplay-ingest-point={
368
+ config.integrations.analytics.openreplay?.ingestPoint
369
+ }
370
+ data-openreplay-project-key={
371
+ config.integrations.analytics.openreplay?.projectKey
372
+ }
373
+ dangerouslySetInnerHTML={{ __html: openReplay }}
374
+ />
375
+ )}
376
+ {pirsch && (
377
+ <script
378
+ data-code={pirsch.code}
379
+ defer={pirsch.defer}
380
+ src={pirsch.src}
381
+ />
382
+ )}
383
+ {plausible && (
384
+ <script
385
+ data-domain={plausible.domain}
386
+ defer={plausible.defer}
387
+ src={plausible.src}
388
+ />
389
+ )}
390
+ {posthog && posthogBootstrap && posthogHost && (
391
+ <>
392
+ <script src={posthog.src} />
393
+ <script
394
+ data-posthog-api-host={posthogHost}
395
+ data-posthog-project-api-key={
396
+ config.integrations.analytics.posthog?.projectApiKey
397
+ }
398
+ dangerouslySetInnerHTML={{ __html: posthogBootstrap }}
399
+ />
400
+ </>
401
+ )}
402
+ {rybbit && (
403
+ <script
404
+ data-site-id={rybbit.siteId}
405
+ defer={rybbit.defer}
406
+ src={rybbit.src}
407
+ />
408
+ )}
409
+ {umami && (
410
+ <script
411
+ data-website-id={umami.websiteId}
412
+ defer={umami.defer}
413
+ src={umami.src}
414
+ />
415
+ )}
416
+ {chaskiq && (
417
+ <script
418
+ data-chaskiq-app-id={config.integrations.support.chaskiq?.appId}
419
+ data-chaskiq-base-url={config.integrations.support.chaskiq?.baseUrl}
420
+ data-chaskiq-ws-url={config.integrations.support.chaskiq?.wsUrl}
421
+ dangerouslySetInnerHTML={{ __html: chaskiq }}
422
+ />
423
+ )}
424
+ {papercups && (
425
+ <script
426
+ data-papercups-base-url={
427
+ config.integrations.support.papercups?.baseUrl
428
+ }
429
+ data-papercups-inbox={config.integrations.support.papercups?.inbox}
430
+ data-papercups-token={config.integrations.support.papercups?.token}
431
+ dangerouslySetInnerHTML={{ __html: papercups }}
432
+ />
433
+ )}
434
+ {typebot && (
435
+ <script
436
+ data-heyo-typebot
437
+ data-typebot-api-host={config.integrations.support.typebot?.apiHost}
438
+ data-typebot-id={config.integrations.support.typebot?.typebot}
439
+ dangerouslySetInnerHTML={{ __html: typebot }}
440
+ type="module"
441
+ />
442
+ )}
95
443
  <Meta />
96
444
  <Links />
97
445
  </head>
98
446
  <body>
447
+ {googleTagManagerNoScript && (
448
+ <noscript>
449
+ <iframe
450
+ height="0"
451
+ src={googleTagManagerNoScript}
452
+ style={{ display: "none", visibility: "hidden" }}
453
+ title="Google Tag Manager"
454
+ width="0"
455
+ />
456
+ </noscript>
457
+ )}
99
458
  <ThemeProvider
100
459
  defaultTheme={config.mode}
101
460
  storageKey={THEME_STORAGE_KEY}
@@ -104,6 +463,58 @@ export function Layout({ children }: { children: ReactNode }) {
104
463
  <ScrollRestoration />
105
464
  <Scripts />
106
465
  </ThemeProvider>
466
+ {swetrix && swetrixBootstrap && (
467
+ <>
468
+ <script defer={swetrix.defer} src={swetrix.src} />
469
+ <script
470
+ data-swetrix-api-url={
471
+ config.integrations.analytics.swetrix?.apiUrl
472
+ }
473
+ data-swetrix-project-id={
474
+ config.integrations.analytics.swetrix?.projectId
475
+ }
476
+ dangerouslySetInnerHTML={{ __html: swetrixBootstrap }}
477
+ />
478
+ </>
479
+ )}
480
+ {intercom && (
481
+ <script
482
+ data-intercom-app-id={config.integrations.support.intercom?.appId}
483
+ data-intercom-api-base={
484
+ config.integrations.support.intercom?.apiBase
485
+ }
486
+ dangerouslySetInnerHTML={{ __html: intercom }}
487
+ />
488
+ )}
489
+ {front && frontBootstrap && (
490
+ <>
491
+ <script src={front.src} />
492
+ <script
493
+ data-front-chat-id={config.integrations.support.front?.chatId}
494
+ dangerouslySetInnerHTML={{ __html: frontBootstrap }}
495
+ />
496
+ </>
497
+ )}
498
+ {chatwoot && (
499
+ <script
500
+ data-chatwoot-base-url={
501
+ config.integrations.support.chatwoot?.baseUrl
502
+ }
503
+ data-chatwoot-website-token={
504
+ config.integrations.support.chatwoot?.websiteToken
505
+ }
506
+ dangerouslySetInnerHTML={{ __html: chatwoot }}
507
+ />
508
+ )}
509
+ {zammad && zammadBootstrap && (
510
+ <>
511
+ <script src={zammad.src} />
512
+ <script
513
+ data-zammad-chat-id={config.integrations.support.zammad?.chatId}
514
+ dangerouslySetInnerHTML={{ __html: zammadBootstrap }}
515
+ />
516
+ </>
517
+ )}
107
518
  </body>
108
519
  </html>
109
520
  );
@@ -0,0 +1,21 @@
1
+ import { createAiChatResponse } from "@heyo-sh/heyo-docs/ai";
2
+ import type { ActionFunctionArgs } from "react-router";
3
+
4
+ import config from "../../heyo-docs.config";
5
+ import { pages } from "virtual:heyo-docs-content";
6
+ import { pages as markdownPages } from "virtual:heyo-docs-content/server";
7
+
8
+ export async function action({ request }: ActionFunctionArgs) {
9
+ if (request.method !== "POST")
10
+ return new Response("Method Not Allowed", {
11
+ headers: { Allow: "POST" },
12
+ status: 405,
13
+ });
14
+
15
+ return createAiChatResponse(request, {
16
+ ai: config.ai,
17
+ markdownPages,
18
+ pages,
19
+ title: config.title,
20
+ });
21
+ }
@@ -16,9 +16,9 @@ import {
16
16
  } from "react-router";
17
17
  import { forwardRef, type ComponentPropsWithoutRef } from "react";
18
18
 
19
- import config from "../../heyo-docs.config";
20
19
  import { iconSet } from "../heyo-docs-icons";
21
20
  import { useTheme } from "../components/theme-provider";
21
+ import { config } from "virtual:heyo-docs-config";
22
22
  import { pages } from "virtual:heyo-docs-content";
23
23
  import { openApiDocuments } from "virtual:heyo-docs-openapi";
24
24
  import { openApiEndpoints } from "virtual:heyo-docs-openapi/index";
@@ -1 +1,20 @@
1
- export { default, loader, meta, ErrorBoundary } from "./docs";
1
+ import { createDocsModel, navigationPages } from "@heyo-sh/heyo-docs";
2
+ import { redirect } from "react-router";
3
+
4
+ import { config } from "virtual:heyo-docs-config";
5
+ import { pages } from "virtual:heyo-docs-content";
6
+
7
+ export function loader() {
8
+ const firstPage = createDocsModel(config, pages)
9
+ .navigation.flatMap((group) => navigationPages(group.sections))
10
+ .at(0);
11
+
12
+ if (!firstPage)
13
+ throw new Response("No local documentation page is configured.", {
14
+ status: 404,
15
+ });
16
+
17
+ return redirect(firstPage.slug);
18
+ }
19
+
20
+ export { default, ErrorBoundary } from "./docs";
@@ -9,5 +9,6 @@ export default [
9
9
  route("llms-full.txt", "routes/llms-full.ts"),
10
10
  route("__heyo-docs/markdown/*", "routes/markdown.ts"),
11
11
  route("heyo-docs-internal/openapi-request", "routes/openapi-request.ts"),
12
+ route("heyo-docs-internal/ai-chat", "routes/ai-chat.ts"),
12
13
  route("*", "routes/page.tsx"),
13
14
  ] satisfies RouteConfig;
@@ -3,6 +3,13 @@ declare module "virtual:heyo-docs-content" {
3
3
  export const pages: DocsPage[];
4
4
  }
5
5
 
6
+ declare module "virtual:heyo-docs-config" {
7
+ import type { HeyoDocsConfig } from "@heyo-sh/heyo-docs";
8
+ export const config: HeyoDocsConfig;
9
+ }
10
+
11
+ declare module "virtual:heyo-docs-theme.css";
12
+
6
13
  declare module "virtual:heyo-docs-content/server" {
7
14
  import type { MarkdownPage } from "@heyo-sh/heyo-docs";
8
15
  export const pages: MarkdownPage[];
@@ -0,0 +1,20 @@
1
+ ---
2
+ title: API overview
3
+ description: Learn how to authenticate and explore the API reference.
4
+ ---
5
+
6
+ # API overview
7
+
8
+ The API reference is generated from `openapi.json`. Use the endpoint pages to
9
+ enter parameters, send a request, and copy a cURL or JavaScript example.
10
+
11
+ ## Authentication
12
+
13
+ The example API uses a Bearer token. Enter it once on any protected endpoint;
14
+ Heyo Docs keeps it in this browser while you move between API pages.
15
+
16
+ ## Custom pages first
17
+
18
+ This ordinary MDX page belongs to the OpenAPI group. Its section is configured
19
+ before the generated endpoint sections, so it always appears at the top of the
20
+ sidebar.
@@ -0,0 +1,22 @@
1
+ <svg xmlns="http://www.w3.org/2000/svg" width="960" height="360" viewBox="0 0 960 360" fill="none">
2
+ <rect width="960" height="360" rx="24" fill="#F7F7F8"/>
3
+ <g fill="#FFFFFF" stroke="#D4D4D8" stroke-width="2">
4
+ <rect x="72" y="108" width="220" height="144" rx="18"/>
5
+ <rect x="370" y="108" width="220" height="144" rx="18"/>
6
+ <rect x="668" y="108" width="220" height="144" rx="18"/>
7
+ </g>
8
+ <g fill="#18181B" font-family="Arial, sans-serif" text-anchor="middle">
9
+ <text x="182" y="166" font-size="17" font-weight="700">Content</text>
10
+ <text x="182" y="194" font-size="14" fill="#71717A">MDX and assets</text>
11
+ <text x="480" y="166" font-size="17" font-weight="700">Build</text>
12
+ <text x="480" y="194" font-size="14" fill="#71717A">Vite bundles files</text>
13
+ <text x="778" y="166" font-size="17" font-weight="700">Documentation</text>
14
+ <text x="778" y="194" font-size="14" fill="#71717A">Static output</text>
15
+ </g>
16
+ <g stroke="#71717A" stroke-linecap="round" stroke-width="2">
17
+ <path d="M314 180h34"/>
18
+ <path d="m340 172 8 8-8 8"/>
19
+ <path d="M612 180h34"/>
20
+ <path d="m638 172 8 8-8 8"/>
21
+ </g>
22
+ </svg>
@@ -0,0 +1,5 @@
1
+ Heyo Docs quick reference
2
+
3
+ - Put MDX pages and local assets in content.
4
+ - Use a relative path to bundle an image or downloadable file.
5
+ - Use /path for assets in public.
@@ -0,0 +1,38 @@
1
+ ---
2
+ title: Changelog
3
+ description: Mock release notes for the Heyo Docs example.
4
+ ---
5
+
6
+ # Changelog
7
+
8
+ <Update label="April 2026" tags={["New", "Documentation"]}>
9
+
10
+ ## Starter documentation
11
+
12
+ New projects and runnable examples now include a structured Quickstart, basic
13
+ configuration guide, deployment overview, and essential writing patterns.
14
+
15
+ ## Square API group
16
+
17
+ The example navigation now keeps the pinned Square OpenAPI schema in its own
18
+ group, making large-schema behaviour easy to inspect.
19
+
20
+ </Update>
21
+
22
+ <Update label="March 2026" tags={["Improved", "Developer experience"]}>
23
+
24
+ ## Clearer navigation
25
+
26
+ External documentation links can display an icon, and sidebar groups now keep
27
+ onboarding, API reference, and release notes separate.
28
+
29
+ </Update>
30
+
31
+ <Update label="February 2026" tags={["Fixed"]}>
32
+
33
+ ## More predictable previews
34
+
35
+ Preview builds now validate configured routes before mock release notes are
36
+ published.
37
+
38
+ </Update>
@@ -64,6 +64,40 @@ The order is meaningful: it controls the sidebar and the previous/next links at
64
64
  the end of each article. Use a page object with `title` and `src` when a
65
65
  sidebar entry should point to a page outside the local documentation.
66
66
 
67
+ ## AI chat
68
+
69
+ Add `ai.chat` to enable a documentation-aware chat. `openai`, `claude`, and `grok`
70
+ use the OpenAI, Anthropic, and xAI adapters respectively. Keep the key in a
71
+ server environment variable; Heyo Docs sends it only from the chat endpoint.
72
+
73
+ <CodeBlock language="ts" title="heyo-docs.config.ts">
74
+ {`ai: {
75
+ chat: {
76
+ provider: "openai",
77
+ key: process.env.OPENAI_API_KEY!,
78
+ model: "gpt-5-mini",
79
+ variant: "right", // "center" shows the compact prompt first
80
+ icon: "chat",
81
+ text: "AI Chat",
82
+ name: "Docs Assistant", // name shown in the drawer and message labels
83
+ placeholder: "Ask AI about the docs", // used in the compact prompt and drawer
84
+ },
85
+ },`}
86
+ </CodeBlock>
87
+
88
+ `provider`, `key`, and `model` are required. The model must be an actual model
89
+ identifier, not the provider name. `variant` defaults to `right`. `name`
90
+ defaults to `AI`; it is used for the drawer title and the assistant's message
91
+ label. `placeholder` defaults to
92
+ `Ask AI about the docs` and is shared by the compact prompt and drawer input.
93
+ The drawer stays open while
94
+ readers navigate between documentation pages and does not block the rest of the
95
+ page.
96
+
97
+ Its chrome follows the selected documentation theme. For example, `grain` uses
98
+ a full-height right panel with a left border, while the other themes keep a
99
+ floating panel treatment.
100
+
67
101
  ## Verify the result
68
102
 
69
103
  Run the project's typecheck and build commands after changing configuration.