Repository navigation
New plugin: Extendable Guided Tours (using BUI and NFS) - #11697
Open
christoph-jerolimov wants to merge 28 commits into
Open
christoph-jerolimov wants to merge 28 commits into
christoph-jerolimov wants to merge 28 commits into
Conversation
Signed-off-by: Christoph Jerolimov <jerolimov+git@redhat.com>
Proposal, design, tasks and spec for an extension-driven guided tour system on the new frontend system: a web library plugins depend on (blueprint, API ref, hook, markdown), a plugin with the api/overlay/page, per-user progress in user settings, login and route auto-start, and cross-page steps. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Signed-off-by: Christoph Jerolimov <jerolimov+git@redhat.com>
Two new packages: - plugins/guided-tour-react: the contract other plugins depend on (GuidedTourBlueprint, guidedTourApiRef, useGuidedTour, target helpers, minimal markdown renderer built on Backstage UI). - plugins/guided-tour: api:guided-tour (registry, runner, per-user progress in the storage api), the app root overlay (spotlight mask, Backstage UI popover anchored with react-aria, route and click-through steps) and the /guided-tours page. App wiring: welcome tour on first login, sidebar entry, data-guided-tour ids on sidebar items. The example plugin ships its own tour that starts on the first visit of /example and depends only on the react library. Verified with unit tests, a Playwright e2e spec and screenshots. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Signed-off-by: Christoph Jerolimov <jerolimov+git@redhat.com>
Centered steps rendered the card straight into the Backstage UI Dialog, which only pads its DialogBody, and the card had a fixed width narrower than the dialog. Wrap centered steps and the loading skeleton in DialogBody, let the card fill its container, and keep the 360px width on the popover variant only. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Signed-off-by: Christoph Jerolimov <jerolimov+git@redhat.com>
Steps with advanceOn: 'click' hid the Next button, which left the second step of the example intro tour without an obvious way forward. The button now stays; clicking the highlighted element remains the second way to advance, and the hint text is kept. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Signed-off-by: Christoph Jerolimov <jerolimov+git@redhat.com>
The component now takes a tourId prop (plus optional label and icon) and is exported from @internal/backstage-plugin-guided-tour-react so any plugin can lazy-load it in a PluginHeaderActionBlueprint. The example plugin reuses it for its intro tour. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Signed-off-by: Christoph Jerolimov <jerolimov+git@redhat.com>
The sidebar steps of the welcome tour now navigate to their pages (route '/', '/create' and '/settings'). Route matching for steps is prefix based: pages such as the scaffolder redirect '/create' to '/create/templates', which the exact pathname comparison treated as "not on the route" and left the step loading forever. The root route still matches exactly. The same matcher is used by the resume-on-load rule. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Signed-off-by: Christoph Jerolimov <jerolimov+git@redhat.com>
"Restart the tour" becomes "Restart the guided tour" for the accessible name and tooltip. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Signed-off-by: Christoph Jerolimov <jerolimov+git@redhat.com>
A step without a route lives on the page the tour reached before it. The tours page and the resume-on-load rule now use the closest earlier route (routeForStep) instead of only the current step's own route. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Signed-off-by: Christoph Jerolimov <jerolimov+git@redhat.com>
resetProgress now requires a tour id; resetAllProgress clears every tour and the onboarded flag. The tours page uses resetAllProgress for its "Reset all tours" action. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Signed-off-by: Christoph Jerolimov <jerolimov+git@redhat.com>
The standalone dev app now loads the home, catalog, scaffolder, notifications and user settings plugins next to the guided tour plugin. Catalog, scaffolder and notifications APIs are replaced by in-memory mocks (dev/mockApis.tsx, dev/mockData.ts) so no backend is needed. The dev app gets its own config (dev/app-config.yaml) instead of the repository's app-config.yaml: a default home page layout, the random joke widget disabled, and the catalog at its default path. New in the demo: an "Explore the portal" tour across all those pages, the RestartTourAction header button, a markdown-heavy first step, and a home page widget pointing to the tours page. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Signed-off-by: Christoph Jerolimov <jerolimov+git@redhat.com>
Each tour of the dev app now lives in dev/tours/. New tours start on the first visit of the catalog, create, notifications and settings pages and spotlight real elements there. The welcome tour of packages/app is carried over, targeting the default sidebar links by href. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Signed-off-by: Christoph Jerolimov <jerolimov+git@redhat.com>
Remove the "Explore the portal" tour. The catalog tour spotlights the whole Personal/Company filter block and drops the "More filters" step. The scaffolder tour spotlights the complete template card. The settings tour highlights the display name and email, adds a "Logout" step on the menu button, highlights the whole theme button group and drops the "More settings" step. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Signed-off-by: Christoph Jerolimov <jerolimov+git@redhat.com>
Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Signed-off-by: Christoph Jerolimov <jerolimov+git@redhat.com>
The "Welcome to the demo" and "Second page tour" tours and the demo and second pages are gone. The home page is now the landing page of the dev app, the welcome tour is the login tour, and the header action restarts it. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Signed-off-by: Christoph Jerolimov <jerolimov+git@redhat.com>
The welcome tour (app and dev app) gains steps for the Notifications and Guided tours sidebar items, drops "Browse and filter", and returns to / when Done is pressed. Tours can set `completeRoute`; the overlay navigates there when the last step is finished with Done or by clicking through. The progress store now ignores storage notifications for a key while its own writes are in flight, so a pending write cannot briefly undo a later one (seen as "Restart" flashing after "Reset all tours"). Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Signed-off-by: Christoph Jerolimov <jerolimov+git@redhat.com>
The "Guided tours" step now follows the intro, the notifications step is titled "Your notifications", and the settings step ends the tour with "Done takes you back to the start page." Applied to the app and the dev app; the e2e spec follows the new order. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Signed-off-by: Christoph Jerolimov <jerolimov+git@redhat.com>
Use ">=4.6.0 <4.9.0" like @backstage/ui and the other Backstage packages, so the guided tour packages share their copy of @remixicon/react instead of pulling a second one. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Signed-off-by: Christoph Jerolimov <jerolimov+git@redhat.com>
Promote the change's spec to openspec/specs/guided-tour/spec.md and move the change folder to openspec/changes/archive/2026-10-23-guided-tour-plugin. Task 6.3 (dark theme and screen reader check) stays open and is marked as such. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Signed-off-by: Christoph Jerolimov <jerolimov+git@redhat.com>
The dev app no longer shows the button on the guided tours page. Instead the catalog, create, notifications and settings plugin headers get a button that restarts their own tour (dev/headerActions.tsx). Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Signed-off-by: Christoph Jerolimov <jerolimov+git@redhat.com>
Rename the packages to @backstage-community/plugin-guided-tours and @backstage-community/plugin-guided-tours-react, set their version to 0.0.0, license them under Apache-2.0 and drop the private flag. The plugin id becomes guided-tours, and the api ref, extension ids, translation ref, storage bucket and dev tour ids follow it. The plugin and openspec folders take the plural name too. Adds the workspace README and the initial changeset and rebuilds the lockfile. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Signed-off-by: Christoph Jerolimov <jerolimov+git@redhat.com>
Restore the leading doc comments that the license header rule replaced, so the placement type keeps its release tag and the react package its package documentation. Export the translation ref from an alpha entry point as other plugins do. Add react-dom as a dev dependency so jest can load react-router-dom, polyfill URL.canParse in the test setup for jsdom 20, and drop two unused dev dependencies that knip reported. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Signed-off-by: Christoph Jerolimov <jerolimov+git@redhat.com>
Contributor
|
Important This PR includes changes that affect public-facing API. Please ensure you are adding/updating documentation for new features or behavior. Changed Packages
|
Create the guided tour API ref with the `createApiRef<T>().with()` form and import the `ScaffolderApi` type of the dev app mocks from `@backstage/plugin-scaffolder-common`. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Signed-off-by: Christoph Jerolimov <jerolimov+git@redhat.com>
Codecov Report❌ Patch coverage is Additional details and impacted files@@ Coverage Diff @@
## main #11697 +/- ##
===========================================
+ Coverage 75.50% 98.17% +22.66%
===========================================
Files 630 24 -606
Lines 17182 656 -16526
Branches 4045 162 -3883
===========================================
- Hits 12973 644 -12329
+ Misses 4162 12 -4150
+ Partials 47 0 -47
Continue to review full report in Codecov by Harness.
🚀 New features to boost your workflow:
|
| route?: string; | ||
| target?: | ||
| | string | ||
| | { |
Member
Author
There was a problem hiding this comment.
Use to: string or page: string or subpage: string???
Document every public type and API member, rename the tour data ref to `guided-tours.tour` and explain why the extension kind stays singular. Retitle the workspace README and start the dev app from the workspace root. Drop the yarnrc the workspace does not need and tidy the gitignore. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Signed-off-by: Christoph Jerolimov <jerolimov+git@redhat.com>
Unit tests now cover the overlay, the step card, the spotlight, the target hooks, the overview page, the extensions, the react hooks and helpers and the remaining branches of the api and progress store. Along the way the target hook stopped leaking the previous step's status into a new step, which could skip or center a step for a moment. The workspace gets Playwright tests against the dev app: the welcome tour across pages, the centered and anchored overlays, the click-through step, the previous button restoring earlier pages, resume after reload, Escape and close, the overview page and the header restart action. CI runs them through the playwrightTests flag. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Signed-off-by: Christoph Jerolimov <jerolimov+git@redhat.com>
The act re-exported by Testing Library is the deprecated one from react-dom/test-utils, which the CI deprecation check rejects. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Signed-off-by: Christoph Jerolimov <jerolimov+git@redhat.com>
christoph-jerolimov
marked this pull request as ready for review
October 24, 2026 05:35
christoph-jerolimov
requested review from
a team and
backstage-service
as code owners
October 24, 2026 05:35
christoph-jerolimov
requested review from
BethGriggs,
awanlin,
ciiay,
karthikjeeyar,
logonoff and
schultzp2020
and removed request for
BethGriggs
October 24, 2026 05:35
The autoStart option now reads `{ path }` to describe the browser location that starts a tour. The step `route` and `completeRoute` keep their names.
Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Signed-off-by: Christoph Jerolimov <jerolimov+git@redhat.com>
The autoStart path now matches the location exactly by default. Tours that should also start below the path, for example on entity pages under /catalog, set exact: false. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Signed-off-by: Christoph Jerolimov <jerolimov+git@redhat.com>
This branch has not been deployed
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Hey, I just made a Pull Request!
Fixes #279.
Adds a new
guided-toursworkspace with two plugins for the new frontend system:@backstage-community/plugin-guided-tours: the tour runner, a spotlight overlay with step cards, per-user progress stored in the storage API, automatic start on login or on the first visit of a path, and an overview page at/guided-tours.@backstage-community/plugin-guided-tours-react: theGuidedTourBlueprint, API ref, hooks and target helpers that let any frontend plugin ship a tour without depending on the main plugin.The main plugin comes with a dev app that showcases tours on the catalog, scaffolder, notifications and user settings pages.
Localization of the tour contents will follow in a later PR. The API for that is not settled yet.
Example
Any plugin ships a tour as an extension built with the
GuidedTourBlueprint. Adopters can do the same in their app with a frontend module. When theguided-toursplugin is not installed, the extension stays unattached and nothing breaks.The tour gets the id
catalog/intro. Elements of your own UI are marked withguidedTourTargetProps('my-plugin.element')and referenced by that id as the step target.Screenshots
✔️ Checklist
Signed-off-byline in the message. (more info)🤖 Generated with Claude Code