diff --git a/skills/README.md b/skills/README.md new file mode 100644 index 00000000000..71e8f668481 --- /dev/null +++ b/skills/README.md @@ -0,0 +1,33 @@ +# Skills + +This directory contains agent skills for working with this repository. + +## Available Skills + +Currently, only **internal skills** for maintainers of this repository are offered. + +| Skill | Description | Invocation | +| --------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ----------------------- | +| `ui5wc-upgrade` | Guides a complete `@ui5/webcomponents` version upgrade — updates dependencies, regenerates wrappers, syncs theming parameters, detects new components and breaking changes, and verifies the build. | `/ui5wc-upgrade 2.25.0` | + +### Installing Internal Skills + +Since these skills are marked as internal, `npx skills` does not list them by default. To discover and install them, set the `INSTALL_INTERNAL_SKILLS` environment variable: + +```bash +INSTALL_INTERNAL_SKILLS=1 npx skills add SAP/ui5-webcomponents-react --list +``` + +Alternatively, install from a local checkout: + +```bash +INSTALL_INTERNAL_SKILLS=1 npx skills add ./skills --skill ui5wc-upgrade +``` + +## Requesting New Skills + +If you use an AI coding agent with UI5 Web Components for React and feel a skill would improve your workflow — whether for component usage, migration, styling, testing, or anything else — we'd love to hear about it. + +Additionally to the [`@ui5/webcomponents-react-mcp` MCP server](../packages/mcp-server/README.md), skills can provide guided multi-step workflows, bundled scripts, and domain-specific knowledge that go beyond what an MCP server offers. + +Open an issue describing your use case and we'll evaluate whether a public skill would be a good fit. diff --git a/skills/maintainer/ui5wc-upgrade/SKILL.md b/skills/maintainer/ui5wc-upgrade/SKILL.md new file mode 100644 index 00000000000..d570b015094 --- /dev/null +++ b/skills/maintainer/ui5wc-upgrade/SKILL.md @@ -0,0 +1,367 @@ +--- +name: ui5wc-upgrade +description: Guide a complete UI5 Web Components version upgrade in the ui5-webcomponents-react monorepo. Updates root and peer dependencies, regenerates wrapper components, syncs theming parameters, updates version-info, detects new components and breaking changes, and verifies the build. Use when a new @ui5/webcomponents version is released and the monorepo needs upgrading. +disable-model-invocation: true +argument-hint: target version (e.g. 2.22.0) +allowed-tools: + - Bash(yarn create-webcomponents-wrapper*) + - Bash(yarn create-webcomponents-wrapper-ai*) + - Bash(yarn create-webcomponents-wrapper-compat*) + - Bash(yarn create-theming-parameters*) + - Bash(yarn create-exports*) + - Bash((cd packages/cli && tsc)*) + - Bash(yarn install*) + - Bash(yarn build*) + - Bash(yarn lint*) +metadata: + internal: true +--- + +# UI5 Web Components Upgrade Protocol + +Follow each step in order. Do NOT skip verification gates. + +## Prerequisites + +Ensure the working tree is clean before starting (`git status` should show no uncommitted changes). The upgrade touches many files across multiple packages, and a dirty tree makes it hard to isolate upgrade-related changes and risks committing unrelated work. + +## Initialization + +1. Parse the **target version** from the argument (e.g. `2.25.0` or `2.25.1`). +2. Derive the **tilde range** `~TARGET_VERSION` for peerDependencies (e.g. `~2.25.1`). +3. Read the **current version** from root `package.json` → `dependencies["@ui5/webcomponents"]`. +4. If current matches target, ask if the user wants to re-run wrapper generation only (skip to Step 2). +5. Check if Renovate already updated root deps — if `dependencies["@ui5/webcomponents"]` already matches target, note that Step 1a can be skipped. + +--- + +## Step 1: Update Dependencies + +### 1a. Root `package.json` + +Skip if Renovate already handled this. + +Update to the exact target version: + +**dependencies:** `@ui5/webcomponents`, `@ui5/webcomponents-fiori`, `@ui5/webcomponents-ai`, `@ui5/webcomponents-compat`, `@ui5/webcomponents-icons` + +**devDependencies:** `@ui5/webcomponents-tools` + +> `@ui5/webcomponents-base` is NOT a direct root dependency — only update it in peerDependencies. + +### 1b. Package peerDependencies + +Update tilde ranges to `~TARGET_VERSION` in all sub-packages. See `references/package-json-peer-deps.md` for the exact map. Summary: + +| File | Keys to update | +| ---------------------------------------- | ------------------------------------------------------- | +| `packages/main/package.json` | `@ui5/webcomponents`, `-base`, `-fiori`, `-icons` | +| `packages/base/package.json` | `@ui5/webcomponents-base` | +| `packages/ai/package.json` | `@ui5/webcomponents-ai` | +| `packages/compat/package.json` | `@ui5/webcomponents-compat`, `@ui5/webcomponents-react` | +| `packages/charts/package.json` | `@ui5/webcomponents-react`, `-react-base` | +| `packages/cypress-commands/package.json` | `@ui5/webcomponents`, `-base` | + +### 1c. Install + +```bash +yarn install +``` + +### Verify + +```bash +grep -r "~OLD_MINOR" packages/*/package.json +``` + +Must return zero results (replace OLD_MINOR with the previous minor version tilde range). + +--- + +## Step 2: Compile CLI & Generate Wrappers + +Run in sequence: + +```bash +(cd packages/cli && tsc) +yarn create-webcomponents-wrapper +yarn create-webcomponents-wrapper-ai +yarn create-webcomponents-wrapper-compat +``` + +`create-webcomponents-wrapper` already runs prettier, eslint --fix, and `sb:prepare-cem`. + +### Verify + +All commands exit 0. Then capture the diff for Steps 6 and 7: + +```bash +git diff --stat +git diff --name-status | grep "^A" +``` + +If any command fails, see `references/common-pitfalls.md`. + +--- + +## Step 2b: Restore Custom Code in Generated Wrappers + +The wrapper generator overwrites ALL files, including ones with hand-written customizations. +These components have custom code that MUST be restored after every generation run. +See `references/custom-wrapper-code.md` for the exact code to restore. + +**Components with custom code:** + +| Component | Package | Custom Code | +| ---------------- | ------- | ----------------------------------------------------------------------------------- | +| `ExpandableText` | main | `addCustomCSSWithScoping` for whitespace, `DeprecatedExpandableTextProps` interface | +| `Table` | compat | `getCompatCustomElementsScopingSuffix` + tag name suffix | +| `TableCell` | compat | Same scoping suffix pattern | +| `TableColumn` | compat | Same scoping suffix pattern | +| `TableGroupRow` | compat | Same scoping suffix pattern | +| `TableRow` | compat | Same scoping suffix pattern | + +**Procedure:** + +1. Read the current generated file for each component above. +2. Read the reference in `references/custom-wrapper-code.md` for the custom code to merge. +3. Merge the custom code into the generated output. The generated types/props/JSDoc may + have changed — integrate the custom additions with the new generated base. +4. If a generated change conflicts with the custom code in a way that cannot be + automatically resolved (e.g., a type the custom code depends on was removed), + **STOP and inform the user** with details of the conflict. +5. If the merge is possible but the generated code changed for these specific components + (new props, changed types, updated JSDoc), **inform the user** that these components + had generated changes that were merged with existing custom code. + +### Verify + +```bash +git diff packages/compat/src/components/Table/index.tsx +git diff packages/compat/src/components/TableCell/index.tsx +git diff packages/compat/src/components/TableColumn/index.tsx +git diff packages/compat/src/components/TableGroupRow/index.tsx +git diff packages/compat/src/components/TableRow/index.tsx +git diff packages/main/src/webComponents/ExpandableText/index.tsx +``` + +Each file should show ONLY the expected generated changes (updated props, JSDoc, etc.) while +retaining all custom code blocks. + +--- + +## Step 3: Sync ThemingParameters + +```bash +yarn create-theming-parameters +``` + +### Verify + +```bash +git diff packages/base/src/styling/ThemingParameters.ts +``` + +Note added/removed CSS variable mappings for the PR description. + +--- + +## Step 4: Update version-info.json + +Edit `config/version-info.json` — add a new entry before the closing `}`: + +```json +"X.Y.0": "TARGET_VERSION" +``` + +The key is the React wrapper minor version (`X.Y.0`), the value is the upstream `@ui5/webcomponents` target version from the argument. The React wrapper version itself is bumped by lerna during the release. + +### Verify + +```bash +node -e "JSON.parse(require('fs').readFileSync('config/version-info.json','utf8'));console.log('OK')" +``` + +--- + +## Step 5: Check for Theme Changes + +```bash +ls packages/main/src/themes/*.css +``` + +Compare against the `Theme` enum in `packages/main/src/enums/Theme.ts`. + +Check the UI5 Web Components release notes for theme additions/removals/consolidations. + +If themes changed, follow `references/theme-and-storybook-checklist.md`. If not, skip. + +--- + +## Step 6: Check for New Components (BEFORE build) + +### 6a. Identify new components + +From the `git diff --name-status | grep "^A"` output in Step 2, look for new directories under: + +- `packages/main/src/webComponents/` +- `packages/ai/src/components/` +- `packages/compat/src/components/` + +### 6b. Update barrel exports + +The wrapper generator does NOT update barrel `index.ts` files. For each new component, add an export line in alphabetical order: + +- `packages/main/src/webComponents/index.ts` → `export * from './/index.js';` +- `packages/ai/src/components/index.ts` (if AI component) +- `packages/compat/src/components/index.ts` (if compat component) + +**This must happen BEFORE `yarn build`** — otherwise `tsc` won't compile new components into `dist/`, and `create-exports` will miss them. + +### 6c. Stories and docs (can be done after build) + +Create for each new component: + +``` +/.stories.tsx +/.mdx +``` + +Follow the pattern of a similar existing component. + +If no new components, skip this step. + +--- + +## Step 7: Check for Breaking Changes + +From the wrapper diff, check: + +**7a. Removed or renamed props** — deleted lines in `interface *Attributes` blocks. + +**7b. Changed event signatures** — changes in event detail type imports. + +**7c. Removed components** — entire component directories deleted. + +**7d. Impact on custom components:** + +```bash +grep -r "ChangedTypeName\|RemovedPropName" packages/main/src/components/ +``` + +**Present findings prominently:** + +``` +## BREAKING CHANGES DETECTED +### +- Removed prop: `oldProp` +- Renamed: `oldName` → `newName` +``` + +If none: "No breaking changes detected in generated wrappers." + +--- + +## Step 8: Build & Verify + +```bash +yarn build +yarn lint +``` + +If lint fails, try `yarn lint --fix` first. + +### 8b. Generate export maps (requires dist/ from build) + +```bash +yarn create-exports +``` + +This reads `dist/` directories to update `package.json` exports maps for new components. + +### Verify + +Both commands exit 0. Check if `create-exports` modified any `package.json` files: + +```bash +git diff packages/*/package.json +``` + +--- + +## Step 9: Update Docs + +> Renovate handles examples, templates, and patterns — skip those. + +Only update: + +- `docs/Welcome.mdx` — if theme list or version table changed +- Component stories — if breaking changes affected story props + +--- + +## Step 10: Commit & PR + +### Commit + +Review `git status` before staging. Only stage upgrade-related files — avoid sweeping `git add -A` if unrelated changes are present. + +```bash +git add package.json yarn.lock config/version-info.json \ + packages/*/package.json \ + packages/main/src/webComponents/ \ + packages/ai/src/components/ \ + packages/compat/src/components/ \ + packages/base/src/styling/ThemingParameters.ts \ + .storybook/custom-element-manifests/ +git commit -m "feat: update to UI5 Web Components X.Y.0" +``` + +### PR description template + +```markdown +## Summary + +- Update `@ui5/webcomponents` family from A.B.C to X.Y.0 +- Regenerated wrapper components for main, fiori, AI, and compat packages +- Synced ThemingParameters + +## New Components + + + +## Breaking Changes + + + +## Theme Changes + + + +## ThemingParameters Changes + + +``` + +### Push & create PR + +```bash +git push -u origin feat/ui5wc-X.Y.0 +gh pr create --title "feat: update to UI5 Web Components X.Y.0" --body "" +``` + +--- + +## Quick Reference: Scripts + +| Script | Purpose | +| ------------------------------------------ | -------------------------------------------------- | +| `yarn install` | Install after version bumps | +| `(cd packages/cli && tsc)` | Compile wrapper generator | +| `yarn create-webcomponents-wrapper` | Main + fiori wrappers + prettier + eslint + CEM | +| `yarn create-webcomponents-wrapper-ai` | AI wrappers | +| `yarn create-webcomponents-wrapper-compat` | Compat wrappers | +| `yarn create-theming-parameters` | Regenerate ThemingParameters.ts | +| `yarn create-exports` | Regenerate package.json exports maps (needs dist/) | +| `yarn build` | Full monorepo build | +| `yarn lint` | ESLint | diff --git a/skills/maintainer/ui5wc-upgrade/references/common-pitfalls.md b/skills/maintainer/ui5wc-upgrade/references/common-pitfalls.md new file mode 100644 index 00000000000..c6daf15e8c4 --- /dev/null +++ b/skills/maintainer/ui5wc-upgrade/references/common-pitfalls.md @@ -0,0 +1,115 @@ +# Common Pitfalls During UI5 WC Upgrades + +## Wrapper Generator Overwrites Custom Code + +The generator blindly overwrites ALL files, including wrappers with hand-written +customizations. Step 2b in the main protocol handles restoring this code. See +`references/custom-wrapper-code.md` for the exact customizations. Affected: + +- **ExpandableText** (main): deprecated compat props + custom CSS injection +- **Table, TableCell, TableColumn, TableGroupRow, TableRow** (compat): MFE scoping suffix + +If you skip Step 2b, these customizations are silently lost. + +--- + +## Renovate Partial Updates + +Renovate typically creates a PR that updates ONLY: + +- Root `package.json` dependencies/devDependencies +- `yarn.lock` + +It does NOT: + +- Update peerDependencies in sub-packages +- Run wrapper generation +- Update `config/version-info.json` +- Update ThemingParameters +- Check for new components or breaking changes + +**Always complete all steps even when starting from a Renovate PR.** + +--- + +## @ui5/webcomponents-tools Version Lag + +The `-tools` package sometimes releases a few days after the main packages. If the target version doesn't exist on npm for `-tools`: + +- Keep the previous version in `devDependencies` +- Note in the PR: "`@ui5/webcomponents-tools` not yet available at X.Y.0" +- Follow up when it's published + +Check availability: `npm view @ui5/webcomponents-tools@X.Y.0 version` + +--- + +## CLI Compilation Failures + +If `(cd packages/cli && tsc)` fails, common causes: + +1. New fields in the upstream Custom Elements Manifest (CEM) that the CLI types don't expect. Check `packages/cli/src/scripts/create-wrappers/main.ts`. +2. Breaking changes in `@ui5/webcomponents-tools` types (CEM type definitions come from this package). + +Fix: Update the CLI code to handle new CEM fields, then retry. + +--- + +## Wrapper Generator Does NOT Update Barrel Exports + +`packages/cli/src/scripts/create-wrappers/main.ts` only creates individual `/index.tsx` files. It does NOT touch: + +- `packages/main/src/webComponents/index.ts` +- `packages/ai/src/components/index.ts` +- `packages/compat/src/components/index.ts` + +New components must be added to these barrel files manually BEFORE `yarn build`, otherwise `tsc` won't compile them into `dist/`. + +--- + +## create-exports Requires Prior Build + +`scripts/create-export-paths.ts` reads from `dist/` directories using `fs.existsSync`. New components only appear in `dist/` after a successful `yarn build`. Running `yarn create-exports` before building will miss new components. + +--- + +## Abstract / Internal Components + +Some generated components are abstract base classes that should not be exported. `scripts/create-export-paths.ts` has an `INTERNAL_COMPONENTS` set that excludes them: + +Current list: `ObjectPageAnchorBar`, `Splitter` + +If a new abstract component appears (check for `@abstract` in its JSDoc), add it to `INTERNAL_COMPONENTS` before running `yarn create-exports`. + +--- + +## CEM JSON Files Are Large + +Changes to `.storybook/custom-element-manifests/*.json` can be 10,000–50,000 lines. This is normal — they are regenerated from upstream CEM data by `sb:prepare-cem`. Do not be alarmed by large diffs in these files. + +--- + +## Compat Package May Have No Changes + +Not every UI5 WC release changes the compat package. If `yarn create-webcomponents-wrapper-compat` produces zero diff, that's expected. + +--- + +## Theme Consolidation History + +Past theme changes for reference: + +- **v2.21.0**: Removed `sap_belize`, `sap_belize_hcb`, `sap_belize_hcw`. Consolidated `sap_horizon_dark` and `sap_horizon_hcw` CSS into `sap_horizon.css` (single selector). Renamed `sap_horizon_hcb.css` to `sap_horizon_hc.css`. Added `sap_horizon_auto` and `sap_horizon_hc_auto` enum values. +- Horizon themes have been the default since v2.0. + +--- + +## Wrapper Generation Already Runs Formatting + +`yarn create-webcomponents-wrapper` already runs: + +- `prettier --write` on generated files +- `eslint --fix` on `*/index.tsx` files +- `sb:prepare-cem` for Storybook manifests + +No need to re-run these separately after wrapper generation. diff --git a/skills/maintainer/ui5wc-upgrade/references/custom-wrapper-code.md b/skills/maintainer/ui5wc-upgrade/references/custom-wrapper-code.md new file mode 100644 index 00000000000..32fa5f5b014 --- /dev/null +++ b/skills/maintainer/ui5wc-upgrade/references/custom-wrapper-code.md @@ -0,0 +1,138 @@ +# Custom Code in Generated Wrappers + +These wrappers have hand-written customizations that the generator overwrites on every run. +After running the wrapper generator, restore the custom code described below. + +If the generated output changed for any of these components (new props, renamed events, etc.), +**merge** the custom code with the new generated base. If the merge is not possible (e.g., +a type the custom code depends on was removed), **STOP and inform the user**. + +--- + +## ExpandableText (`packages/main/src/webComponents/ExpandableText/index.tsx`) + +### Custom import + +Add after the other imports: + +```tsx +import { addCustomCSSWithScoping } from '@ui5/webcomponents-react-base/internal/utils'; +``` + +### Custom CSS injection (top-level, after imports) + +```tsx +//todo: remove once ExpandableText supports setting white-space +addCustomCSSWithScoping( + 'ui5-expandable-text', + ` +:host([data-_render-whitespace]) [ui5-text]{ +white-space: pre-wrap; +}`, +); +``` + +### DeprecatedExpandableTextProps interface (before ExpandableTextAttributes) + +```tsx +interface DeprecatedExpandableTextProps { + /** + * Text of the component. + * + * @deprecated: Please use `text` instead. + */ + children?: string; + /** + * Determines if the full text should be displayed inside a `ResponsivePopover` or in-place. + * + * @deprecated: Please use `overflowMode` instead. + */ + showOverflowInPopover?: boolean; + //todo: deprecate once white-space can be applied w/o addCustomCSS + /** + * Defines how white-space inside Text is handled. If set to true, sequences of white space are preserved. + */ + renderWhitespace?: boolean; +} +``` + +### Modified PropTypes interface + +The `ExpandableTextPropTypes` must extend `DeprecatedExpandableTextProps` and exclude +`children` from `CommonProps`: + +```tsx +interface ExpandableTextPropTypes + extends + ExpandableTextAttributes, + Omit, + DeprecatedExpandableTextProps {} +``` + +The generator will produce: + +```tsx +interface ExpandableTextPropTypes extends ExpandableTextAttributes, Omit {} +``` + +### Modified JSDoc + +Add to the component JSDoc, before the `__Note:__ This is a UI5 Web Component!` line: + +``` + * __Note:__ For compatibility reasons, `children`, `showOverflowInPopover`, and `renderWhitespace` are added by the UI5 Web Components for React wrapper and are not part of the underlying web component (`ui5-expandable-text`). + * These props will be removed in the next major release (not yet planned); see their deprecation notices for alternatives. +``` + +--- + +## Compat Table Components + +All 5 compat table components share the same custom code pattern for MFE scoping support. + +**Affected files:** + +- `packages/compat/src/components/Table/index.tsx` +- `packages/compat/src/components/TableCell/index.tsx` +- `packages/compat/src/components/TableColumn/index.tsx` +- `packages/compat/src/components/TableGroupRow/index.tsx` +- `packages/compat/src/components/TableRow/index.tsx` + +### Custom import + +Add after the other `@ui5/webcomponents-compat` imports: + +```tsx +import { getCompatCustomElementsScopingSuffix } from '@ui5/webcomponents-compat/dist/utils/CompatCustomElementsScope.js'; +``` + +### Scoping suffix constants (top-level, after imports, before interfaces) + +```tsx +const compatScopingSuffix = getCompatCustomElementsScopingSuffix(); +const tagSuffix = compatScopingSuffix ? `-${compatScopingSuffix}` : ''; +``` + +### Modified `withWebComponent` tag name + +The generator produces a plain string tag name: + +```tsx +const Table = withWebComponent( + 'ui5-table', +``` + +Replace with template literal using the suffix: + +```tsx +const Table = withWebComponent( + `ui5-table${tagSuffix}`, +``` + +Apply the same pattern for each component: + +- `Table` → `` `ui5-table${tagSuffix}` `` +- `TableCell` → `` `ui5-table-cell${tagSuffix}` `` +- `TableColumn` → `` `ui5-table-column${tagSuffix}` `` +- `TableGroupRow` → `` `ui5-table-group-row${tagSuffix}` `` +- `TableRow` → `` `ui5-table-row${tagSuffix}` `` diff --git a/skills/maintainer/ui5wc-upgrade/references/package-json-peer-deps.md b/skills/maintainer/ui5wc-upgrade/references/package-json-peer-deps.md new file mode 100644 index 00000000000..3bc976703ce --- /dev/null +++ b/skills/maintainer/ui5wc-upgrade/references/package-json-peer-deps.md @@ -0,0 +1,87 @@ +# Package peerDependency Map for UI5 WC Upgrades + +When upgrading to a target version, update tilde ranges to `~TARGET_VERSION` in these files. + +## Root package.json (dependencies, NOT peerDeps) + +Update to exact target version (e.g. `2.25.1`): + +```json +"dependencies": { + "@ui5/webcomponents": "TARGET_VERSION", + "@ui5/webcomponents-ai": "TARGET_VERSION", + "@ui5/webcomponents-compat": "TARGET_VERSION", + "@ui5/webcomponents-fiori": "TARGET_VERSION", + "@ui5/webcomponents-icons": "TARGET_VERSION" +}, +"devDependencies": { + "@ui5/webcomponents-tools": "TARGET_VERSION" +} +``` + +`@ui5/webcomponents-base` is NOT a direct root dependency. + +--- + +## packages/main/package.json + +```json +"peerDependencies": { + "@ui5/webcomponents": "~X.Y.Z", + "@ui5/webcomponents-base": "~X.Y.Z", + "@ui5/webcomponents-fiori": "~X.Y.Z", + "@ui5/webcomponents-icons": "~X.Y.Z" +} +``` + +## packages/base/package.json + +```json +"peerDependencies": { + "@ui5/webcomponents-base": "~X.Y.Z" +} +``` + +## packages/ai/package.json + +```json +"peerDependencies": { + "@ui5/webcomponents-ai": "~X.Y.Z" +} +``` + +## packages/compat/package.json + +```json +"peerDependencies": { + "@ui5/webcomponents-compat": "~X.Y.Z", + "@ui5/webcomponents-react": "~X.Y.Z" +} +``` + +## packages/charts/package.json + +```json +"peerDependencies": { + "@ui5/webcomponents-react": "~X.Y.Z", + "@ui5/webcomponents-react-base": "~X.Y.Z" +} +``` + +## packages/cypress-commands/package.json + +```json +"peerDependencies": { + "@ui5/webcomponents": "~X.Y.Z", + "@ui5/webcomponents-base": "~X.Y.Z" +} +``` + +--- + +## Important Notes + +- `charts` and `compat` reference `@ui5/webcomponents-react` (the React wrapper), not the upstream `@ui5/webcomponents` packages directly. +- `@ui5/webcomponents-react-base` in `charts` tracks the monorepo version, which since v2.4.0 aligns with the UI5 WC minor version. +- `peerDependenciesMeta` sections do NOT need updating — they only mark deps as optional and contain no version info. +- Non-UI5 peer deps (`react`, `react-dom`, `@types/react`, `cypress`) are NOT touched during upgrades. diff --git a/skills/maintainer/ui5wc-upgrade/references/theme-and-storybook-checklist.md b/skills/maintainer/ui5wc-upgrade/references/theme-and-storybook-checklist.md new file mode 100644 index 00000000000..846489fc39c --- /dev/null +++ b/skills/maintainer/ui5wc-upgrade/references/theme-and-storybook-checklist.md @@ -0,0 +1,110 @@ +# Theme Change Checklist + +When UI5 Web Components adds, removes, or renames themes, ALL of the following locations must be updated consistently. + +## 1. Theme CSS Files + +**Location:** `packages/main/src/themes/` + +Each theme has: + +- `.css` — CSS custom properties scoped by `[data-sap-theme]` selector +- `.css.ts` — TypeScript module for the build system + +Current files (as of 2.21.0): + +- `base.css` / `base.css.ts` (always present) +- `sap_fiori_3.css` / `.css.ts` +- `sap_fiori_3_dark.css` / `.css.ts` +- `sap_fiori_3_hcb.css` / `.css.ts` +- `sap_fiori_3_hcw.css` / `.css.ts` +- `sap_horizon.css` / `.css.ts` +- `sap_horizon_hc.css` / `.css.ts` +- `CustomVariables.ts` (always present, not a theme file) + +Action: Add files for new themes, remove files for deleted themes. Note that some theme enum values (like `sap_horizon_dark`) may not have their own CSS file if they were consolidated into another file's selector. + +--- + +## 2. ThemeProvider CSS Imports + +**Location:** `packages/main/src/components/ThemeProvider/ThemeProvider.css` + +This file imports all theme CSS files. Must exactly match the set of `.css` files from the themes directory (excluding `.css.ts` and `CustomVariables.ts`). + +Current: + +```css +@import './Sizes.css'; +@import '../../themes/base.css'; +@import '../../themes/sap_fiori_3.css'; +@import '../../themes/sap_fiori_3_dark.css'; +@import '../../themes/sap_fiori_3_hcb.css'; +@import '../../themes/sap_fiori_3_hcw.css'; +@import '../../themes/sap_horizon.css'; +@import '../../themes/sap_horizon_hc.css'; +``` + +--- + +## 3. Theme Enum + +**Location:** `packages/main/src/enums/Theme.ts` + +TypeScript enum with all valid runtime theme identifiers. + +Current: + +```typescript +export enum Theme { + sap_fiori_3 = 'sap_fiori_3', + sap_fiori_3_dark = 'sap_fiori_3_dark', + sap_fiori_3_hcb = 'sap_fiori_3_hcb', + sap_fiori_3_hcw = 'sap_fiori_3_hcw', + sap_horizon = 'sap_horizon', + sap_horizon_dark = 'sap_horizon_dark', + sap_horizon_hcb = 'sap_horizon_hcb', + sap_horizon_hcw = 'sap_horizon_hcw', + sap_horizon_auto = 'sap_horizon_auto', + sap_horizon_hc_auto = 'sap_horizon_hc_auto', +} +``` + +Note: The enum may contain values without a corresponding CSS file (e.g. `sap_horizon_dark` has no separate file since 2.21.0 — it was consolidated into `sap_horizon.css`'s selector). Enum values are valid runtime identifiers, not file names. + +--- + +## 4. Storybook Theme Picker + +**Location:** `.storybook/utils.ts` + +Update the `MAPPED_THEMES` array: + +```typescript +export const MAPPED_THEMES = [ + { value: 'sap_horizon', title: 'Morning Horizon (Light)' }, + { value: 'sap_horizon_dark', title: 'Evening Horizon (Dark)' }, + { value: 'sap_horizon_hcb', title: 'Horizon High Contrast Black' }, + { value: 'sap_horizon_hcw', title: 'Horizon High Contrast White' }, + { value: 'sap_horizon_auto', title: 'OS Adaptive Horizon Theme' }, + { value: 'sap_horizon_hc_auto', title: 'OS Adaptive High Contrast Horizon Theme' }, + { value: 'sap_fiori_3', title: 'Quartz Light' }, + { value: 'sap_fiori_3_dark', title: 'Quartz Dark' }, + { value: 'sap_fiori_3_hcb', title: 'Quartz High Contrast Black' }, + { value: 'sap_fiori_3_hcw', title: 'Quartz High Contrast White' }, +]; +``` + +--- + +## 5. Welcome Documentation + +**Location:** `docs/Welcome.mdx` + +Contains a manually written "Available Themes" section. Update to match the current theme set. + +--- + +## Not Updated During Upgrades + +- **Examples, templates, patterns** — Renovate handles these separately.