# Audit: rating-group audit-version: 1 audited-at: 2026-06-26 scope: (SCOPE-DRIFT → SYS-1) method: adversarially-verified workflow (analyze → refute); HIGH lead-verified by direct read of the cited code. B5 ground-truth: the A31 O(N²) isSelected/isExpanded (.includes from a per-item $derived) is confirmed across listbox/grid-list/tree-view/tree-grid/tag-group (SYS-7); rovingTargetEl is correctly LIFTED everywhere (not A31); virtual-* use SvelteMap (A33-clean). provider: src/uix/soma/components/rating-group/rating-group-provider.svelte.ts reactivity (A31/A33/A35): CLEAN: items computed once via $derived (line 130-142); per-item state lookup via direct array index (line 350), not provider method call. No $state(Map/Set), no per-item effects reading global state. No A31/A33/A35 hazards detected." ## Summary Counts (post-verification): CRITICAL 0 · HIGH 0 · MEDIUM 1 · LOW 0. ## Findings ### MEDIUM: SYS-1 scope-drift — rating-group-001 - dimension: scope, contract - rule: SYS-1 scope-drift - location: src/uix/morfo/components/rating-group.ts:7 - evidence: Morfo declares scope: ['soma', 'sema'] but eidos recipe directory exists at src/uix/eidos/components/rating-group/ with full recipe tokens (base.ts:2018-2044) and eidos wrapper component - impact: Eidos layer is functionally present but not declared in scope; discovery tooling and consumers may miss that eidos layer exists or assume morfo scope is incomplete - repro: Inspect src/uix/morfo/components/rating-group.ts line 7 and confirm eidos directory + recipe tokens exist - proposed-fix: Update morfo scope from ['soma', 'sema'] to ['soma', 'sema', 'eidos'] - verify: [confirmed] Confirmed SYS-1 scope-drift. src/uix/morfo/components/rating-group.ts:7 declares `scope: ['soma', 'sema'],` while a full eidos layer exists: recipe block at src/uix/eidos/lib/recipes/base.ts:2018 (`'rating-group': { 'gap-xs': ... 'item-color-active': 'var(--color-fulfill-solid)' ... }`) plus eidos wrapper/css/types/README under src/uix/eidos/components/rating-group/ (rating-group.svelte, rating-group.css, types.ts, README.md). Direct peers that ALSO have eidos recipes DO declare it: radio-group.ts:7, checkbox.ts:7, toggle-group.ts:10 all read `scope: ['soma', 'sema', 'eidos']`. So 'eidos' is the project's convention when an eidos recipe is present, and rating-group omits it. MEDIUM per SYS-1 baseline. (Note: a broader population of soma-rooted components — calendar, combobox, command — also omit 'eidos' despite having eidos css; this is a wider systemic pattern, but rating-group's drift is real and matches the SYS-1 rule against its rating-control peers.) Proposed fix: change to `scope: ['soma', 'sema', 'eidos']`. - fix-status: open ## No-findings dimensions contract, parts_registered, aria_data_declared_vs_emitted, events_inert, field_merge, reactivity_A31, reactivity_A33, reactivity_A35, reactivity_A30, reactivity_A6, dom_selector_escape, direct_global_access, morfo_as_const, soma_imports_eidos, double_write_divergence, require_topology, theming_roles, theming_literals_magic, theming_z_index, theming_opacity, theming_spacing, theming_sizing ## Theming facts (E-bis) - magic z-index: none - magic literals: none - undeclared parts: none - roles clean: true · variants clean: true ## Tests (F) - exists: true · env: jsdom - covers: slider_attr_projection; field_flag_merging; item_states; hover_preview; pointer_click_commit; clearable_click; keyboard_nav; rtl_arrows; readonly_disabled_guards - untested: pointer_touch_isolation; clearable_disabled_edge_case; large_max_regression; value_change_callback_ordering ## Style observations (non-blocking) - CSS uses exclusively role aliases (color-fulfill-solid, color-neutral-border, color-surface-default, etc.) and canonical tokens (--space-*, --font-size-*, --radius-*). Opacity via --rating-group-disabled-opacity (line 52), not raw decimal. Transitions use --duration-fast/--ease-default. Gap/item-size responsive via eidos size prop. No magic z-index, no bare hex colors, no opacity literals. Sizing: item-size in px literal (14-34px) tied to size variants; font-size via --font-size-* refs. Naming conventions correct: --rating-group-{gap,item-size,font-size,item-color}-*.