Serendie Design System

AboutGet StartedAIFoundationsComponents
© Mitsubishi Electric Corporation

Migrating from v1 to v3

Changes to be aware of and a checklist for updating @serendie/ui from v1.x to v3.x.

Last updated 10/19/2026

About this guide

This page summarizes the changes that affect applications when updating @serendie/ui from v1.0.0 to v3.x (v3.5.1 or later), along with a checklist for the update. See GitHub Releases for the release notes of each version.

Releases - Serendie UI (GitHub)

Major changes by version

Three changes have the largest impact on applications.

v2.1.0 — Upgrade to Ark UI v5

The headless UI library Ark UI used internally was upgraded from v3 to v5. The internal implementation, DOM structure, data-scope / data-part attributes, and event timing of Select, Search, CheckBox, ChoiceBox, and other components changed. If you use the Ark UI API directly, also refer to the Ark UI migration guide.

v3.0.0 — Dark mode support and design token update

@serendie/design-token was updated from 1.1 to 1.4, adding dark mode support. As a result, the background and outline system tokens used by many components changed (for example, sd.system.color.component.surface → surfaceContainerBright, outlineVariant → outlineBright / outlineDim).

Serendie UI uses class names generated by Panda CSS, and those class names are derived from the style values. Token changes therefore change the generated class names. Generated class names are not a public API and are not guaranteed to be compatible between versions. If your app CSS targets generated class names directly, the UI will break at this version.

v3.1.1 — @pandacss/dev moved to devDependencies

Before v3.1.1, @pandacss/dev, which is only needed at build time, was listed in the regular dependencies, so npm audit --omit=dev reported Panda CSS-related packages (PostCSS, picomatch, browserslist, esbuild, etc.). It was moved to devDependencies in v3.1.1.

npm audit —omit=dev results

Checked on 2026-10-19. In a new project with only the specified version installed, npm audit --omit=dev reported 52 findings for @serendie/ui@1.0.0 (High 46 / Moderate 6), and 0 for @serendie/ui@3.5.1 and @serendie/ui@3.7.2.

Results change as npm’s advisory database is updated. Finding counts do not directly indicate runtime vulnerabilities or real-world exploitability (a single advisory can be counted multiple times through dependents). Use npm explain <package> to trace where a package comes from (for example, npm explain axios form-data esbuild).

To fail when High or higher severity vulnerabilities are detected, run npm audit --omit=dev --audit-level=high.

Dependency summary

  • @ark-ui/react: ^3.5.0 → ^5.18.0 (v2.1.0+)
  • @serendie/design-token: ^1.1.0 → ^1.4.5 (v3.0.0+)
  • @pandacss/dev: dependencies → devDependencies (v3.1.1+)
  • react (peerDependencies): >=18.3.1 (unchanged)

Setup changes

Installation, the @layer declaration and @serendie/ui/styles.css import in the root CSS, theme switching via data-panda-theme, and the package exports (., ./*, ./css, ./tokens, ./types, ./patterns, ./jsx, ./styles.css) are unchanged from v1.

The following features were added. All of them are optional.

  • @serendie/ui/client — entry point for use from Server Components in the Next.js App Router
  • SerendieProvider — a provider for language (lang), color theme (colorTheme), and color mode (colorMode). Required for dark mode or English UI text. Without it, components behave as before (Japanese, light mode)
  • Theme and i18n exports such as ColorSchemeScript, useThemeContext, and useTranslations

Changes by component

ProgressIndicator — Props changed

In v1, ProgressIndicator was a spinning svg element accepting size and color; gray applied sd.reference.color.scale.gray.400, and white applied sd.reference.color.scale.white.1000. In v3 it is split into ProgressIndicator for determinate progress (type, size, value, max) and ProgressIndicatorIndeterminate for indeterminate state. In v3.5.1, ProgressIndicator has no color prop. ProgressIndicatorIndeterminate accepts color="primary" | "subtle"; primary applies sd.system.color.impression.primary, and subtle applies sd.reference.color.scale.gray.300. subtle is the closest to the v1 gray value, but the colors are not identical. There is no equivalent for v1 white. Check the rendered appearance when choosing.

// v1
<ProgressIndicator size="medium" color="white" />
<ProgressIndicator size="medium" color="gray" />

// v3: ProgressIndicatorIndeterminate

<ProgressIndicatorIndeterminate type="circular" size="medium" color="primary" />
<ProgressIndicatorIndeterminate type="circular" size="medium" color="subtle" />

Select

  • items is now optional, and collection can no longer be passed because it is created internally
  • portalled (default true) and requiredLabel were added
  • The render target of the options changed. In v1 they were always rendered under body; in v3, when used inside a Serendie UI ModalDialog or Drawer, they are automatically rendered inside that dialog’s content
  • Clicking the currently selected item again keeps the selection, and onValueChange does not fire again because the value did not change (Ark UI v5 behavior)
  • className is applied to the root element only, not to internal elements such as options
  • items, portalled, allowCustomValue (default true), and onSearch were added
  • In v1 the suggestion list was rendered only when there were items; in v3 it is always rendered and controlled through a Portal
  • The DOM structure of the clear button changed (from Ark UI Combobox.Trigger to a plain button element)
  • portalled (default true) was added. As with Select, the menu is rendered inside a ModalDialog / Drawer automatically

ModalDialog

  • submitButtonProps was added
  • The close button label is now localized (the Japanese label is unchanged)
  • The background token changed from surface to surfaceContainerBright

CheckBox / ChoiceBox

  • Support for the Ark UI v5 indeterminate state. checked can now be "indeterminate" in addition to boolean
  • The position of the hidden input element in ChoiceBox changed

Pagination

  • aria-label / title are now localized (the Japanese labels are unchanged)

Button / IconButton

  • The ButtonProps type is now exported
  • The loading indicator changed to ProgressIndicatorIndeterminate
  • Background and outline tokens changed

New components

Chart, DataTable, DatePicker, Slider, Steps, and Tooltip were added. They do not affect existing code.

Customizing styles

The most common issue when migrating from v1 is CSS overrides targeting generated class names no longer taking effect. Check whether your app CSS depends on generated class names.

# Check your app CSS for dependencies on generated class names
grep -rnE --include='*.css' 'bg_sd|c_sd|bd_sd|sd\.system' src

Use the following instead of generated class names.

  • Props — props provided by each component, such as size and styleType. This is the safest option
  • className — adds styles to the root element. Not every component supports it (as of v3.5.1, AccordionGroup, List, PasswordField, and RadioGroup do not), and it does not reach internal elements
  • Overriding design tokens — to change colors or sizes across the whole theme, see Theming
  • Ark UI data-scope / data-part attribute selectors — can be used to target internal elements. More stable than generated class names, but they may change with major Ark UI upgrades

There is currently no API (such as classNames or slotProps) for stably targeting internal elements. If you need one, please start a thread in GitHub Discussions.

Portal and z-index behavior

Select, Search, DropdownMenu, and DatePicker render their options or menus through a Portal. In v3 they behave as follows.

  • portalled (default true): rendered under body. However, when used inside a Serendie UI ModalDialog / Drawer, they are automatically rendered inside that dialog’s content
  • z-index values are defined by design tokens (sd.system.elevation.zIndex.dropdown = 500, sd.system.elevation.zIndex.modal = 1000)
  • portalled={false}: rendered in place without a Portal. Options may be clipped by a parent element’s overflow: hidden

When used inside a dialog that is not from Serendie UI (a custom dialog or one from another library), the options are rendered under body, so they are hidden if the dialog’s z-index is greater than 500. In that case, pass portalled={false} or adjust the dialog’s z-index.

// When options are hidden inside a non-SDS dialog
<Select items={items} portalled={false} />

Rendering can also be affected if your app CSS changes z-index or creates a stacking context (transform, filter, isolation, etc.), or if the @layer declaration order differs from the setup instructions.

Update checklist

  1. Check dependencies with npm ls @ark-ui/react @pandacss/dev (@pandacss/dev is not a regular dependency from v3.1.1)
  2. Run npm audit --omit=dev --audit-level=high to check for High or higher severity vulnerabilities
  3. Find CSS that targets generated class names and replace it with props, className, or design tokens
  4. For v1 ProgressIndicator color="gray", ProgressIndicatorIndeterminate color="subtle" (gray.300) is the closest v3 value, but not identical; there is no equivalent for color="white". Choose between v3 color="primary" | "subtle" and check the rendered appearance
  5. Find Select / Search / DropdownMenu used inside dialogs, and consider portalled={false} for dialogs that are not from Serendie UI
  6. Confirm that Select onValueChange handlers do not assume firing when the same value is selected again
  7. Confirm that CheckBox / ChoiceBox checked is not treated as a strict boolean
  8. Confirm that @layer reset, base, tokens, recipes, utilities; in the root CSS is declared before your app CSS
  9. Check layouts at both compact and expanded breakpoints (expanded is the only standard Serendie UI breakpoint)
  10. If you use dark mode, configure colorMode on SerendieProvider and add ColorSchemeScript