Table Breaking Redesigned Table component with new useTable hook API.
Table component (React Aria wrapper) is renamed to TableRootTable component that handles data display, pagination, sorting, and selectionuseTable hook is completely redesigned with a new API supporting three pagination modes (complete, offset, cursor)ColumnConfig, TableProps, TableItem, UseTableOptions, UseTableResultNew features include unified pagination modes, debounced query changes, stale data preservation during reloads, and row selection with toggle/replace behaviors. #32050
Migration Guide:
useTable hook:-import { Table, useTable } from '@backstage/ui';
-const { data, paginationProps } = useTable({ data: items, pagination: {...} });
+import { Table, useTable, type ColumnConfig } from '@backstage/ui';
+const { tableProps } = useTable({
+ mode: 'complete',
+ getData: () => items,
+});
-<Table aria-label="My table">
- <TableHeader>...</TableHeader>
- <TableBody items={data}>...</TableBody>
-</Table>
-<TablePagination {...paginationProps} />
+const columns: ColumnConfig<Item>[] = [
+ { id: 'name', label: 'Name', isRowHeader: true, cell: item => <CellText title={item.name} /> },
+ { id: 'type', label: 'Type', cell: item => <CellText title={item.type} /> },
+];
+
+<Table columnConfig={columns} {...tableProps} />
Breaking Updating color tokens to match the new neutral style on different surfaces. #32202
Migration Guide:
There's no direct replacement for the old tint tokens but you can use the new neutral set of color tokens on surface 0 or 1 as a replacement.
--bui-bg-tint can be replaced by --bui-bg-neutral-on-surface-0--bui-bg-tint-hover can be replaced by --bui-bg-neutral-on-surface-0-hover--bui-bg-tint-pressed can be replaced by --bui-bg-neutral-on-surface-0-pressed--bui-bg-tint-disabled can be replaced by --bui-bg-neutral-on-surface-0-disabledBreaking Introduce new ToggleButton & ToggleButtonGroup components in Backstage UI #32232
Breaking Renamed CSS variable --bui-bg to --bui-bg-surface-0 for consistency. #32200
Box Fixes app background color on dark mode. #32203
Checkbox Added indeterminate state support to the Checkbox component for handling partial selection scenarios like table header checkboxes. #32371
Select Added missing aria-label attributes to SearchField components in Select, MenuAutocomplete, and MenuAutocompleteListbox to fix accessibility warnings. #32337
Button Fixes disabled state in primary and secondary buttons in Backstage UI. #32297
build(deps-dev): bump storybook from 10.1.9 to 10.1.10 #32185
Button Fixed disabled tertiary buttons incorrectly showing hover effects on surfaces. #32385
Added new Popover component for Backstage UI with automatic overflow handling, and full placement support. Also introduced --bui-shadow token for consistent elevation styling across overlay components (Popover, Tooltip, Menu). #32313
Table Fixed Table sorting indicator not being visible when a column is actively sorted. #32350
Menu Fixed Menu component trigger button not toggling correctly. Removed custom click-outside handler that was interfering with React Aria's built-in state management, allowing the menu to properly open and close when clicking the trigger button. #32347
Table Added support for column width configuration in Table component. Columns now accept width, defaultWidth, minWidth, and maxWidth props for responsive layout control. #32336
Searchfield Fixed SearchField startCollapsed prop not working correctly in Backstage UI. The field now properly starts in a collapsed state, expands when clicked and focused, and collapses back when unfocused with no input. Also fixed CSS logic to work correctly in all layout contexts (flex row, flex column, and regular containers). #32123
Fixed Link component causing hard page refreshes for internal routes. The component now properly uses React Router's navigation instead of full page reloads. #32265
Table Added support for custom pagination options in useTable hook and Table component. You can now configure pageSizeOptions to customize the page size dropdown, and hook into pagination events via onPageSizeChange, onNextPage, and onPreviousPage callbacks. When pageSize doesn't match any option, the first option is used and a warning is logged. #32321
Table Fixed missing border styles on table selection cells in multi-select mode. #32369
Table Added className and style props to the Table component. #32342
Breaking The Cell component has been refactored to be a generic wrapper component that accepts children for custom cell content. The text-specific functionality (previously part of Cell) has been moved to a new CellText component. #31917
Migration Guide:
If you were using Cell with text-specific props (title, description, leadingIcon, href), you need to update your code to use CellText instead:
Before:
<Cell
title="My Title"
description="My description"
leadingIcon={<Icon />}
href="/path"
/>
After:
<CellText
title="My Title"
description="My description"
leadingIcon={<Icon />}
href="/path"
/>
For custom cell content, use the new generic Cell component:
<Cell>{/* Your custom content */}</Cell>
Checkbox Fixed Checkbox indicator showing checkmark color when unchecked. #31904
Button Icon Fixed ButtonIcon incorrectly applying className to inner elements instead of only the root element. #31900
Fixed Table Row component to correctly handle cases where no href is provided, preventing unnecessary router provider wrapping and fixing the cursor incorrectly showing as a pointer despite the element not being a link. #31843
Table Added row selection support with visual state styling for hover, selected, and pressed states. Fixed checkbox rendering to only show for multi-select toggle mode. #31907
Fixed useTable hook to prioritize providedRowCount over data length for accurate row count in server-side pagination scenarios. #31817
Fixed Table column sorting indicator to show up arrow when no sort is active, correctly indicating that clicking will sort ascending. #31844
Fixed Table Row component to correctly handle cases where no href is provided, preventing unnecessary router provider wrapping and fixing the cursor incorrectly showing as a pointer despite the element not being a link. #31843
Fixed useTable hook to prioritize providedRowCount over data length for accurate row count in server-side pagination scenarios. #31817
Fixed Table column sorting indicator to show up arrow when no sort is active, correctly indicating that clicking will sort ascending. #31844
Avatar Breaking Migrated Avatar component from Base UI to custom implementation with size changes:
x-small size added (1.25rem / 20px)small size unchanged (1.5rem / 24px)medium size unchanged (2rem / 32px, default)large size changed from 3rem to 2.5rem (40px)x-large size added (3rem / 48px) #31566Migration Guide:
# Remove Base UI-specific props
- <Avatar src="..." name="..." render={...} />
+ <Avatar src="..." name="..." />
# Update large size usage to x-large for same visual size
- <Avatar src="..." name="..." size="large" />
+ <Avatar src="..." name="..." size="x-large" />
Added purpose prop for accessibility control ('informative' or 'decoration').
Breaking Migrated Checkbox component from Base UI to React Aria Components.
API changes required:
checked → isSelecteddefaultChecked → defaultSelecteddisabled → isDisabledrequired → isRequiredlabel prop removed - use children insteadbui-CheckboxLabel class removeddata-checked → data-selectedMigration Guide:
Before:
<Checkbox label="Accept terms" checked={agreed} onChange={setAgreed} />
After:
<Checkbox isSelected={agreed} onChange={setAgreed}>
Accept terms
</Checkbox>
Before:
<Checkbox label="Option" disabled />
After:
<Checkbox isDisabled>Option</Checkbox>
Before:
<Checkbox />
After:
<Checkbox>
<VisuallyHidden>Accessible label</VisuallyHidden>
</Checkbox>
Breaking Fixing styles on SearchField in Backstage UI after migration to CSS modules. SearchField has now its own set of class names. We previously used class names from TextField but this approach was creating some confusion so going forward in your theme you'll be able to theme TextField and SearchField separately. #31507
Breaking Removed central componentDefinitions object and related type utilities (ComponentDefinitionName, ComponentClassNames).
Component definitions are primarily intended for documenting the CSS class API for theming purposes, not for programmatic use in JavaScript/TypeScript. #31744
Migration Guide:
If you were using component definitions or class names to build custom components, we recommend migrating to either:
Menu Switch Skeleton Header Header Page Tabs Breaking Changed className prop behavior to augment default styles instead of being ignored or overriding them.
If you were passing custom className values to any of these components that relied on the previous behavior, you may need to adjust your styles to account for the default classes now being applied alongside your custom classes. #31496
Breaking Removed Collapsible component. Migrate to Accordion or use React Aria Disclosure. #31493
Migration Guide:
Path 1: Accordion (Opinionated Styled Component)
Accordion provides preset styling with a similar component structure.
- import { Collapsible } from '@backstage/ui';
+ import { Accordion, AccordionTrigger, AccordionPanel } from '@backstage/ui';
- <Collapsible.Root>
- <Collapsible.Trigger render={(props) => <Button {...props}>Toggle</Button>} />
- <Collapsible.Panel>Content</Collapsible.Panel>
- </Collapsible.Root>
+ <Accordion>
+ <AccordionTrigger title="Toggle" />
+ <AccordionPanel>Content</AccordionPanel>
+ </Accordion>
CSS classes: .bui-CollapsibleRoot → .bui-Accordion, .bui-CollapsibleTrigger → .bui-AccordionTrigger (now on heading element), .bui-CollapsiblePanel → .bui-AccordionPanel
Path 2: React Aria Disclosure (Full Customization)
For custom styling without preset styles:
import { Disclosure, Button, DisclosurePanel } from 'react-aria-components';
<Disclosure>
<Button slot="trigger">Toggle</Button>
<DisclosurePanel>Content</DisclosurePanel>
</Disclosure>;
Select Breaking The SelectProps interface now accepts a generic type parameter for selection mode.
Added searchable and multiple selection support to Select component. The component now accepts searchable, selectionMode, and searchPlaceholder props to enable filtering and multi-selection modes. #31649
Migration Guide:
If you're using SelectProps type directly, update from SelectProps to SelectProps<'single' | 'multiple'>. Component usage remains backward compatible.
Header Fix broken external links in Backstage UI Header component. #31525
Select Fixed CSS issues in Select component including popover width constraints, focus outline behavior, and overflow handling. #31618
Password Field Searchfield Improved visual consistency of PasswordField, SearchField, and MenuAutocomplete components. #31679
Text Fix default text color in Backstage UI #31429
Text Fixed Text component to prevent truncate prop from being spread to the underlying DOM element. #31615
Link Improved the Link component structure in Backstage UI. #31524
Dialog Fixed dialog backdrop appearance in dark mode. #31673
Avatar Migrated CellProfile component from Base UI Avatar to Backstage UI Avatar component. #31608
Avatar Avatar components in x-small and small sizes now display only one initial instead of two, improving readability at smaller dimensions. #31623
Removed @base-ui-components/react dependency as all components now use React Aria Components. #31672
Fix the default font size in Backstage UI. #31435
Fix CSS layer ordering in Backstage UI to make sure component styles are loaded after tokens and base declarations. #31448
Radio Group Fixed RadioGroup radio button ellipse distortion by preventing flex shrink and grow. #31576
Fix font smoothing as default in Backstage UI. #31444
Enable tree-shaking of imports other than *.css. #31516
Button Button Icon Added loading prop to Button and ButtonIcon components for displaying spinner during async operations. #31681
Table Fixed Table Row component to properly support opening links in new tabs via right-click or Cmd+Click when using the href prop. #31680
Set the color-scheme property depending on theme #31469
Visually Hidden Added new VisuallyHidden component for hiding content visually while keeping it accessible to screen readers. #31484
Fix default font weight and font family in Backstage UI. #31432
Fix default text color in Backstage UI #31429
Fix the default font size in Backstage UI. #31435
Fix CSS layer ordering in Backstage UI to make sure component styles are loaded after tokens and base declarations. #31448
Fix font smoothing as default in Backstage UI. #31444
Fix default font wight and font family in Backstage UI. #31432
Breaking Added a new PasswordField component. As part of this change, the password and search types have been removed from TextField. #31238
Breaking Restructure Backstage UI component styling to use CSS Modules instead of pure CSS. We don't expect this to be an issue in practice but it is important to call out that all styles are now loaded through CSS modules with generated class names. We are still providing fixed class names for all components to allow anyone to style their Backstage instance. #31399
Breaking The ScrollArea component has been removed from Backstage UI because it did not meet our accessibility standards. #31409
Breaking Remove Icon component in Backstage UI. This component was creating issue for tree-shaking. It is recommended to use icons from @remixicon/react until we found a better alternative in Backstage UI. #31407
Adding a new Dialog component to Backstage UI. #31371
remove default selection of tab #31216
Fix margin utility classes in Backstage UI. #31389
Fix scroll jumping when opening menu in Backstage UI. #31394
Making href mandatory in tabs that are part of a Header component #31343
Update react-aria-components to version 1.13.0 #31367
Fix table sorting icon position in Backstage UI. #31393
Add new virtualized, maxWidth and maxHeight props to Menu, MenuListBox, MenuAutocomplete and MenuAutocompleteListBox to allow for virtalization of long lists inside menus. #31375
Added support for data attributes in <Box />, <Container />, <Flex />, and <Grid /> components, ensuring they are correctly applied to the rendered elements. #31374
Cleaning up Backstage UI props definitions as well as removing ScrollArea in Card to improve accessibility. #31404
Add react router for internal routing for ButtonLinks #31276
Added a background color default on the body #31365
We are restructuring our CSS to have a better layer structure. #31362
Improved SearchField component flex layout and animations. Fixed SearchField behavior in Header components by switching from width-based transitions to flex-basis transitions for better responsive behavior. Added new Storybook stories to test SearchField integration with Header component. #31158
Remove auto selection of tabs for tabs that all have href defined #31281
Avoid overriding onChange when spreading props #31232
Using react router for internal links in the Menu component #31339
Making href mandatory in tabs that are part of a Header component #31343
Add react router for internal routing for ButtonLinks #31276
Remove auto selection of tabs for tabs that all have href defined #31281
Using react router for internal links in the Menu component #31339
Enable tooltips on disabled buttons with automatic wrapper #31230
Avoid overriding onChange when spreading props #31232
remove default selection of tab #31216
Improved SearchField component flex layout and animations. Fixed SearchField behavior in Header components by switching from width-based transitions to flex-basis transitions for better responsive behavior. Added new Storybook stories to test SearchField integration with Header component. #31158
Add missing class for flex: baseline #31013
Fix Select component to properly attach aria-label and aria-labelledby props to the rendered element for improved accessibility. #31037
Removed the need to mock window.matchMedia in tests, falling back to default breakpoint values instead. #31148
Breaking We are moving our DataTable component to React Aria. We removed our DataTable to only use Table as a single and opinionated option for tables. This new structure is made possible by using React Aria under the hood. #30654
Breaking Backstage UI - HeaderPage - We are updating the breadcrumb to be more visible and accessible. #30874
Breaking We are updating the Menu component to use React Aria under the hood. The structure and all props are changing to follow React Aria's guidance. #30908
Breaking We are upgrading our Text component to support all font sizes making the Heading component redundant. The new Text component introduces 4 sizes for title and 4 sizes for body text. All of these work in multiple colors and font weights. We improved the as prop to include all possible values. The Link component has also been updated to match the new Text component. #30592
Fixes some styles on the Select component in BUI. #30642
Export CardHeader, CardBody and CardFooter from Card component index #30882
Add new TagGroup component to Backstage UI. #30919
Fixes a couple of small bugs in BUI including setting H1 and H2 correctly on the Header and HeaderPage. #30636
Update styling of Tooltip element #30591
Move breadcrumb to fit in the HeaderPage instead of the Header in Backstage UI. #30701
We are motion away from motion to use gsap instead to make Backstage UI backward compatible with React 17. #30626
Updated Menu component in Backstage UI to use useId() from React Aria instead of React to support React 17. #30675
Remove stylesheet import from Select component. #30800
Add startCollapsed prop on the SearchField component in BUI. #30729
Adds onTabSelectionChange to ui header component. #30588
@backstage/canon has been deprecated and replaced by @backstage/ui. #30525Breaking We are updating the default size of the Button component in Canon to be small instead of medium. #30085
Breaking We set the default size for IconButton in Canon to be small instead of medium. #30097
Breaking Move TextField component to use react Aria under the hood. Introducing a new FieldLabel component to help build custom fields. #30286
Breaking We are adding a new as prop on the Heading and Text component to make it easier to change the component tag. We are removing the render prop in favour of the as prop. #30291
Breaking TextField in Canon now has multiple label sizes as well as the capacity to hide label and description but still make them available for screen readers. #30249
Breaking Fixes spacing props on layout components and aligned on naming for the Grid component. You should now call the Grid root component using <Grid.Root /> instead of just <Grid />. #30013
Add min-width: 0; by default on every Flex components in Canon to help support truncated texts inside flex elements. #30168
Fix styling for the title4 prop on the Heading component in Canon. #30167
Added a render prop to the Button component in Canon to use it as a link. #30165
Add new Switch component in Canon. #30251
The filter input in menu comboboxes should now always use the full width of the menu it's in. #30104
Remove leftover console.log from Container component. #30040
Breaking Icons on Button and IconButton now need to be imported and placed like this: <Button iconStart={<ChevronDownIcon />} /> #29667
Breaking We are modifying the way we treat custom render using 'useRender()' under the hood from BaseUI. #29989
Breaking The icon prop in TextField now accept a ReactNode instead of an icon name. We also updated the icon sizes for each input sizes. #29974
Use correct colour token for TextField clear button icon, prevent layout shift whenever it is hidden or shown and properly size focus area around it. Also stop leading icon shrinking when used together with clear button. #29878
Fix Canon missing dependencies #29642
For improved a11y, clicking a Select component label now focuses the Select trigger element, and the TextField component's label is now styled to indicate it's interactive. #29755
Added new icon and onClear props to the TextField to make it easier to accessorize inputs. #29820
Add new Tabs component to Canon #29996
Pin version of @base-ui-components/react. #29782
Fixed an issue with Canon's DataTable.Pagination component showing the wrong number for the "to" count. #29688
Removed various typos #29665
Update Menu component in Canon to make the UI more condensed. We are also adding a new Combobox option for nested navigation. #29986
Use the Field component from Base UI within the TextField. #29826
Add new truncate prop to Text and Heading components in Canon. #29988
Breaking Improve class name structure using data attributes instead of class names. #29560
Breaking Updated TextField and Select component to work with React Hook Form. #29482
Breaking Add new Select component for Canon #29440
Breaking Added a new TextField component to replace the Field and Input component. After feedback, it became clear that we needed to build a more opinionated version to avoid any problem in the future. #29364
Updated styles for the Menu component in Canon. #29351
Fix Checkbox styles on dark theme in Canon. #29544
Add new breakpoint helpers up(), down() and current breakpoint to help you use our breakpoints in your React components. #29564
Internal refactor and fixes to the prop extraction logic for layout components. #29389
Add new Collapsible component for Canon. #29617
Removes instances of default React imports, a necessary update for the upcoming React 19 migration.
https://legacy.reactjs.org/blog/2020/09/22/introducing-the-new-jsx-transform.html #29499
Add global CSS reset for anchor tags. #29357
Improved Container styles, changing our max-width to 120rem and improving padding on smaller screens. #29475
Add new Avatar component to Canon. #29594
Add new TableCellProfile component for Table and DataTable in Canon. #29600
Fix types on the Icon component. #29306
Add new DataTable component and update Table component styles. #29484
Move styles to the root of the TextField component. #29466
We added a render prop to the Link component to make sure it can work with React Router. #29247
Fix Select styles on small sizes + with long option names in Canon. #29545
Added a new gray scale for Canon for both light and dark theme. #29543
Add support for column sizing in DataTable. #29603
Fix the Icon component when the name is not found to return null instead of an empty SVG. #29280
Internal refactor and fixes to the prop extraction logic for layout components. #29389
Fix types on the Icon component. #29306
Updated styles for the Menu component in Canon. #29351
Add global CSS reset for anchor tags. #29357
Fix the Icon component when the name is not found to return null instead of an empty SVG. #29280
Breaking Fix CSS imports and move CSS outputs out of the dist folder. #28961
Breaking Added a new Tooltip component to Canon. #29241
Breaking We added a new IconButton component with fixed sizes showcasing a single icon. #29239
Breaking Added about 40 new icons to Canon. #29264
Breaking We are renaming CanonProvider to IconProvider to improve clarity on how to override icons. #29002
Breaking Added a new Menu component to Canon. #29151
Breaking Updating styles for Text and Link components as well as global surface tokens. #29200
Breaking Added a new ScrollArea component for Canon. #29240
Fix Button types that was preventing the use of native attributes like onClick. #29205
To avoid conflicts with Backstage, we removed global styles and set font-family and font-weight for each components. #28972
Introducing Canon to Backstage. Canon styling system is based on pure CSS. We are adding our styles.css at the top of your Backstage instance. #29137
Breaking Merged the Stack and Inline component into a single component called Flex. #28634
Breaking This is the first alpha release for Canon. As part of this release we are introducing 5 layout components and 7 components. All theming is done through CSS variables. #28562
Breaking Fixing css structure and making sure that props are applying the correct styles for all responsive values. #28630
Breaking Updated core CSS tokens and fixing the Button component accordingly. #28789
Removed client directive as they are not needed in React 18. #28626
Fix spacing props not being applied for custom values. #28770
Removed older versions of React packages as a preparatory step for upgrading to React 19. This commit does not introduce any functional changes, but removes dependencies on previous React versions, allowing for a cleaner upgrade path in subsequent commits. #28579
We're excited to share the initial release of Backstage UI 💚 In this first alpha version, you'll find the foundation of our design system: a set of versatile layout components and a handful of essential atomic elements to help you get started. While Backstage UI is still in its early stages, it's ready for exploration and we'd love for you to give it a try and share your feedback.