lashy0 on GitHub

lashy0/web-template

Reviewed against Rams quality heuristics: accessibility, color, typography, spacing, components, motion, UX, and craft.

30 files reviewed·September 11, 2026

View on GitHub

Low

Design risk in this codebase.

4issues
Serious & Moderate · top 2 shown below

Top fix

Add a confirmation dialog before firing the logout action.

See the fix

Verdict

Strong visual foundations are undermined by two interaction shortcuts that trade safety for simplicity. The unguarded logout is the real risk: one misclick and the session is gone with no recovery path.

Files Rams reviewed

apps/frontend/src/components/Account/AccountMenu.tsx

apps/frontend/src/components/Account/AccountSummary.tsx

apps/frontend/src/components/Admin/AdminNavigation.tsx

apps/frontend/src/components/Admin/AdminSidebar.tsx

apps/frontend/src/components/Admin/AdminUserMenu.tsx

apps/frontend/src/components/Auth/LoginForm.tsx

apps/frontend/src/components/Common/AuditChanges.tsx

apps/frontend/src/components/Common/AuditFilter.tsx

apps/frontend/src/components/Common/DataTable/DataTable.tsx

apps/frontend/src/components/Common/DataTable/DataTablePagination.tsx

apps/frontend/src/components/Defects/Audit/ChangesAudit.tsx

apps/frontend/src/components/Defects/Audit/PendingAudit.tsx

apps/frontend/src/components/Defects/Audit/columns.tsx

apps/frontend/src/components/Defects/Groups/AddDefectGroup.tsx

apps/frontend/src/components/Defects/Groups/ArchiveStatusDefectGroup.tsx

apps/frontend/src/components/Defects/Groups/DefectGroupActionsMenu.tsx

apps/frontend/src/components/Defects/Groups/DefectGroupFilters.tsx

apps/frontend/src/components/Defects/Groups/DeleteDefectGroup.tsx

apps/frontend/src/components/Defects/Groups/EditDefectGroup.tsx

apps/frontend/src/components/Defects/Groups/PendingDefectGroups.tsx

apps/frontend/src/components/Defects/Groups/columns.tsx

apps/frontend/src/components/Defects/Types/AddDefectType.tsx

apps/frontend/src/components/Defects/Types/ArchiveStatusDefectType.tsx

apps/frontend/src/components/Defects/Types/DefectGroupSelect.tsx

apps/frontend/src/components/Defects/Types/DefectTypeActionsMenu.tsx

apps/frontend/src/components/Defects/Types/DefectTypeFilters.tsx

apps/frontend/src/components/Defects/Types/DeleteDefectType.tsx

apps/frontend/src/components/Defects/Types/EditDefectType.tsx

apps/frontend/src/components/Defects/Types/PendingDefectTypes.tsx

apps/frontend/src/components/Defects/Types/ViewDefectType.tsx

98/100

Accessibility

1 serious
AccessibilitySerious

apps/frontend/src/components/Auth/LoginForm.tsx:100

Password toggle changes aria-label AND aria-pressed together, announcing redundant state

In `LoginForm.tsx` lines 99-101, `InputGroupButton` sets `aria-label={isPasswordVisible ? 'Скрыть пароль' : 'Показать пароль'}` while also toggling `aria-pressed`. Screen readers announce both the new label and the pressed state, so users hear "Скрыть пароль, pressed": the label already carries the state, making `aria-pressed` noise.

Why it matters

Doubling state communication through label changes and aria-pressed forces screen-reader users to parse redundant announcements on every toggle.

Fix

Use a stable aria-label with aria-pressed for state, or a changing label without aria-pressed: never both simultaneously.

<InputGroupButton
  aria-label={isPasswordVisible ? 'Скрыть пароль' : 'Показать пароль'}
  aria-pressed={isPasswordVisible}
  ...>
<InputGroupButton
  aria-label="Показать пароль"
  aria-pressed={isPasswordVisible}
  ...>
98/100

UX

1 serious
UXSerious

apps/frontend/src/components/Account/AccountMenu.tsx:57

Logout fires instantly with no confirmation, one misclick ends the session

In `AccountMenu.tsx` lines 38-41, `handleLogout` calls `logout()` immediately on click. The item is styled `variant="destructive"` signaling intent, but there is no confirm step. A user who clips the item while navigating the menu loses their session with no recovery.

Why it matters

Irreversible actions without confirmation increase accidental session termination, especially on touch targets in compact menus.

Fix

Require a confirmation step before executing any irreversible destructive action.

<DropdownMenuItem variant="destructive" onClick={handleLogout}>
  <LogOutIcon />
  Выйти
</DropdownMenuItem>
// Replace direct logout with a confirmation dialog trigger:
<DropdownMenuItem variant="destructive" onClick={() => setLogoutConfirmOpen(true)}>
  <LogOutIcon aria-hidden="true" />
  Выйти
</DropdownMenuItem>
<LogoutConfirmDialog open={logoutConfirmOpen} onConfirm={handleLogout} onCancel={() => setLogoutConfirmOpen(false)} />

Typography

No issues found

Color

No issues found

Spacing

No issues found

Components

No issues found

Motion

No issues found

Craft

No issues found

Working well

  • The collapsed-desktop path uses aria-label on the SidebarMenuButton and a sr-only span as a belt-and-suspenders pattern: the accessible name is declared at the control level where it belongs, not buried in a child element that a composite widget might not surface.
  • Computing sidebarLabel from sidebar state and passing it as aria-label to SidebarTrigger is the correct pattern: the accessible name reflects the current action rather than the static widget name, so VoiceOver and NVDA announce exactly what the button will do.
  • The min-w-0 on both the outer flex container and the inner text div is exactly right: without it, truncate silently does nothing inside a flex parent, and long names blow the layout open. Getting both levels is the detail most implementations miss.
  • The side placement logic ('right' when collapsed, 'top' otherwise) is a clean context-aware decision that prevents the menu from overlapping a collapsed sidebar rail: most implementations hardcode one side and break the other state.

Scored September 11, 2026 with Rams Engine v0.0.4 · Engine changelog

This page is an automated design review of lashy0/web-template’s UI code: 30 files read against 313 versioned rules covering accessibility, color, typography, spacing, components, UX, motion, and craft. The score is out of 100; confirmed criticals cap it — one at 59, two at 49, three or more at 39.

More design scores

Score your own repo.

Free on public repos, no account. The same engine that scored this page reads your UI code and mints a score page like this one.

Public repos only. The full engine reviews the UI code and mints a public score page — we email you the link too. Already-scored repos open instantly.

Or get a design review on every pull requestInstall Rams