Skip to content

feat(onboarding): add Storybook components#2564

Draft
elizabetdev wants to merge 12 commits into
mainfrom
elizabet/onboarding-storybook-components
Draft

feat(onboarding): add Storybook components#2564
elizabetdev wants to merge 12 commits into
mainfrom
elizabet/onboarding-storybook-components

Conversation

@elizabetdev

@elizabetdev elizabetdev commented Jul 1, 2026

Copy link
Copy Markdown
Contributor

🚧 WIP / Draft — not ready for review yet. Opening early for visibility.

Summary

First of two PRs for the redesigned onboarding experience. This PR is presentational only — it adds the reusable building blocks and their Storybook stories, with no changes to app behavior or routing. The /getting-started page that wires these into the app (plus the OSS/self-managed/fully-managed flows) will follow in a separate PR, once this one merges.

What's included

  • OnboardingAccordion — stepper card with 3-state status badges/circles (Completed / In progress / Not started), a compact header progress ring, and a "remove from sidebar" footer affordance. Stories cover the OSS, self-managed, and fully-managed flows.
  • SummaryRow — compact, icon-led status row (check circle + status badge, optional action/footer slots) used for nested setup items like connect / data sources / collector setup.
  • components/Integrations/ — reusable integrations module (not onboarding-specific):
    • IntegrationsDrawer — right-side drawer with searchable, categorized integration tiles (languages, frameworks, infrastructure, cloud, collectors). Fully prop-driven (opened/onClose/endpoint/apiKey/initialCategory), showcased in Storybook and used by the OnboardingAccordion stories.
    • Docs rendered from the source, not scraped. Tiles with a dedicated docs page open an inline setup guide rendered directly from the ClickStack docs' own markdown — the SDKs/frameworks plus kubernetes, nginx, kafka, aws, opentelemetry, and vector (via the sdks / integration-examples / ingesting-data pages in ClickHouse/mintlify-docs-dev). Tiles without a page still deep-link out.
    • No more endpoint/key substitution. Snippets are shown verbatim from the docs; the guide surfaces the Connection panel (endpoint + ingestion key) and a note telling the user to replace the docs' placeholder values with theirs. "View full docs" links use each page's frontmatter slug.
    • useIntegrationDoc + IntegrationDocMarkdown — fetch an integration's markdown at render time and render it (remark-gfm tables, copy-paste code blocks). Kept decoupled from the drawer so a future full integrations page can render the same content.
    • integrationsCatalog — the catalog backing the tiles; each inline item carries a docSource pointing at its markdown, with docSourceUrl as the single place to swap sources (e.g. to the docs site's .md endpoint once it's public).
  • LogoBadge — theme-aware brand logo badge; adds a --logo-badge-shadow design token to both the hyperdx and clickstack themes.
  • Storybook font fix — Mantine renders Drawers/Modals/Tooltips in a portal on document.body, outside the decorator wrapper, so they fell back to the browser default font. The font className is now also applied to <html> (mirroring pages/_app.tsx) so portal content inherits it.
  • docs/clickstack-docs-quickstart-proposal.md — proposal to the docs team for a stable per-page .md endpoint, standard placeholder tokens, and lightweight structured frontmatter (category/signals) to power the drawer and a future integrations page (non-blocking).
  • Storybook stories now use the brand SVGs in public/integrations instead of react-icons (dependency removed); adds remark-gfm; switches the root app:storybook script to yarn workspace @hyperdx/app storybook.

Why split this out

Keeping the pure presentational components + Storybook separate from the app wiring/migration makes both PRs smaller and easier to review. There is no user-facing behavior change here.

Follow-ups / notes

  • We read the raw markdown from GitHub for now because the docs site only serves per-page .md behind the Mintlify preview flag; swapping to the public .md endpoint is a one-line change in docSourceUrl (see the proposal doc).
  • docker, gcp, and azure still deep-link out — they don't have a dedicated docs page yet.

Test plan

  • yarn workspace @hyperdx/app storybook — review the OnboardingAccordion, SummaryRow, IntegrationsDrawer, and LogoBadge stories
  • In the OnboardingAccordion "Send telemetry" stories, click "Browse integration guides" / "Language SDKs" and confirm the real IntegrationsDrawer opens on the right category
  • Open the IntegrationsDrawer story and open a guide (e.g. Browser, Kubernetes, Vector); confirm it renders from the docs (headings/tables/code) and shows the Connection panel + "replace the endpoint and ingestion key" note — snippets are not substituted
  • Confirm Infrastructure/Cloud/Collectors tiles with a page (kubernetes, nginx, kafka, aws, opentelemetry, vector) open inline, while docker/gcp/azure open the docs in a new tab
  • Open a Drawer story and confirm the font matches the app (portal font fix)
  • Toggle light/dark theme and confirm LogoBadge shadow + public/integrations logos render correctly in both hyperdx and clickstack themes
  • make ci-lint passes

Add the presentational building blocks for the redesigned onboarding
experience, showcased in Storybook (no app behavior change yet):

- OnboardingAccordion: stepper card with status badges/circles and a
  progress ring
- SummaryRow: compact status row (check circle + status badge) for nested
  setup items
- LogoBadge: theme-aware brand logo badge (adds --logo-badge-shadow token)

Also fixes Storybook so Drawer/Modal portals inherit the app font (applied
to <html>, matching pages/_app.tsx), and adds the react-icons dependency
used by the stories.

These components are presentational only; the /getting-started page that
wires them into the app follows in a separate PR.

Co-authored-by: Cursor <cursoragent@cursor.com>
@changeset-bot

changeset-bot Bot commented Jul 1, 2026

Copy link
Copy Markdown

⚠️ No Changeset found

Latest commit: dd54110

Merging this PR will not cause a version bump for any packages. If these changes should not result in a new version, you're good to go. If these changes should result in a version bump, you need to add a changeset.

This PR includes no changesets

When changesets are added to this PR, you'll see the packages that this PR includes changesets for and the associated semver types

Click here to learn what changesets are, and how to add one.

Click here if you're a maintainer who wants to add a changeset to this PR

@vercel

vercel Bot commented Jul 1, 2026

Copy link
Copy Markdown

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated (UTC)
hyperdx-oss Ready Ready Preview, Comment Jul 9, 2026 10:43am
hyperdx-storybook Ready Ready Preview, Comment Jul 9, 2026 10:43am

Request Review

@greptile-apps

greptile-apps Bot commented Jul 1, 2026

Copy link
Copy Markdown
Contributor

Greptile Summary

This PR is presentational-only — it adds the reusable building blocks (OnboardingAccordion, SummaryRow, IntegrationsDrawer, LogoBadge) and their Storybook stories ahead of the routing/wiring PR. No app behavior or page routing is changed.

  • OnboardingAccordion — stepper card with 3-state status badges/circles, a compact header progress ring, and controlled/uncontrolled expand logic; correctly wires aria-expanded on the toggle button.
  • IntegrationsDrawer — right-side drawer with searchable, categorized integration tiles; items with a docSource open an inline guide rendered from raw MDX fetched from raw.githubusercontent.com, while others deep-link to docs.
  • LogoBadge / SummaryRow — theme-aware brand tile and compact status-row primitives backed by new --logo-badge-shadow design tokens in both themes.

Confidence Score: 5/5

Pure presentational addition with no routing or data-mutation changes; safe to merge.

All new components are Storybook-only for now with no production routing wired up. The MDX fetching, catalog lookups, and accordion state management are all straightforward and handle edge cases (missing items, network errors, uncontrolled/controlled mode) correctly. The one stylistic concern — a hardcoded brand name in the drawer title — is a cosmetic issue that won't affect any production user until the follow-up wiring PR ships.

IntegrationsDrawer.tsx — the drawer title hardcodes "ClickStack" with no prop override, which will need to be addressed before the component is used in a HyperDX-branded context.

Important Files Changed

Filename Overview
packages/app/src/components/Integrations/IntegrationsDrawer.tsx Thin wrapper around DrawerContent; safe except for the hardcoded "ClickStack" brand name in the header.
packages/app/src/components/Integrations/DrawerContent.tsx Stateful drawer body with search/category filtering; logic is correct and re-mounts cleanly on open/close.
packages/app/src/components/Integrations/GuideView.tsx Renders a single integration's setup guide; handles undefined item and error/loading states gracefully.
packages/app/src/components/Integrations/useIntegrationDoc.ts React Query hook that fetches and parses MDX from raw.githubusercontent.com; frontmatter stripping and MDX-to-CommonMark cleaning look correct.
packages/app/src/components/Integrations/integrationsCatalog.tsx Static catalog of integration items and categories; helper functions are straightforward and correctly typed.
packages/app/src/components/Integrations/IntegrationDocMarkdown.tsx react-markdown renderer with copy-able code blocks; no dangerouslySetInnerHTML/rehype-raw so XSS risk is absent.
packages/app/src/components/OnboardingAccordion/OnboardingAccordion.tsx Controlled/uncontrolled accordion with correct step-toggle logic; accessible button wrapping and aria-expanded usage look good.
packages/app/src/components/GettingStarted/SummaryRow.tsx Presentational status-row component; exports StatusCircle, StatusBadge, CheckCircle, StatusPill cleanly.
packages/app/src/components/LogoBadge/LogoBadge.tsx Theme-aware badge tile with dashed/solid modes; shadow driven by --logo-badge-shadow design token.
packages/app/.storybook/preview.tsx Adds font className to html element to fix portal inheritance; QueryClient is freshly initialized per-story mount.

Flowchart

%%{init: {'theme': 'neutral'}}%%
flowchart TD
    OA[OnboardingAccordion] --> SR[SummaryRow]
    OA --> ID[IntegrationsDrawer]
    ID --> DC[DrawerContent]
    DC --> CS[ConnectionSnippet]
    DC --> IT[ItemTile / CategorySection]
    IT -- hasGuide → openGuide --> GV[GuideView]
    IT -- no guide --> ExtLink[External docs link]
    GV --> CS
    GV --> UID[useIntegrationDoc]
    UID -- fetch MDX --> GH[(raw.githubusercontent.com)]
    GV --> IDM[IntegrationDocMarkdown]
    LB[LogoBadge] --> IT
    LB --> OA
Loading
%%{init: {'theme': 'base', 'themeVariables': {"darkMode": true, "background": "#0d1117", "primaryColor": "#21262d", "primaryTextColor": "#e6edf3", "primaryBorderColor": "#8b949e", "lineColor": "#8b949e", "textColor": "#e6edf3", "edgeLabelBackground": "#161b22", "actorBkg": "#21262d", "actorBorder": "#8b949e", "actorTextColor": "#e6edf3", "actorLineColor": "#8b949e", "signalColor": "#8b949e", "signalTextColor": "#e6edf3", "noteBkgColor": "#373320", "noteBorderColor": "#d4a72c", "noteTextColor": "#f0e6c0", "labelBoxBkgColor": "#21262d", "labelBoxBorderColor": "#8b949e", "labelTextColor": "#e6edf3", "loopTextColor": "#e6edf3", "activationBkgColor": "#30363d", "activationBorderColor": "#8b949e"}}}%%
flowchart TD
    OA[OnboardingAccordion] --> SR[SummaryRow]
    OA --> ID[IntegrationsDrawer]
    ID --> DC[DrawerContent]
    DC --> CS[ConnectionSnippet]
    DC --> IT[ItemTile / CategorySection]
    IT -- hasGuide → openGuide --> GV[GuideView]
    IT -- no guide --> ExtLink[External docs link]
    GV --> CS
    GV --> UID[useIntegrationDoc]
    UID -- fetch MDX --> GH[(raw.githubusercontent.com)]
    GV --> IDM[IntegrationDocMarkdown]
    LB[LogoBadge] --> IT
    LB --> OA
Loading

Reviews (9): Last reviewed commit: "feat(integrations): render setup docs fr..." | Re-trigger Greptile

Comment on lines +32 to +36
'in-progress': {
label: 'In progress',
fg: 'var(--color-bg-warning)',
bg: 'color-mix(in srgb, var(--color-bg-warning) 18%, transparent)',
},

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 The in-progress entry uses --color-bg-warning (a background-intent token) as the text/foreground color. This works today but is semantically incorrect — if the warning background token is ever adjusted to a color that's only safe on dark surfaces, the badge text will lose contrast. There is no --color-text-warning token defined in either theme, so the closest correct substitute is the amber value expressed directly, or a dedicated text token added alongside the other --color-text-* tokens.

Suggested change
'in-progress': {
label: 'In progress',
fg: 'var(--color-bg-warning)',
bg: 'color-mix(in srgb, var(--color-bg-warning) 18%, transparent)',
},
'in-progress': {
label: 'In progress',
// TODO: replace with --color-text-warning once that token is added to each theme.
fg: 'var(--color-bg-warning)',
bg: 'color-mix(in srgb, var(--color-bg-warning) 18%, transparent)',
},

Fix in Claude Code Fix in Conductor Fix in Cursor Fix in Codex

Comment thread packages/app/src/components/LogoBadge/LogoBadge.tsx
Comment thread package.json
@github-actions

github-actions Bot commented Jul 1, 2026

Copy link
Copy Markdown
Contributor

E2E Test Results

All tests passed • 171 passed • 2 skipped • 1053s

Status Count
✅ Passed 171
❌ Failed 0
⚠️ Flaky 0
⏭️ Skipped 2

Tests ran across 3 shards in parallel.

View full report →

Add the presentational IntegrationsDrawer used by the "Send telemetry" step,
plus a Storybook story:

- IntegrationsDrawer: right-side drawer with searchable, categorized
  integration tiles (languages, frameworks, infrastructure, cloud, collectors)
- SDK/framework tiles open inline copy-paste setup guides with the team's
  endpoint + ingestion key substituted in; other tiles deep-link to docs
- integrationsCatalog + integrationGuides.generated.json back the tiles/guides

The drawer is fully prop-driven (opened/onClose/endpoint/apiKey); the
getting-started page wiring and the guide generator script land in a
follow-up PR.

Co-authored-by: Cursor <cursoragent@cursor.com>
@github-actions

github-actions Bot commented Jul 1, 2026

Copy link
Copy Markdown
Contributor

Knip - Unused Code Analysis

🔴 2 issues found

Unused exports (1)

  • packages/app/src/components/Integrations/useIntegrationDoc.ts:parseIntegrationDoc

Unused exported types (1)

  • packages/app/src/components/Integrations/index.ts:IntegrationsDrawerProps

Knip finds unused files, dependencies, and exports in your codebase.
Run yarn knip locally to see full details.

…stories

The integrations drawer isn't onboarding-specific, so move it out of the
GettingStarted folder to a shared components/IntegrationsDrawer/ module
(carrying its integrationsCatalog + generated guides, re-exported via index.ts
so other surfaces can reuse it).

Wire the OnboardingAccordion "Browse integration guides" / "Language SDKs"
links to the real IntegrationsDrawer instead of the previous mock docs drawer,
opening the languages category from the SDKs link. Removes the now-unused mock
(IntegrationsDocsDrawer/DocRow and its static lists).

Co-authored-by: Cursor <cursoragent@cursor.com>
Use the broader components/Integrations/ name (was IntegrationsDrawer/) so the
module can house more integration-related surfaces beyond the drawer.

Co-authored-by: Cursor <cursoragent@cursor.com>
Add the generator that produces components/Integrations/
integrationGuides.generated.json from the ClickStack SDK MDX
(yarn generate:integration-guides), pointed at the new Integrations module
path, plus the package.json script entry.

Include the "machine-readable Quickstart contract" proposal that motivates
making the docs structured so the generator can drop its heuristics; adapted
to reference this PR's Integrations module and to note it's non-blocking.

Co-authored-by: Cursor <cursoragent@cursor.com>
Add an optional `logo` field to catalog items that points to a brand SVG in
public/integrations/ and takes precedence over the react-icons glyph/monogram,
for logos react-icons doesn't carry. Ship the Vector logo as the first one and
switch Vector from its "Vec" monogram to the SVG.

Co-authored-by: Cursor <cursoragent@cursor.com>
Add the brand SVGs under public/integrations/ and point every catalog item at
its <id>.svg, replacing the react-icons glyphs and text monograms. Render logos
on a white tile in both themes since several brand SVGs use near-black marks
meant for a light background.

Co-authored-by: Cursor <cursoragent@cursor.com>
Comment thread packages/app/src/components/Integrations/GuideView.tsx
…rows

Replace the two plain endpoint/ingestion-key copy rows at the top of the
integrations drawer with a ConnectionSnippet card that mirrors the send-telemetry
connection panel (monospace endpoint/api-key block, reveal-key toggle, copy) —
scoped to just the URL view, since the collector/env-var/AI-agent tabs aren't
relevant when picking an integration.

Co-authored-by: Cursor <cursoragent@cursor.com>
…tiles

- Add a signals map (logs/traces/metrics) per integration and show a
  "This guide integrates: [chips]" row in the setup guide.
- Mark tiles that deep-link out with a corner external-link icon and an
  "Opens the docs in a new tab" tooltip, so it's clear which open externally
  vs. show an inline guide.

Co-authored-by: Cursor <cursoragent@cursor.com>
Mantine's Drawer body shrinks its right padding to reserve scrollbar
space, which reads as missing right padding on overlay-scrollbar
systems. Override paddingInlineEnd so left/right padding match.

Co-authored-by: Cursor <cursoragent@cursor.com>
@Blargian

Blargian commented Jul 2, 2026

Copy link
Copy Markdown

@elizabetdev you mentioned it in the call, but I suspect trying to extract the structure from the docs will be a big challenge - especially in the present state where there isn't a strong structure across files.

I would suggest we find a way to render the markdown in the product directly from the .md page that the Mintlify docs site serves.

For example:

  • Navigate to clickhouse.com/docs?mintlify_preview=1
  • Hard refresh the browser (you should see the new site)
  • Navigate to https://clickhouse.com/docs/integrations/language-clients/js (hard refresh if you get any errors or see the current docs site)
  • Once the page is open, you can append .md to this url -> https://clickhouse.com/docs/integrations/language-clients/js.md and it will serve the markdown directly.

We could give you pages with the structure you need, and it would then be a case of figuring out how we render this markdown within the product. It doesn't look like the page front-matter is served. Compare: https://github.com/ClickHouse/mintlify-docs-dev/blob/main/integrations/language-clients/js.mdx

… stories

Re-wire onDismiss into the story flows so the "Remove from sidebar"
footer link renders again, and override paddingInlineEnd on the
collector-setup, connection, and data-source drawers so their body
padding is symmetric (Mantine reserves scrollbar space on the right).

Co-authored-by: Cursor <cursoragent@cursor.com>
Replace the build-time guide generator + committed JSON with runtime
rendering of the docs' own markdown, and stop substituting the endpoint /
ingestion key into the snippets:

- useIntegrationDoc fetches each integration's markdown straight from the
  ClickStack docs repo; IntegrationDocMarkdown renders it (remark-gfm for
  tables, copy-able code blocks)
- GuideView shows the connection panel plus a note to replace the
  placeholder endpoint/key, instead of rewriting the snippets
- wire inline guides for kubernetes, nginx, kafka, aws, opentelemetry and
  vector via the integration-examples / ingesting-data docs; "View full
  docs" uses each page's frontmatter slug
- drop the generator script, generated JSON, and the
  generate:integration-guides package script

Also swap the Storybook brand glyphs to public/integrations SVGs and remove
the react-icons dependency.

Co-authored-by: Cursor <cursoragent@cursor.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants