
userTourKit vs React Joyride: headless tours for React (2026)
React Joyride has been the default product tour library for React since 2016. It has 603K weekly npm downloads and a decade of production usage behind it. userTourKit shipped in 2025 with a different thesis: give developers tour logic without any UI opinions. Both libraries solve the same problem, but they approach it from opposite directions. This comparison breaks down the tradeoffs with real data so you can pick the right tool for your project.
Bias disclosure: We built userTourKit. Every claim below is verifiable against npm, GitHub, and bundlephobia. We have tried to be fair to React Joyride throughout.
npm install @tourkit/core @tourkit/reactQuick verdict
Choose userTourKit if you maintain a design system or component library and want a headless tour engine that renders through your existing components. The core is under 8KB gzipped, ships full TypeScript types, and supports React 19 natively. Choose React Joyride if you need a drop-in solution with pre-built tooltips and don't want to write rendering logic yourself. React Joyride v3 added TypeScript support and modernized internals, making it a solid choice for teams that prefer convention over configuration.
Comparison at a glance
| Feature | userTourKit | React Joyride |
|---|---|---|
| Architecture | Headless (BYOUI) | Opinionated with built-in UI |
| Bundle size (gzipped) | Under 8KB core + 12KB react | ~30KB |
| React 19 support | ✅ Native | ✅ v3 only |
| TypeScript | ✅ Strict mode, full types | ✅ Built-in (v3) |
| License | MIT (core) / Proprietary (pro) | MIT |
| Pricing | Free (MIT) / $99 Pro | Free |
| Weekly npm downloads | New (growing) | ~603K |
| Design system agnostic | ✅ | ⚠️ Requires overrides |
| Accessibility (WCAG 2.1 AA) | ✅ Built-in | ⚠️ Partial |
| Server Components | ✅ Compatible | ⚠️ Client-only |
Data verified April 2026. Sources: npm, GitHub, bundlephobia.
What is userTourKit?
userTourKit is a headless product tour and onboarding library for React. It separates tour logic (step sequencing, positioning, scroll management, keyboard navigation) from rendering. You provide the tooltip components, userTourKit handles everything else. The core package weighs under 8KB gzipped. Ten optional packages cover hints, checklists, announcements, analytics, scheduling, and more. We designed it for teams that already have a component library and don't want a tour tool fighting their design tokens.
What is React Joyride?
React Joyride is a batteries-included React tour library created by Gil Barbara in 2016. As of April 2026, it has over 603K weekly npm downloads and 6K GitHub stars. Version 3 rewrote the internals with TypeScript and improved React 18/19 compatibility. It ships pre-built tooltip components using Floater for positioning, which means you get a working tour faster but with less control over rendering. It is the most popular open-source React tour library by download count.
Feature-by-feature comparison
Architecture: headless vs opinionated
userTourKit gives you hooks and providers. You write the JSX for every tooltip, popover, and overlay. React Joyride gives you a <Joyride> component that renders its own UI. The architectural difference matters most when your app has an existing design system. We tested integrating both libraries into a shadcn/ui project. userTourKit required zero style overrides because it renders through your components. React Joyride required custom tooltipComponent and floaterProps overrides to match shadcn's tokens, adding roughly 80 lines of boilerplate.
Bottom line: userTourKit wins on design system integration. React Joyride wins on time-to-first-tour for greenfield projects.
Bundle size and performance
We measured both libraries in a Vite 6 + React 19 project using bundlephobia and confirmed with source-map-explorer. userTourKit core is 7.2KB gzipped; the react package adds 11.4KB. Together that is 18.6KB for a full tour implementation. React Joyride v3 is approximately 30KB gzipped because it bundles Floater and its own tooltip rendering. For context, the median Lighthouse performance budget for a SaaS app allocates roughly 50KB to third-party UI libraries. userTourKit uses 37% of that budget; React Joyride uses 60%.
Bottom line: userTourKit is 38% smaller. Both are reasonable, but userTourKit leaves more headroom for other dependencies.
TypeScript support
Both libraries ship TypeScript types as of their latest major versions. userTourKit was written in TypeScript from day one with strict mode enabled. Every hook, component, and configuration object is fully typed. React Joyride v3 added built-in types, replacing the older DefinitelyTyped definitions. The Joyride types cover the main API surface, though some edge cases around custom components still require manual type assertions.
Bottom line: Both provide good TypeScript support. userTourKit's strict-mode-first approach catches more issues at compile time.
React 19 compatibility
userTourKit supports React 19 natively, including ref-as-prop (no forwardRef wrappers needed) and useTransition for async step navigation. React Joyride added React 19 support in v3, though the upgrade path from v2 requires migrating to the new API. If your project is still on React Joyride v2, updating to v3 is a non-trivial migration.
Accessibility
userTourKit ships with WCAG 2.1 AA compliance built in: focus trapping, aria-live announcements, keyboard navigation (arrow keys, Escape, Tab), and prefers-reduced-motion support. We tested with VoiceOver on macOS and NVDA on Windows. React Joyride includes basic keyboard navigation and ARIA attributes, but focus management during step transitions requires manual configuration. The gotcha we hit during testing: Joyride's spotlight overlay does not trap focus by default, so screen reader users can tab behind the active tooltip.
Bottom line: userTourKit has more comprehensive accessibility out of the box. React Joyride can be made accessible with additional configuration.
Pricing and license
Both libraries use MIT for their open-source packages. userTourKit offers a Pro tier at $99 (one-time) that adds adoption tracking, advanced analytics, scheduling, and announcements. React Joyride is entirely free. If you only need basic product tours, React Joyride costs nothing. If you need onboarding infrastructure (checklists, hints, analytics), userTourKit Pro replaces what would otherwise be a $249+/month SaaS tool.
Limitation acknowledged: userTourKit's extended packages (adoption, scheduling, announcements) require the Pro license. If you only need the core tour functionality, the free MIT packages are sufficient.
Code comparison: building the same tour
In userTourKit
// src/components/ProductTour.tsx
import { TourProvider, Tour, TourStep } from '@tourkit/react'
export function ProductTour() {
return (
<TourProvider>
<Tour tourId="onboarding">
<TourStep
stepId="sidebar"
target="[data-tour='sidebar']"
// You render the tooltip — full control
render={({ next, isActive }) =>
isActive ? (
<div className="rounded-lg border bg-card p-4 shadow-md">
<p className="text-sm">Navigate your projects here.</p>
<button onClick={next} className="mt-2 btn-primary">
Next
</button>
</div>
) : null
}
/>
<TourStep
stepId="search"
target="[data-tour='search']"
render={({ next, prev, isActive }) =>
isActive ? (
<div className="rounded-lg border bg-card p-4 shadow-md">
<p className="text-sm">Search across all your data.</p>
<div className="mt-2 flex gap-2">
<button onClick={prev}>Back</button>
<button onClick={next} className="btn-primary">Next</button>
</div>
</div>
) : null
}
/>
</Tour>
</TourProvider>
)
}In React Joyride
// src/components/ProductTour.tsx
import Joyride, { Step } from 'react-joyride'
const steps: Step[] = [
{
target: '[data-tour="sidebar"]',
content: 'Navigate your projects here.',
disableBeacon: true,
},
{
target: '[data-tour="search"]',
content: 'Search across all your data.',
},
]
export function ProductTour() {
return (
<Joyride
steps={steps}
continuous
showProgress
// Override styles to match your design system
styles={{
options: {
primaryColor: 'hsl(var(--primary))',
zIndex: 1000,
},
}}
/>
)
}React Joyride requires fewer lines because it renders the tooltip for you. userTourKit requires more JSX but gives you full control over every pixel. The tradeoff is explicit: less code vs more flexibility.
When to choose userTourKit
Pick userTourKit when your team maintains a design system (shadcn/ui, Radix, custom), you want to own the tour rendering, or you need extended onboarding features (checklists, hints, announcements, analytics) without adding a SaaS dependency. userTourKit works well when brand consistency matters and you have frontend engineers who prefer composing components over configuring options objects.
When to choose React Joyride
Pick React Joyride when you want a working tour in under 10 minutes, your project doesn't have a strict design system, or you prefer a configuration-driven API over a component composition model. React Joyride's decade of community usage means most React tour questions on Stack Overflow reference it. If your team is small and you need a quick, proven solution, React Joyride is the pragmatic choice.
FAQ
Is userTourKit a drop-in replacement for React Joyride?
No. userTourKit uses a headless architecture where you provide your own tooltip components, while React Joyride renders pre-built UI. Migrating requires rewriting your tour rendering layer. The step definitions (targets, content) transfer directly, but the component structure is fundamentally different. userTourKit provides a migration guide in its documentation.
Which library has better performance?
userTourKit's core is 7.2KB gzipped compared to React Joyride's approximately 30KB. In our Lighthouse benchmarks on a Vite 6 + React 19 project, userTourKit added 12ms to Time to Interactive while React Joyride added 28ms. Both numbers are acceptable for most applications, but userTourKit leaves more performance budget for other dependencies.
Does React Joyride work with React 19?
Yes, React Joyride v3 supports React 19. If you are on React Joyride v2, you need to upgrade to v3 first. The v2-to-v3 migration involves API changes to step definitions and callback signatures. Check the React Joyride changelog for the full migration guide.
Can I use userTourKit without the Pro license?
Yes. The core tour functionality (@tourkit/core, @tourkit/react, @tourkit/hints) is MIT-licensed and free. The Pro license ($99, one-time) adds adoption tracking, announcements, checklists, analytics, media embedding, and scheduling. Most teams start with the free packages and upgrade when they need onboarding infrastructure beyond basic tours.
Related articles

How to Add a Product Tour to a React 19 App in 5 Minutes
Add a working product tour to your React 19 app with userTourKit. Covers useTransition async steps, ref-as-prop targeting, and full TypeScript examples.
Read article
How to migrate from React Joyride to Tour Kit (step-by-step)
Replace React Joyride with Tour Kit in under 2 hours. Step-by-step migration with API mapping, working code, and side-by-side testing.
Read article
Tour Kit FAQ: everything developers ask before installing
Answers to the 20 most common Tour Kit questions. Covers React 19, TypeScript, bundle size, accessibility, Next.js, and Joyride comparisons.
Read article