@wix/agent-skills 1.18.2 → 1.19.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (68) hide show
  1. package/package.json +1 -1
  2. package/skills/wix-app/SKILL.md +42 -40
  3. package/skills/wix-app/references/BACKEND_API.md +151 -152
  4. package/skills/wix-app/references/DASHBOARD_PAGE.md +6 -10
  5. package/skills/wix-app/references/EDITOR_REACT_COMPONENT.md +16 -7
  6. package/skills/wix-app/references/EXTENSION_REGISTRATION.md +12 -8
  7. package/skills/wix-app/references/WIX_PATTERNS_DOCS.md +53 -131
  8. package/skills/wix-app/references/dashboard-page/UX_SUCCESS_MODEL.md +1 -2
  9. package/skills/wix-app/references/editor-react-component/ACCESSIBILITY.md +83 -73
  10. package/skills/wix-app/references/editor-react-component/COMPONENT-CONTRACT.md +3 -2
  11. package/skills/wix-app/references/editor-react-component/CSS-GUIDELINES.md +9 -0
  12. package/skills/wix-app/references/editor-react-component/PARTS.md +5 -2
  13. package/skills/wix-app/references/editor-react-component/REACT-GUIDELINES.md +1 -1
  14. package/skills/wix-app/scripts/pkg-root.cjs +73 -0
  15. package/skills/wix-app/scripts/scan-a11y-code.cjs +310 -40
  16. package/skills/wix-app/scripts/scan-a11y-eslint.cjs +118 -24
  17. package/skills/wix-app/scripts/scan-a11y-render.cjs +551 -0
  18. package/skills/wix-app/scripts/scan-a11y-review.cjs +373 -0
  19. package/skills/wix-base44-connector/SKILL.md +24 -22
  20. package/skills/wix-base44-connector/scripts/utils.cjs +39 -3
  21. package/skills/wix-docs/SKILL.md +47 -20
  22. package/skills/wix-headless/entry/bootstrap.mjs +106 -50
  23. package/skills/wix-headless/entry/skill.md +5 -3
  24. package/skills/wix-headless/references/managed/AUTHENTICATION.md +25 -5
  25. package/skills/wix-headless-fast/SKILL.md +25 -7
  26. package/skills/wix-headless-fast/entry/skill.md +23 -14
  27. package/skills/wix-headless-fast/install/fast-path.mjs +48 -5
  28. package/skills/wix-headless-fast/install/pin-agents-md.mjs +57 -0
  29. package/skills/wix-headless-fast/references/shared/CUSTOM_OPERATIONS.md +3 -3
  30. package/skills/wix-headless-fast/references/storefront/INSTRUCTIONS.md +204 -35
  31. package/skills/wix-headless-fast/references/storefront/app/hooks/storefront/useShop.ts +146 -36
  32. package/skills/wix-headless-fast/references/storefront/app/wix/storefront/cart-store.ts +8 -2
  33. package/skills/wix-headless-fast/references/storefront/app/wix/storefront/catalog.ts +95 -20
  34. package/skills/wix-headless-fast/references/storefront/seed/SEED.md +21 -2
  35. package/skills/wix-headless-fast/references/storefront/seed/seed-store.mjs +104 -18
  36. package/skills/wix-manage/SKILL.md +14 -8
  37. package/skills/wix-manage/references/bookings/booking-service-policy-setup.md +59 -33
  38. package/skills/wix-manage/references/bookings/bookings-staff-setup.md +45 -22
  39. package/skills/wix-manage/references/bookings/multi-resource-service-creation.md +70 -12
  40. package/skills/wix-manage/references/calendar/configure-default-business-hours.md +53 -17
  41. package/skills/wix-manage/references/google-ads/billing-and-payment.md +3 -3
  42. package/skills/wix-manage/references/google-ads/create-performance-max-campaign.md +8 -8
  43. package/skills/wix-manage/references/google-ads/get-campaign-suggestions.md +4 -4
  44. package/skills/wix-manage/references/google-ads/google-ads-dashboard-navigation.md +1 -1
  45. package/skills/wix-manage/references/google-ads/install-and-create-account.md +9 -9
  46. package/skills/wix-manage/references/google-ads/query-campaign-analytics.md +7 -7
  47. package/skills/wix-manage/references/seo/manage-content-plan.md +181 -135
  48. package/skills/wix-manage/references/seo/manage-google-search-console.md +272 -0
  49. package/skills/wix-manage/references/sites/upload-static-site.md +53 -0
  50. package/skills/wix-manage/references/stores/change-store-currency.md +1 -1
  51. package/skills/wix-manage/references/stores/create-product-catalog-v3.md +17 -1
  52. package/skills/wix-vibe-headless/platforms/base44-ecom-light-seed-with-install.md +12 -9
  53. package/skills/wix-vibe-headless/platforms/base44-ecom-light-seed.md +12 -9
  54. package/skills/wix-vibe-headless/platforms/base44-ecom-light.md +1 -1
  55. package/skills/wix-vibe-headless/platforms/base44.md +11 -3
  56. package/skills/wix-vibe-headless/references/storefront/INSTRUCTIONS.md +5 -1
  57. package/skills/wix-vibe-headless/references/storefront/seed/SEED.md +5 -4
  58. package/skills/wix-vibe-headless/references/storefront/seed/seed-store.cjs +33 -5
  59. package/skills/wix-app/references/dashboard-page/COLLECTION_TOOLKIT.md +0 -80
  60. package/skills/wix-app/references/dashboard-page/ENTITY_PAGE_TOOLKIT.md +0 -140
  61. package/skills/wix-app/references/dashboard-page/PATTERNS_BUNDLE_READING.md +0 -112
  62. package/skills/wix-headless-fast/references/storefront/app/components/storefront/ProductCard.tsx +0 -100
  63. package/skills/wix-headless-fast/references/storefront/app/components/storefront/ProductDetailView.tsx +0 -130
  64. package/skills/wix-headless-fast/references/storefront/app/components/storefront/ProductGrid.tsx +0 -48
  65. package/skills/wix-headless-fast/references/storefront/app/components/storefront/ShopView.tsx +0 -66
  66. package/skills/wix-headless-fast/references/storefront/app/components/storefront/VariantPicker.tsx +0 -103
  67. package/skills/wix-headless-fast/references/storefront/app-astro/pages/products/[slug].astro +0 -56
  68. package/skills/wix-headless-fast/references/storefront/app-astro/pages/shop.astro +0 -23
@@ -24,7 +24,8 @@ roles intact.
24
24
 
25
25
  ## Workflow
26
26
 
27
- 1. **Scaffold only when creating.** If the component folder does not exist, run:
27
+ 1. **Scaffold only when creating.** If the component folder does not exist, run
28
+ inside the Wix app project (the folder with `wix.config.json`):
28
29
 
29
30
  ```bash
30
31
  npx wix generate --params '{"extensionType":"EDITOR_REACT_COMPONENT","name":"ComponentName","folder":"component-name","description":"A brief description"}'
@@ -37,7 +38,7 @@ roles intact.
37
38
  accessibility-review dependencies are installed:
38
39
 
39
40
  ```bash
40
- node -e "const fs=require('fs'),path=require('path'),ps=['@wix/react-component-schema','@wix/react-component-utils','@wix/editor-react-types','@babel/parser','@babel/traverse','@babel/types','eslint','eslint-plugin-jsx-a11y','@typescript-eslint/parser','typescript','@types/eslint-plugin-jsx-a11y'];const missing=ps.filter(p=>!(require.resolve.paths(p)||[]).some(d=>fs.existsSync(path.join(d,p,'package.json'))));if(missing.length){console.error('Missing dependencies: '+missing.join(', '));process.exit(1)}" || { d="$PWD"; while [ "$d" != "/" ] && [ ! -f "$d/yarn.lock" ]; do d="${d%/*}"; done; if [ -f "$d/yarn.lock" ]; then yarn add @wix/react-component-schema @wix/react-component-utils @wix/editor-react-types && yarn add -D @babel/parser @babel/traverse @babel/types eslint eslint-plugin-jsx-a11y @typescript-eslint/parser 'typescript@<7' @types/eslint-plugin-jsx-a11y; else npm install @wix/react-component-schema @wix/react-component-utils @wix/editor-react-types && npm install --save-dev @babel/parser @babel/traverse @babel/types eslint eslint-plugin-jsx-a11y @typescript-eslint/parser 'typescript@<7' @types/eslint-plugin-jsx-a11y; fi; }
41
+ node -e "const fs=require('fs'),path=require('path'),ps=['@wix/react-component-schema','@wix/react-component-utils','@wix/editor-react-types','@babel/parser','@babel/traverse','@babel/types','eslint','eslint-plugin-jsx-a11y','@typescript-eslint/parser','typescript','@types/eslint-plugin-jsx-a11y','jsdom','axe-core'];const missing=ps.filter(p=>!(require.resolve.paths(p)||[]).some(d=>fs.existsSync(path.join(d,p,'package.json'))));if(missing.length){console.error('Missing dependencies: '+missing.join(', '));process.exit(1)}" || { d="$PWD"; while [ "$d" != "/" ] && [ ! -f "$d/yarn.lock" ]; do d="${d%/*}"; done; if [ -f "$d/yarn.lock" ]; then yarn add @wix/react-component-schema @wix/react-component-utils @wix/editor-react-types && yarn add -D @babel/parser @babel/traverse @babel/types eslint eslint-plugin-jsx-a11y @typescript-eslint/parser 'typescript@<7' @types/eslint-plugin-jsx-a11y jsdom axe-core; else npm install @wix/react-component-schema @wix/react-component-utils @wix/editor-react-types && npm install --save-dev @babel/parser @babel/traverse @babel/types eslint eslint-plugin-jsx-a11y @typescript-eslint/parser 'typescript@<7' @types/eslint-plugin-jsx-a11y jsdom axe-core; fi; }
41
42
  ```
42
43
 
43
44
  3. **Plan the contract and structure.** Identify props, semantic root, named
@@ -47,10 +48,16 @@ roles intact.
47
48
  the props file, logic in TSX, styles in the CSS Module. Do not edit
48
49
  `*.generated.ts`.
49
50
 
50
- 5. **Run the accessibility review.** Follow
51
- [`editor-react-component/ACCESSIBILITY.md`](editor-react-component/ACCESSIBILITY.md): run scanners,
52
- triage output, complete the manual checklist, fix issues, rerun on changed
53
- JSX.
51
+ 5. **Run the accessibility review.** Once the JSX is complete, run from the
52
+ same folder (`<SKILL_ROOT>` is the directory containing the active `SKILL.md`):
53
+
54
+ ```bash
55
+ node <SKILL_ROOT>/scripts/scan-a11y-review.cjs src/extensions/site/components/<component-name>
56
+ ```
57
+
58
+ Then follow [`editor-react-component/ACCESSIBILITY.md`](editor-react-component/ACCESSIBILITY.md):
59
+ fix confirmed findings, rerun after each fix pass (at most two), and report
60
+ what remains.
54
61
 
55
62
  6. **Configure the editor extension when required.** For a new component or a
56
63
  requested sizing, installation, or manifest change, apply
@@ -121,7 +128,9 @@ extension configuration, and supporting files.
121
128
  - Explicit foreground colors need a known contrasting background; transparent
122
129
  roots inherit from the host.
123
130
  - Baseline Widely Available CSS/DOM only, or supported fallbacks.
124
- - Route ARIA through `a11y`; no one-off ARIA props.
131
+ - Accessibility per part, per [`ACCESSIBILITY.md`](editor-react-component/ACCESSIBILITY.md):
132
+ read only `a11y.ariaLabel`, and only for a control without a visible name;
133
+ never spread the `a11y` object or add one-off ARIA props.
125
134
  - Named parts: global class, module class, and `elementProps` (root uses
126
135
  top-level props).
127
136
  - Native design states: pair selectors with injected modifiers; keep non-input
@@ -1,19 +1,24 @@
1
1
 
2
2
  # Extension Registration
3
3
 
4
- `src/extensions.ts` is the single entry point that tells the build system which extensions exist. Without a `.use()` call for an extension, it does not load.
4
+ `src/extensions.ts` is the single entry point that tells the build system which extensions exist. Without a `.use()` call for an extension, it does not load. HTTP endpoints are file-based routes and do not use this registration mechanism.
5
5
 
6
6
  ## Registration is automatic via the CLI
7
7
 
8
- For every CLI-supported extension type, `wix generate --params` updates `src/extensions.ts` for you — you do NOT need to write the import or the `.use()` call by hand. Verify the file was updated after each `wix generate` invocation.
8
+ For every CLI-supported extension type, `wix generate --params` updates `src/extensions.ts` for you — you do NOT need to write the import or the `.use()` call by hand. Verify the file was updated after each `wix generate` invocation. The one exception is `HTTP_ENDPOINT`: it is file-based, `wix generate` does not touch `src/extensions.ts` for it, and an unchanged file after generating an endpoint is expected (see below).
9
9
 
10
- ## Extension types that require manual registration
10
+ ## HTTP endpoints: no registration
11
11
 
12
- | Type | Why manual |
13
- | --- | --- |
14
- | **Backend API** | Astro endpoints under `src/pages/api/` are auto-discovered by the runtime. They do not need to be added to `src/extensions.ts`. |
12
+ `wix generate --params '{"extensionType":"HTTP_ENDPOINT","name":"hello"}'`
13
+ creates the endpoint file without changing `src/extensions.ts`:
15
14
 
16
- Every other extension type is wired up automatically by the CLI.
15
+ | Project | Discovery directory | Example route |
16
+ | --- | --- | --- |
17
+ | `@wix/custom-extensions` (default `apiDir: "endpoints"`) | `src/endpoints/` | `hello.ts` → `/hello` |
18
+ | `@wix/astro` | `src/pages/api/` | `hello.ts` → `/api/hello` |
19
+
20
+ Leave `app()` unchanged. Do not add endpoint imports, `.use()` calls, or IDs.
21
+ See [BACKEND_API.md](BACKEND_API.md) for supported versions and frontend URLs.
17
22
 
18
23
  ## Manual recovery (when the CLI output drifts)
19
24
 
@@ -21,7 +26,6 @@ Edit `src/extensions.ts` directly only when:
21
26
 
22
27
  - The CLI failed mid-run and left the file out of sync
23
28
  - A user hand-edited the file and broke the chain
24
- - You're adding a Backend API helper (uncommon)
25
29
 
26
30
  Each extension file is a default export from `<folder>/<folder>.extension.ts`. In `src/extensions.ts`, import it as a default import using the camelCase of the folder name, then chain `.use(...)`:
27
31
 
@@ -2,174 +2,96 @@
2
2
 
3
3
  ## Prerequisites
4
4
 
5
- Lookups here are direct file reads — no script. Resolve the installed package root once per session and reuse it:
5
+ Resolve the package root once per session and reuse it — a bare `require.resolve` throws under Yarn PnP:
6
6
 
7
7
  ```bash
8
- node -e "
9
- const fs = require('fs'), path = require('path');
10
- function tryEnablePnp() {
11
- let dir = process.cwd();
12
- for (;;) {
13
- const pnp = path.join(dir, '.pnp.cjs');
14
- if (fs.existsSync(pnp)) { try { require(pnp).setup(); } catch {} return; }
15
- const parent = path.dirname(dir);
16
- if (parent === dir) return;
17
- dir = parent;
18
- }
19
- }
20
- tryEnablePnp();
21
- try {
22
- console.log(path.dirname(require.resolve('@wix/patterns/package.json', { paths: [process.cwd()] })));
23
- } catch {
24
- let dir = process.cwd();
25
- for (;;) {
26
- const candidate = path.join(dir, 'node_modules', '@wix', 'patterns');
27
- if (fs.existsSync(path.join(candidate, 'package.json'))) { console.log(candidate); process.exit(0); }
28
- const parent = path.dirname(dir);
29
- if (parent === dir) { console.error('@wix/patterns not found'); process.exit(1); }
30
- dir = parent;
31
- }
32
- }
33
- "
8
+ node <this-skill-dir>/scripts/pkg-root.cjs @wix/patterns
34
9
  ```
35
10
 
36
- A bare `require.resolve` without the PnP-activation step throws in a Yarn Berry project even when installed — run the whole snippet, not a shortened version.
11
+ Then check the install, two ways: `ls <pkgRoot>/dist/dts-bundle/index.json`, and — the one that matters — look for a **`Collection Toolkit`** key once step 1 has the docs index. The guides are *entries inside* that index rather than a directory, so no missing file reveals their absence.
37
12
 
38
- Then confirm the installed version actually ships the bundle index:
13
+ **If either fails, stop and upgrade `@wix/patterns`.** "Which component serves this need" now lives in the package, so proceeding means guessing names; do not hunt elsewhere in `node_modules` for a substitute. Everything below degrades by version rather than breaking, so probe rather than version-check.
39
14
 
40
- ```bash
41
- ls <pkgRoot>/dist/dts-bundle/index.json
42
- ```
15
+ **Patterns API facts come from three published trees only:** `dist/docs/` (pages), `dist/dts-bundle/` (types), `dist/examples/` (worked calls). Never take a component, prop or type from `src/`, `dist/esm/` or `dist/cjs/`, or a deep path a bundle mentions — internals change without notice. `dist/types/` is one narrow exception, used only where step 5 says: `package.json` points `types` at it, so it is what `tsc` enforces. Within those trees, `grep`/`sed` for one declaration usually beats a whole-file read.
43
16
 
44
- **If it's missing, stop — do not look elsewhere for types or docs.** The installed `@wix/patterns` predates the index (ships from **1.458.0**); upgrade and re-run the check. Prefer **1.465.0**+ — the lookups below assume it (`OffsetQuery`, `useEntityPage`'s create route, `withDashboard.md`, a deprecation `status` in `dist/docs/index.json`, page-relative router paths). A missing *file* isn't the same as a name not being covered (see below).
17
+ ## The Discovery Chain
45
18
 
46
- **Never inspect `node_modules` by hand** — no `ls`, `find`, or `cat` of an arbitrary path, not even `dist/dts-bundle/` or `dist/docs/`. Every lookup below names the exact file to `Read` — go straight to it.
19
+ ### 1 — The index
47
20
 
48
- ## Library Architecture
21
+ **Probe `<pkgRoot>/dist/docs/index.json`; do not read it whole.** At ~80 KB a `Read` truncates part-way and reports nothing, so the tail goes silently missing. Pull what you need with one `grep`/`python3` call, resolving every symbol you plan to write in it.
49
22
 
50
- ### Composition Hierarchy
23
+ Start here rather than the bundle index: it carries every documented name *and* the guides.
51
24
 
52
- ```
53
- Provider <- WixPatternsProvider or WixPatternsBMProvider
54
- +-- Page <- CollectionPage, EntityPage, or SettingsPage
55
- +-- Collection <- Table, Grid, TableGridSwitch, etc.
56
- +-- Features <- filters, actions, sorting, drag-and-drop, etc.
57
- ```
25
+ - **Read each entry's `summary` before opening anything.** It is that page's opening paragraph, so for most questions the index *is* the answer and step 4 becomes no read.
26
+ - **Resolve against the keys *and* each entry's `symbols` aliases.** The index is keyed by Storybook title: `ExportButton` lives under `ExportTo`, `CollectionToolbarFilters` under `ToolbarFilters`. Matching is exact — scan for something close before concluding a name isn't covered.
27
+ - **`status: "deprecated"`** means use what `statusMessage` names. A deprecated component still renders, so nothing else stops you.
58
28
 
59
- ### The Collection Triad
29
+ **Not in the docs index? Check `dist/dts-bundle/index.json` before concluding it does not exist.** It curates names with no page of their own — hooks, prop and query types, names re-exported from another package — and carries `importPath` and `file`, so step 4 still applies with no page to read.
60
30
 
61
- Each collection type follows the same Component + State + Hook pattern:
31
+ **For that whole namespace cheaply, `Read <pkgRoot>/dist/dts-bundle/index.txt`** — ~9 KB, one read, every curated name with `kind`, `importPath` and file. From 1.469.0 it adds `bytes`, `props` (`5/63` — what the file declares against what the symbol has) and `stubs`: step 5's triage for every symbol at once, with the columns named in its header. Drop to the `.json` for `readWith`, `readWithBytes` and status prose.
62
32
 
63
- | Component | State Type | Hook |
64
- | --- | --- | --- |
65
- | `Table` | `TableState` | `useTableCollection()` |
66
- | `Grid` | `GridState` | `useGridCollection()` |
67
- | `TableGridSwitch` | `TableGridSwitchState` | `useTableGridSwitchCollection()` |
68
- | `TableFolders` | `TableFoldersState` | `useTableFolders()` |
69
- | `GridFolders` | `GridFoldersState` | `useGridFolders()` |
33
+ ### 2 — Composition, once per session
70
34
 
71
- Common types only; `dist/dts-bundle/index.json` has the authoritative set. Create state with the hook -> pass it to the component's `state` prop -> wrap in a page component.
35
+ `Read <pkgRoot>/dist/docs/Composition and Providers.md` before writing any patterns JSX: which provider, the four nesting layers, the collection triad, and why the provider must be a parent component rather than a sibling — the mistake that throws at runtime while the JSX looks right.
72
36
 
73
- ### Choosing the Right Provider
37
+ ### 3 — Which component serves this need
74
38
 
75
- | Provider | When to Use |
39
+ | Building | Guide |
76
40
  | --- | --- |
77
- | `WixPatternsProvider` | **Default — start here.** Auto-detects the environment (BM, Essentials, Giza). |
78
- | `WixPatternsBMProvider` / `WixPatternsGizaProvider` | Optional alternatives for Yoshi BM Flow (Business Manager / Giza). |
79
- | `WixPatternsEssentialsProvider` | Yoshi Fullstack. |
80
- | `WixPatternsBaseProvider` | App does **not** run under Giza/WixEssentials and you inject services (i18n, sentry) yourself. |
81
-
82
- **Confirm the import path in the provider's own bundle** — not all share a subpath (`WixPatternsEssentialsProvider`, `WixPatternsBaseProvider` live under `@wix/patterns/essentials`).
83
-
84
- ### Keep Provider and Page Separate
85
-
86
- The provider **must** be a parent of the page content: hooks like `useTableCollection` need its context above them in the tree.
87
-
88
- **Wrong:** calling `useTableCollection` in the component that renders `WixPatternsProvider` — the hook runs before the provider exists, so it throws at runtime even though the JSX looks right.
89
-
90
- **Correct — provider in root, page in a separate file:**
91
- ```tsx
92
- // App.tsx
93
- import { WixPatternsProvider } from '@wix/patterns/provider';
94
-
95
- function App() {
96
- return (
97
- <WixPatternsProvider>
98
- <MyCollectionPage />
99
- </WixPatternsProvider>
100
- );
101
- }
102
-
103
- // MyCollectionPage.tsx
104
- import { Table, useTableCollection, OffsetQuery } from '@wix/patterns';
105
- import { CollectionPage } from '@wix/patterns/page';
106
-
107
- function MyCollectionPage() {
108
- // works — the provider context exists above this component
109
- const state = useTableCollection({
110
- queryName: 'my-items',
111
- itemKey: (item) => item.id,
112
- itemName: (item) => item.name,
113
- fetchData: async (query: OffsetQuery) => ({ items: [], total: 0 }),
114
- filters: {},
115
- });
116
- return (
117
- <CollectionPage>
118
- <Table state={state} columns={[{ title: 'Name', render: (item) => item.name }]} />
119
- </CollectionPage>
120
- );
121
- }
122
- ```
41
+ | Anything collection-shaped — tables, filters, search, aggregates, row and bulk actions, empty states | `dist/docs/Collection Toolkit.md` |
42
+ | The path from a listed row to one record, and its form | `dist/docs/Collection to Entity Flow.md` |
123
43
 
124
- Keep the provider (and router, if any) in the app's root component and each page in its own file.
44
+ Each guide's index entry carries `relatedComponents`; every name in it resolves, because `@wix/patterns` fails its own build otherwise. Prefer one of those over a name you recall.
125
45
 
126
- For **multiple pages**, use the `@wix/patterns` routing solution (`PatternsReactRouter`, `PatternsReactRoute`, `usePatternsNavigate`) rather than a separate router. Read `PatternsReactRouter.md` and `withDashboard.md` for setup — the router reads page location from the dashboard context `withDashboard` renders, so it needs that wrapper above it with a `location` prop, and throws at render time without them. (it ships from **1.465.0**; no entry in `dist/docs/index.json` means an older install — use `PatternsReactRouter.md`'s **Requirements**.)
46
+ ### 4 — Read only what answers your question, then stop
127
47
 
128
- ## How to Look Things Up
48
+ | Your question | Read | Path |
49
+ | --- | --- | --- |
50
+ | What is it, and how does it wire in? | **nothing** — the entry says | `summary` |
51
+ | Where do I import it from? | **nothing** — the entry says | `importPath` |
52
+ | How do I call it? | one **example**, or a call in a guide's prose | `dist/examples/<examples[i]>` · `dist/docs/<guide>.md` |
53
+ | What props, and which are optional? | the **example** first; then the **`.d.ts`** *or* the doc — never both | `bundle` present: `dist/dts-bundle/<bundle>` · absent: `dist/docs/<file>` |
54
+ | A setup requirement or gotcha? | the **doc's** prose | `dist/docs/<file>` |
129
55
 
130
- **Don't guess which components or props exist — read the doc files first.**
56
+ Prefix the index's bare values with their tree — `file` → `dist/docs/`, `examples` → `dist/examples/`, `bundle` → `dist/dts-bundle/` — and never rebuild a path from a symbol name.
131
57
 
132
- ### Finding the right name
58
+ **Those two middle rows are one question in practice.** You ask how to call it, start writing, and the question turns prop-shaped mid-call — where the second row sends you to a `.d.ts` that may be stubbed (step 5). Take the props off the example first; go to the `.d.ts` only for what it cannot show — optionality, union members, an exact callback signature.
133
59
 
134
- `Read <pkgRoot>/dist/dts-bundle/index.json` — one entry per name, grouped implicitly by its `category` field. Lookup is **exact-match only** — no fuzzy matching. If the exact key isn't there, scan the index you already hold for something close before concluding the name isn't covered.
60
+ **A guide's prose often holds the call.** `PrimaryActions`' bundle stubs its own props type, while `usePatternsNavigate.md` carries `<PrimaryActions label="Add shift" onClick={…} />` verbatim. Check what you have already read before opening anything.
135
61
 
136
- Not every real export is in this index — only names these guides reference. If a needed name genuinely isn't there, **stop and say so rather than falling back to `node_modules`.**
62
+ **`bundle` and a doc props table are mutually exclusive.** With `bundle`, the page's `### Props` is only a pointer; without it, that table marks what is required. Reading both is one hop too many.
137
63
 
138
- ### Reading doc files
64
+ **A `.d.ts` names props; it never says what they do.** Wiring and defaults live in prose: `CollectionSearch`'s bundle lists four optional props and no behaviour, while its page says the search term reaches your `fetchData` via `query.search`. When a behaviour question outlives the `summary`, open the page.
139
65
 
140
- `Read <pkgRoot>/dist/docs/index.json` to resolve a name to its doc file — or a `symbols` alias, for cases where the Storybook title doesn't match the export (`ExportTo.md` documents `ExportButton`) — then `Read <pkgRoot>/dist/docs/<file>.md` directly, the whole file, not piped through `head`. It covers more names than the bundle index above — every documented component, not just the curated ones.
66
+ **Artifact not listed?** No `examples` — a hook's usage is usually filed under the component it pairs with (`useEntityPage` → `EntityPage/basic.tsx`). No `importPath` — a guide, or documented but not exported. Nothing at all — a state object you receive rather than construct; its doc is the only source.
141
67
 
142
- **Always check the import statement inside the doc** — not everything comes from `@wix/patterns` (some use subpaths, e.g. `@wix/patterns/provider`).
68
+ ### 5 — Traps that make a read wrong
143
69
 
144
- A doc whose index entry has a `bundle` field does **not** list its props — its `### Props` points at that bundle. One without it carries its own table. Either way the doc owns prose, variations, BI events, and the import line.
70
+ **Search inside the file an index named, never across the tree.** A shared shape is re-stubbed in every bundle referencing it, so a tree-wide `grep` returns mostly pointers, and the first hit is rarely the declaration.
145
71
 
146
- ### Reading the file the index names
72
+ **Most bundles stub the parent holding the props — 70 of the 105 curated entries do** — and the index says so per entry. **`dist/dts-bundle/index.json` is the triage surface, not merely a fallback for names the docs index lacks:** a component entry carries `ownProps` / `inheritedProps` beside `bytes` and `readWith`, so "is this file the whole answer" is a lookup, not an inspection.
147
73
 
148
- The mechanics of the file an index names — batching the reads, types docs don't cover, one-line stubs that are answers rather than truncation, subpath entry points, cross-references, split compound docs — are in [Reading bundles and docs](dashboard-page/PATTERNS_BUNDLE_READING.md). Read it before your first `dist/dts-bundle/*.d.ts` of the session.
74
+ - `Table` → `ownProps: 5, inheritedProps: 58`, `readWith` naming 3 files. Five of sixty-three.
75
+ - `PrimaryActions` → `ownProps: 0, inheritedProps: 12`. A 470-byte file declaring none of them.
76
+ - No `ownProps` on a component entry means no split — that file *is* the whole answer.
149
77
 
150
- ## The Collection → Entity Flow
78
+ A split is not a dead end: the parent is a real file, `readWith` names it, and from 1.469.0 so does the stub inside the file (`Full shape: types/Filter.d.ts`). **Read that one file — one hop, not N.** The rest of `readWith` is types referenced *inside* it, opened only if needed. Judge by the entry's own `bytes`, never `readWithBytes` — `Table`'s are 5,277 against 31,731 — since the combined figure talks you out of a read you should just do. A `…Params` type built from `Pick<>`/`Omit<>` is the same trap in another shape.
151
79
 
152
- A collection page and its item form are **two patterns pages**, not a page plus a modal. Reserve modals for dialogs that neither write nor display a listed record (a delete or discard confirmation, an unsaved-changes prompt); **a create / "add new" form is not one of them** — it writes the record, so it's an `EntityPage` regardless of size. A page that lists nothing is outside this rule — full test in [SKILL.md](../SKILL.md#entity-create-and-edit).
80
+ **When you do need several `readWith` files, read them in one call** — one `Read` per file in a single message. Reads measure ~21 ms each, so ten is a fifth of a second and one round trip. Deciding is what costs: decide once, then batch, and never hop one file per turn. Batching is not a licence to skip the filter, though — a few deliberate reads beat dozens of just-in-case ones.
153
81
 
154
- | Step | What owns it |
155
- | --- | --- |
156
- | Navigate from a row / primary action to the item | `usePatternsNavigate()` → `navigateToEntityPage({ path, entity })` |
157
- | Register the route | `PatternsReactRoute` inside `PatternsReactRouter` |
158
- | Fetch, save, validation, dirty state, skeletons, errors | `useEntityPage({ fetch, onSave })` |
159
- | Form state and field binding | `useForm` / `useController` from `@wix/patterns/form` — `useController`, never `register` |
160
- | Body layout | `EntityPage.Header`, `.MainContent`, `.AdditionalContent`, `.Card` |
161
- | The individual fields inside those cards | `@wix/design-system` (`FormField`, `Input`, `Text`) |
82
+ **If the parent is large, take the declaration `tsc` uses.** `dist/types/components/CollectionTable/CollectionTable.d.ts` is 5,919 B against the bundle's 20,802 B, carries JSDoc, and states `columns: TableColumn<T>[]` (required) outright. Nothing there is stubbed, so a `grep` for a prop name is reliable. This case only.
162
83
 
163
- Prefer `navigateToEntityPage` over a plain route change — the entity header renders before the fetch resolves. **Every `path` above is page-relative**: the router roots at `path="/"` even on a page scaffolded `route: "shifts"`, so never repeat that name in a `path`, `parentPath`, or `navigateToEntityPage` call — it fails silently. See [ENTITY_PAGE_TOOLKIT.md](dashboard-page/ENTITY_PAGE_TOOLKIT.md).
84
+ The generated files' conventions — which one-line stubs are answers rather than truncation, how entry-point files are scoped — are in `dist/docs/Reading the Doc Indices.md`, worth reading before your first `dist/dts-bundle/*.d.ts` of the session.
164
85
 
165
- Read `EntityPage.md`, `useEntityPage.md` and `usePatternsNavigate.md` before implementing, plus [ENTITY_PAGE_TOOLKIT.md](dashboard-page/ENTITY_PAGE_TOOLKIT.md) for the `useEntityPage` call itself (generics, `onSave`, params). Note `useCreateCollection` is **not** about creating items: it returns a function that initializes collection state.
86
+ ### Rules for the reads themselves
166
87
 
167
- ## When Patterns Has No Equivalent
88
+ - **Use the exact `file`, `bundle` and `examples` values, prefixed per step 4.** Bundles nest one directory per kind, so `<Name>.d.ts` at the top level is wrong by construction, and an example slug is not derivable from a title.
89
+ - **Extract from the file the index named.** A whole-file `Read` is safe (`bytes` gives the size first); a scoped `grep`/`sed` is cheaper. If an extraction is empty or ambiguous, read the whole file rather than guess.
90
+ - **A `@wix/design-system` name is not yours to look up here.** Use the `wix-design-system` skill; never follow a deep `@wix/design-system/dist/...` path a bundle mentions.
91
+ - **If a name is in neither index, stop and say so**, naming the path that dead-ended. A wrong guess compiles and breaks at runtime.
168
92
 
169
- A concept is only "missing" from patterns after you've checked `dist/dts-bundle/index.json` and `dist/docs/index.json` **and** searched by keyword within what you've read. Then:
93
+ ## When Patterns Has No Equivalent
170
94
 
171
- 1. Look the component up in `@wix/design-system` via the `wix-design-system` skill.
172
- 2. Render it *inside* the patterns page shell / collection, not as a replacement for it.
173
- 3. If WDS lacks it too, compose from WDS primitives (`Box`, `Card`, `Text`) — never restyle patterns internals, never add another UI library.
95
+ A concept is only "missing" after you have checked both indices **and** searched by keyword in what you have read. Then look it up via the `wix-design-system` skill and render it *inside* the patterns page shell rather than in place of it; if WDS lacks it too, compose from `Box`, `Card` and `Text`. Never restyle patterns internals, and never add another UI library.
174
96
 
175
- Anything page- or collection-shaped (shell, header, table, grid, filters, sorting, paging, row/bulk actions) is patterns' territory. Building one from WDS parts means a skipped lookup.
97
+ Anything page- or collection-shaped is patterns' territory; building one from WDS parts means a skipped lookup.
@@ -112,7 +112,6 @@ Presentation success applies across all five stages. Choose both the right **rep
112
112
  | **Kanban** | Work moves through meaningful stages. | Stage, workload, and valid movement are understandable. |
113
113
  | **Timeline or calendar** | Time, sequence, or scheduling matters. | Upcoming activity, conflicts, and timing are clear. |
114
114
  | **Chart** | The user needs to understand a trend or relationship. | The visualization answers a specific business question. |
115
- | **Summary metrics** | The user needs a quick health signal. | Metrics clarify current conditions and where to focus. |
116
115
 
117
116
  - Choose the default view that best supports the primary task.
118
117
  - Offer another view only when it provides distinct value.
@@ -130,7 +129,7 @@ Choose the smallest interface that gives users enough context and room to comple
130
129
  | **Entity page** | The task involves complex details, multi-section editing, history, or related information. | The user has enough space and structure to complete deeper work. |
131
130
  | **Inline or expanded row** | The user needs a quick inspection or simple action. | Detail appears without creating a separate workspace. |
132
131
 
133
- Which Wix primitive builds each of these — and which components serve the summaries, filters and empty states named above — is in [Collection Toolkit](COLLECTION_TOOLKIT.md). Patterns has no side panel; that one is WDS.
132
+ Which Wix primitive builds each of these — and which components serve the summaries, filters and empty states named above — is in the installed package's `Collection Toolkit.md` guide — reached through [The Discovery Chain](../WIX_PATTERNS_DOCS.md#the-discovery-chain). Patterns has no side panel; that one is WDS.
134
133
 
135
134
 
136
135
  ## Data Success
@@ -1,13 +1,13 @@
1
1
  # Accessibility Implementation and Review
2
2
 
3
- Use this reference while authoring Editor React Component props and JSX and
4
- after every JSX edit.
3
+ Use this reference while authoring Editor React Component props and JSX, then
4
+ run the review command once the JSX is complete.
5
5
 
6
6
  ## Contents
7
7
 
8
8
  - [Implementation Contract](#implementation-contract)
9
9
  - [Review Scope](#review-scope)
10
- - [Automated Scanners](#automated-scanners)
10
+ - [Automated Review](#automated-review)
11
11
  - [Finding Triage](#finding-triage)
12
12
  - [Manual Review](#manual-review)
13
13
  - [Pre-Fix Checks for Non-Interactive Controls](#pre-fix-checks-for-non-interactive-controls)
@@ -15,29 +15,42 @@ after every JSX edit.
15
15
 
16
16
  ## Implementation Contract
17
17
 
18
- ### Route ARIA Through `a11y`
18
+ ### Own Accessibility per Part
19
19
 
20
- Do not add individual public props such as `ariaLabel`, `ariaDescribedBy`, or
21
- `role`. Use the platform `A11y` type and convert it at the semantic target.
20
+ Use the platform `A11y` type instead of individual public props such as
21
+ `ariaLabel`, `ariaDescribedBy`, or `role`. For each part:
22
+
23
+ - Prefer a native element.
24
+ - Keep roles, heading levels, keyboard and focus behavior, relationships, live
25
+ regions, and widget state in component code.
26
+ - Read `a11y.ariaLabel` only when a control has no visible name.
27
+
28
+ Every `a11y` field that reaches the DOM becomes an editor control. Read only the
29
+ field the part needs and write it as its HTML attribute,
30
+ `aria-label={a11y?.ariaLabel}`. Never spread the whole object.
22
31
 
23
32
  ```tsx
24
- import type { A11y, Direction } from '@wix/editor-react-types';
25
- import { convertA11yKeysToHtmlFormat } from '@wix/react-component-utils';
26
-
27
- export type TabsProps = {
28
- id: string;
29
- className?: string;
30
- direction?: Direction;
31
- a11y?: A11y;
33
+ import type { A11y } from '@wix/editor-react-types';
34
+
35
+ type ToggleProps = {
36
+ elementProps?: { toggle?: { className?: string; a11y?: A11y } };
32
37
  };
33
38
 
34
- <nav {...(a11y && convertA11yKeysToHtmlFormat(a11y))}>{tabs}</nav>;
39
+ function Toggle({ elementProps }: ToggleProps) {
40
+ const { a11y: toggleA11y, ...toggleProps } = elementProps?.toggle ?? {};
41
+
42
+ return (
43
+ <button {...toggleProps} aria-label={toggleA11y?.ariaLabel ?? ARIA_LABELS.toggle}>
44
+ <ChevronIcon aria-hidden="true" />
45
+ </button>
46
+ );
47
+ }
35
48
  ```
36
49
 
37
- Apply root accessibility to the elected root. If requirements assign
38
- accessibility to a named inner part, route it through that part's
39
- `elementProps.<name>.a11y` contract and convert it on the actual semantic
40
- element.
50
+ Keep the root's typed `a11y?: A11y` prop even when it reads no field. Destructure
51
+ `a11y` out of an `elementProps` entry before spreading the entry; a spread entry
52
+ records the nested object as a whole. Image alt text comes from the `Image`
53
+ type's `alt` field, not from `a11y`.
41
54
 
42
55
  ### Provide Accessible Names
43
56
 
@@ -53,6 +66,7 @@ Never hardcode an `aria-label` string directly in JSX.
53
66
  ```tsx
54
67
  // constants.ts
55
68
  export const ARIA_LABELS = {
69
+ toggle: 'Toggle details',
56
70
  playButton: 'Play animation',
57
71
  pauseButton: 'Pause animation',
58
72
  } as const;
@@ -80,36 +94,47 @@ including an icon plus visible text, usually do not need another ARIA label.
80
94
 
81
95
  ## Review Scope
82
96
 
83
- Run this review after creating or editing JSX.
97
+ Run this review once the JSX is complete and again after each fix pass, at
98
+ most two passes. Do not rerun after a clean result unless JSX changed.
84
99
 
85
- | Request | Scan and inspect |
100
+ | Request | Pass to the command |
86
101
  | --- | --- |
87
- | Specific file | That file and rendered wrappers or shared components it imports |
88
- | A component name or "this component" | All hand-edited files in its component folder plus relevant shared imports |
89
- | Full audit | Every component under `src/extensions/site/components/` plus relevant shared imports |
102
+ | Specific file | That file; its component folder is rendered |
103
+ | A component name or "this component" | The component folder |
104
+ | Full audit | `src/extensions/site/components/` |
90
105
 
91
- Exclude `*.generated.ts`; it is regenerated from JSX and CSS.
106
+ `*.generated.ts` is regenerated from JSX and CSS and is never scanned.
92
107
  Imported shared components are inspection context, not automatic edit scope.
93
108
  Report a confirmed shared-component issue instead of changing a broadly reused
94
109
  primitive unless the requested fix requires that shared change and its impact is
95
110
  understood.
96
111
 
97
- ## Automated Scanners
112
+ ## Automated Review
98
113
 
99
114
  `<SKILL_ROOT>` is the absolute directory containing the active `SKILL.md`. Run
100
- both commands from the consumer Wix package so dependencies resolve from that
101
- project. Pass `.tsx` or `.jsx` paths relative to the current directory.
115
+ from the consumer Wix package so dependencies resolve from that project.
102
116
 
103
117
  ```bash
104
- node <SKILL_ROOT>/scripts/scan-a11y-eslint.cjs <file1> [file2] ...
105
- node <SKILL_ROOT>/scripts/scan-a11y-code.cjs <file1> [file2] ...
118
+ node <SKILL_ROOT>/scripts/scan-a11y-review.cjs <component-dir | files...>
106
119
  ```
107
120
 
108
- Do not treat scanner startup failure as a clean result. The ESLint scanner
109
- reports JSX accessibility rules. The semantic scanner follows imports up to
110
- four levels and emits resolution evidence and confidence. Neither scanner
111
- covers every Editor React Component contract, so complete the manual review
112
- even when both return zero findings.
121
+ One command, one report. It runs the jsx-a11y ESLint rules, a semantic scanner
122
+ that follows imports and checks the per-part `a11y` contract, and a render
123
+ audit: the component is rendered with `defaultProps` in Node (an SSR check),
124
+ loaded into jsdom with its CSS Modules, and audited with axe-core.
125
+ `component.preview.tsx` must render without falling back to the placeholder.
126
+
127
+ The JSON report has `summary.line`, then `findings` grouped by rule with a
128
+ count, locations or DOM target, the scanner message, and the axe help link,
129
+ then `notChecked`. Exit `0` means every scanner ran and found nothing, `1`
130
+ means findings, `2` means the review is inconclusive; never treat `2` as clean.
131
+ Exit `2` with `render FAILED (missing-deps)` means `jsdom` or `axe-core` is not
132
+ installed: install them (SKILL.md step 2) and rerun. Exit `2` with
133
+ `render FAILED (loader)` means the audit could not load a module the component
134
+ imports; that is a scanner limit, not a component defect. Change the import
135
+ only if `tsc` also rejects it; otherwise stop and report the loader limit in the
136
+ final summary as a check that could not run. Color contrast, target size, and
137
+ keyboard behavior need a browser and remain manual.
113
138
 
114
139
  ## Finding Triage
115
140
 
@@ -154,39 +179,23 @@ evidence supports.
154
179
 
155
180
  ## Manual Review
156
181
 
157
- Verify all of the following after triaging scanner output.
158
-
159
- ### Semantic Targeting
160
-
161
- - `a11y` is typed and converted on the correct semantic element.
162
- - Wrappers and polymorphic components preserve their documented semantics.
163
- - Configurable heading or tag choices reach the rendered element.
164
- - Extension overrides preserve generated accessibility fields.
165
-
166
- ### Names and Visual Content
167
-
168
- - Icon-only controls have configurable or stable system-owned names.
169
- - Visually hidden text remains in the accessibility tree when needed.
170
- - Meaningful images and icons are named; decorative repetitions are hidden.
171
- - Accessibility strings are not hardcoded directly in JSX.
172
-
173
- ### Hidden Content and Focus
174
-
175
- - Hidden or collapsed state agrees across visuals, focusability, and the
176
- accessibility tree.
177
- - Invisible content cannot receive focus unless the interaction requires it.
178
- - Disabled and inert states behave consistently for keyboard and assistive
179
- technology users.
180
-
181
- ### Interaction and Structure
182
-
183
- - Interactive-looking elements use native semantics or complete role, focus,
184
- and keyboard behavior.
185
- - `onClick` on a non-interactive tag is checked, including conditional spreads.
186
- - Nested interactive children and existing focus management are inspected
187
- before semantics are added to a wrapper.
188
- - Lists, headings, landmarks, tabs, menus, dialogs, and breadcrumbs keep their
189
- intended structure.
182
+ In the default rendered state the command checks names, alt text, ARIA
183
+ validity, nesting, list and heading structure, hidden-but-focusable content,
184
+ the `a11y` contract, and SSR safety. Verify what it cannot see:
185
+
186
+ - Every meaningful non-default state (expanded, selected, playing, error,
187
+ empty, hover/focus) keeps correct names, focusability, hidden state, and
188
+ structure; the command audits only the default render.
189
+ - Wrappers and polymorphic components preserve their documented semantics;
190
+ extension overrides preserve generated accessibility fields.
191
+ - Accessible names describe the action, and visually hidden text that carries
192
+ meaning stays in the accessibility tree.
193
+ - State hidden through `--display` or transforms agrees with focusability and
194
+ the accessibility tree; disabled and inert states behave consistently.
195
+ - Custom widgets (tabs, menus, dialogs, sliders) implement their keyboard
196
+ pattern: arrow keys, Home/End, Escape, roving `tabIndex`.
197
+ - Interactive controls have a hit area of at least 24×24 CSS px and visible
198
+ focus.
190
199
  - The root implements the direction contract, and every `ReactNode` slot
191
200
  isolates nested content with `dir="ltr"`.
192
201
 
@@ -211,12 +220,13 @@ Prefer a native element when it preserves product behavior.
211
220
 
212
221
  The accessibility review is complete only when:
213
222
 
214
- - both scanners start successfully;
215
- - every finding is triaged;
216
- - confirmed issues are fixed when safe;
217
- - the manual review is complete; and
218
- - both scanners are rerun on every changed `.tsx` or `.jsx` file.
223
+ - the last run exited `0` or `1`; exit `2` is acceptable only for a reported
224
+ `loader` limit;
225
+ - every finding is triaged and confirmed issues are fixed when safe;
226
+ - the command was rerun after the last fix pass; and
227
+ - the manual review is complete.
219
228
 
229
+ After two fix passes, stop and report the remaining findings with their triage.
220
230
  Preserve visual and runtime behavior. Fix the semantic owner: root, named inner
221
231
  part, shared primitive, or call site. Then return to the main workflow for the
222
232
  Wix build, manifest generation, TypeScript check, and relevant project tests.
@@ -42,8 +42,9 @@ export type PlanCardProps = {
42
42
 
43
43
  Rules:
44
44
 
45
- - Route all ARIA attributes through `a11y`; do not add individual `ariaLabel`,
46
- `role`, or similar props.
45
+ - Follow `ACCESSIBILITY.md`. Expose only `ariaLabel`, for a control without a
46
+ visible name, through the typed `a11y` contract. Keep semantics and state in
47
+ code. Do not add one-off ARIA props or spread the whole object.
47
48
  - Expose only content and behavior that the site owner controls. Keep derived
48
49
  values internal.
49
50
  - Add only callbacks required by the component specification. Use supported SDK