Compare commits
2 Commits
b9f4ccd71d
...
449b428cea
| Author | SHA1 | Date | |
|---|---|---|---|
| 449b428cea | |||
| c5f8f6fcbc |
@ -0,0 +1,229 @@
|
|||||||
|
# Technical Design Spec: Auth-Yes Mobile-First & Modern Minimalist UI Revamp
|
||||||
|
|
||||||
|
**Date:** 2026-08-24\
|
||||||
|
**Author:** Tyler Gillispie & Antigravity\
|
||||||
|
**Status:** Approved by User\
|
||||||
|
**Scope:** Frontend UI & SSR Layouts (`ui/`)
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 1. Executive Summary & Objectives
|
||||||
|
|
||||||
|
Auth-Yes provides an ultra-low-friction IAM and WebAuthn Passkey authority. The
|
||||||
|
goal of this technical revamp is to modernize the user interface with a
|
||||||
|
**mobile-first, modern minimalist design** that feels native and thumb-friendly
|
||||||
|
on smartphones while remaining clean, responsive, and spacious on desktop
|
||||||
|
browsers.
|
||||||
|
|
||||||
|
### Key Objectives:
|
||||||
|
|
||||||
|
1. **Ergonomic Mobile Navigation**: Implement a fixed, thumb-accessible bottom
|
||||||
|
navigation bar on mobile (`< 768px`) with `env(safe-area-inset-bottom)`
|
||||||
|
support.
|
||||||
|
2. **Instant Biometric Login**: Transform the login experience to prioritize
|
||||||
|
one-tap passkey biometric authentication with WebAuthn conditional UI
|
||||||
|
autofill, moving USB/username clutter behind progressive disclosure.
|
||||||
|
3. **Adaptive Card Decks**: Eliminate rigid desktop-style tables on mobile
|
||||||
|
devices for Sessions, Passkeys, and Admin screens in favor of responsive,
|
||||||
|
touch-friendly card lists.
|
||||||
|
4. **Zero-Dependency Purity**: Maintain 100% pure Hono SSR JSX and vanilla CSS
|
||||||
|
with zero client-side framework runtime bloat.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 2. Visual Design System & Theme Foundation
|
||||||
|
|
||||||
|
### 2.1 CSS Custom Properties (Design Tokens)
|
||||||
|
|
||||||
|
The stylesheet will be embedded globally via the root layouts using standard CSS
|
||||||
|
custom properties:
|
||||||
|
|
||||||
|
```css
|
||||||
|
:root {
|
||||||
|
/* Brand & Accents */
|
||||||
|
--primary: #0066cc;
|
||||||
|
--primary-hover: #0052a3;
|
||||||
|
--primary-light: #e6f0fa;
|
||||||
|
--primary-ring: rgba(0, 102, 204, 0.25);
|
||||||
|
|
||||||
|
/* Neutrals & Surfaces */
|
||||||
|
--surface-canvas: #f8fafc;
|
||||||
|
--surface-card: #ffffff;
|
||||||
|
--surface-muted: #f1f5f9;
|
||||||
|
--border-subtle: #e2e8f0;
|
||||||
|
--border-strong: #cbd5e1;
|
||||||
|
|
||||||
|
/* Typography */
|
||||||
|
--text-primary: #0f172a;
|
||||||
|
--text-secondary: #475569;
|
||||||
|
--text-muted: #94a3b8;
|
||||||
|
|
||||||
|
/* Semantic Feedback */
|
||||||
|
--success: #10b981;
|
||||||
|
--success-bg: #ecfdf5;
|
||||||
|
--success-border: #a7f3d0;
|
||||||
|
--warning: #f59e0b;
|
||||||
|
--warning-bg: #fffbeb;
|
||||||
|
--warning-border: #fde68a;
|
||||||
|
--danger: #ef4444;
|
||||||
|
--danger-bg: #fef2f2;
|
||||||
|
--danger-border: #fecaca;
|
||||||
|
|
||||||
|
/* Spacing & Geometry */
|
||||||
|
--radius-sm: 6px;
|
||||||
|
--radius-md: 10px;
|
||||||
|
--radius-lg: 16px;
|
||||||
|
--radius-full: 9999px;
|
||||||
|
--touch-target-min: 48px;
|
||||||
|
--shadow-sm: 0 1px 2px 0 rgb(0 0 0 / 0.05);
|
||||||
|
--shadow-md: 0 4px 6px -1px rgb(0 0 0 / 0.1), 0 2px 4px -2px rgb(0 0 0 / 0.1);
|
||||||
|
--shadow-lg: 0 10px 15px -3px rgb(0 0 0 / 0.1), 0 4px 6px -4px rgb(0 0 0 / 0.1);
|
||||||
|
}
|
||||||
|
|
||||||
|
@media (prefers-color-scheme: dark) {
|
||||||
|
:root {
|
||||||
|
--surface-canvas: #0b0f19;
|
||||||
|
--surface-card: #111827;
|
||||||
|
--surface-muted: #1e293b;
|
||||||
|
--border-subtle: #1f2937;
|
||||||
|
--border-strong: #374151;
|
||||||
|
|
||||||
|
--text-primary: #f8fafc;
|
||||||
|
--text-secondary: #cbd5e1;
|
||||||
|
--text-muted: #64748b;
|
||||||
|
|
||||||
|
--primary-light: #172554;
|
||||||
|
--success-bg: #064e3b;
|
||||||
|
--success-border: #065f46;
|
||||||
|
--warning-bg: #451a03;
|
||||||
|
--warning-border: #78350f;
|
||||||
|
--danger-bg: #450a0a;
|
||||||
|
--danger-border: #7f1d1d;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 3. Shell Architecture & Navigation
|
||||||
|
|
||||||
|
### 3.1 Adaptive Layout Structure
|
||||||
|
|
||||||
|
```
|
||||||
|
+-------------------------------------------------------------+
|
||||||
|
| MOBILE VIEW (< 768px) |
|
||||||
|
+-------------------------------------------------------------+
|
||||||
|
| [⚡ Auth-Yes] Launchpad [tylerg] [🚪Logout] | <-- Compact Top Bar
|
||||||
|
+-------------------------------------------------------------+
|
||||||
|
| |
|
||||||
|
| (Main Content Area - Adaptive Cards & Tiles) |
|
||||||
|
| |
|
||||||
|
+-------------------------------------------------------------+
|
||||||
|
| [ 🚀 Launchpad ] [ 📱 Sessions ] [ 🔑 Passkeys ] [ 🛡️ Admin ] | <-- Fixed Bottom Nav
|
||||||
|
+-------------------------------------------------------------+
|
||||||
|
```
|
||||||
|
|
||||||
|
```
|
||||||
|
+-------------------------------------------------------------+
|
||||||
|
| DESKTOP VIEW (≥ 768px) |
|
||||||
|
+-------------------------------------------------------------+
|
||||||
|
| [⚡ Auth-Yes] Launchpad Sessions Passkeys [Admin] [Logout] | <-- Sticky Top Bar
|
||||||
|
+-------------------------------------------------------------+
|
||||||
|
| |
|
||||||
|
| (Main Content Area - Wide Container & Tables) |
|
||||||
|
| |
|
||||||
|
+-------------------------------------------------------------+
|
||||||
|
```
|
||||||
|
|
||||||
|
### 3.2 Navigation Components
|
||||||
|
|
||||||
|
1. **`ui/components/AuthenticatedLayout.tsx`**:
|
||||||
|
- On screens `< 768px`: Renders a fixed bottom navigation bar with 4 primary
|
||||||
|
targets:
|
||||||
|
- **Launchpad**: `/dashboard`
|
||||||
|
- **Sessions**: `/dashboard/sessions`
|
||||||
|
- **Passkeys**: `/dashboard/passkeys`
|
||||||
|
- **Admin Console**: `/admin/users` (visible when `isAdmin === true`)
|
||||||
|
- Bottom padding on `<main>` container dynamically set to
|
||||||
|
`calc(4rem + env(safe-area-inset-bottom))` to prevent content overlap.
|
||||||
|
- On screens `≥ 768px`: Hides the bottom navigation bar and renders the top
|
||||||
|
horizontal navigation pill strip.
|
||||||
|
|
||||||
|
2. **`ui/components/AdminLayout.tsx`**:
|
||||||
|
- Sub-navigation across Admin modules (_Users_, _Invites_, _Apps_, _Roles_,
|
||||||
|
_Audit Logs_, _AAGUIDs_) rendered as a horizontal scrollable pill bar on
|
||||||
|
mobile and clean tab bar on desktop.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 4. Authentication Flow & Ergonomics
|
||||||
|
|
||||||
|
### 4.1 Login Screen (`ui/components/LoginPage.tsx`)
|
||||||
|
|
||||||
|
- **Primary Hero**: Large 52px button: **"Sign In with Passkey"** with biometric
|
||||||
|
fingerprint glyph.
|
||||||
|
- **Conditional UI / Autofill**: Script initializes
|
||||||
|
`SimpleWebAuthnBrowser.startAuthentication({ ... }, true)` with
|
||||||
|
`mediation: 'conditional'` if supported by browser.
|
||||||
|
- **Progressive Disclosure**: USB instructions and optional username input
|
||||||
|
collapsed behind an expandable trigger: _"Need to specify a username or use
|
||||||
|
account recovery?"_.
|
||||||
|
- **Live State**: Smooth spinner and subtle pulsing aura while authenticator
|
||||||
|
prompt is active.
|
||||||
|
|
||||||
|
### 4.2 Registration Screen (`ui/components/RegisterPage.tsx`)
|
||||||
|
|
||||||
|
- Clean 2-step onboarding card for invite-code validation + 1-tap passkey
|
||||||
|
enrollment.
|
||||||
|
- 12-word recovery phrase presented with single-tap "Copy Seed Phrase" button.
|
||||||
|
|
||||||
|
### 4.3 Recovery Screen (`ui/components/RecoveryPage.tsx`)
|
||||||
|
|
||||||
|
- Mobile-friendly 12-box input matrix supporting paste-all and auto-focus
|
||||||
|
advance.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 5. Adaptive Data Views
|
||||||
|
|
||||||
|
### 5.1 Application Launchpad (`ui/components/AppLaunchpadPage.tsx`)
|
||||||
|
|
||||||
|
- Responsive grid (1 column on mobile, minmax(320px, 1fr) on desktop).
|
||||||
|
- Card elements: App Name, Domain link, Role Badge (`Admin` / `Member` /
|
||||||
|
`Viewer`), description, and prominent 48px **"Launch App ↗"** button.
|
||||||
|
|
||||||
|
### 5.2 Sessions Management (`ui/components/SessionsPage.tsx`)
|
||||||
|
|
||||||
|
- **Mobile Cards**: Replaces rigid table with session cards showing:
|
||||||
|
- Device type icon (📱 Phone / 💻 Laptop).
|
||||||
|
- Emerald **"Current Device"** pill.
|
||||||
|
- IP Address and formatted date.
|
||||||
|
- Dedicated **"Revoke Session"** button.
|
||||||
|
- Top Action: **"Revoke All Other Sessions"** danger button.
|
||||||
|
|
||||||
|
### 5.3 Passkeys Management (`ui/components/PasskeysPage.tsx`)
|
||||||
|
|
||||||
|
- **Mobile Cards**: Replaces rigid table with passkey cards showing:
|
||||||
|
- Authenticator vendor brand chip (Google Password Manager, Apple Keychain,
|
||||||
|
YubiKey).
|
||||||
|
- Nickname and Credential ID preview.
|
||||||
|
- Creation and last-used dates.
|
||||||
|
- 1-tap "Add New Passkey" hero action button.
|
||||||
|
- Revoke / Delete action.
|
||||||
|
|
||||||
|
### 5.4 Admin Screens (`ui/components/Admin*.tsx`)
|
||||||
|
|
||||||
|
- Responsive cards for Users, Apps, Invites, and Audit Logs on mobile with
|
||||||
|
search filters and expandable details.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 6. Implementation & Quality Gates
|
||||||
|
|
||||||
|
1. **Pure SSR JSX**: All changes strictly implemented in Hono SSR JSX without
|
||||||
|
React runtime.
|
||||||
|
2. **Quality Gates**:
|
||||||
|
- `deno fmt`
|
||||||
|
- `deno task lint`
|
||||||
|
- `deno task check`
|
||||||
|
- `deno task test`
|
||||||
@ -0,0 +1,78 @@
|
|||||||
|
# TASK METADATA
|
||||||
|
|
||||||
|
- **Target Files:** `ui/components/Layout.tsx`,
|
||||||
|
`ui/components/AuthenticatedLayout.tsx`, `ui/components/AdminLayout.tsx`
|
||||||
|
- **Core Objective:** Implement a unified CSS custom property design token
|
||||||
|
layer, dark/light theme adaptation, and dual-mode responsive layout shell
|
||||||
|
(fixed mobile bottom navigation + desktop sticky header).
|
||||||
|
- **Dependencies:**
|
||||||
|
`docs/superpowers/specs/2026-08-24-mobile-first-ui-revamp-design.md`
|
||||||
|
- **Additional Important Notes:** Must remain 100% pure Hono SSR JSX (zero React
|
||||||
|
runtime dependencies) and support mobile safe-area insets
|
||||||
|
(`env(safe-area-inset-bottom)`).
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 1. TASK METADATA
|
||||||
|
|
||||||
|
The header block specifies the target layout templates, core objective,
|
||||||
|
dependencies, and constraints.
|
||||||
|
|
||||||
|
## 2. Architectural Considerations & Risks
|
||||||
|
|
||||||
|
### Risks
|
||||||
|
|
||||||
|
- **Content Clipping Behind Fixed Bottom Navigation:** If the bottom navigation
|
||||||
|
bar is fixed to the bottom of the viewport on mobile without sufficient
|
||||||
|
padding on the `<main>` container, page content (such as action buttons or
|
||||||
|
footer links) could be obscured.
|
||||||
|
- _Mitigation:_ Explicitly set
|
||||||
|
`padding-bottom: calc(4.5rem + env(safe-area-inset-bottom))` on the main
|
||||||
|
layout container.
|
||||||
|
- **Flash of Unstyled Content / Layout Shift:** Inlining the design system
|
||||||
|
tokens into SSR JSX `<style>` tags ensures zero-latency stylesheet loading and
|
||||||
|
eliminates FOUC on mobile connections.
|
||||||
|
- **Theme Inconsistency:** Hardcoded colors across sub-components can cause
|
||||||
|
visual defects when switching between light and dark modes.
|
||||||
|
- _Mitigation:_ Standardize all colors to CSS custom properties
|
||||||
|
(`var(--surface-canvas)`, `var(--text-primary)`, `var(--border-subtle)`,
|
||||||
|
etc.).
|
||||||
|
|
||||||
|
### Alternatives
|
||||||
|
|
||||||
|
- **External CSS Bundle vs Inline SSR Style Block:** Using an external
|
||||||
|
stylesheet requires extra HTTP roundtrips and cache-busting logic. Embedding
|
||||||
|
the design tokens directly in the root layout preserves the zero-dependency,
|
||||||
|
ultra-low-latency SSR architecture of Auth-Yes.
|
||||||
|
|
||||||
|
## 3. Proposed Implementation
|
||||||
|
|
||||||
|
### Phase 1: Global CSS Design Tokens & Base Theme
|
||||||
|
|
||||||
|
1. Define `:root` and `@media (prefers-color-scheme: dark)` CSS custom
|
||||||
|
properties in `ui/components/Layout.tsx` and
|
||||||
|
`ui/components/AuthenticatedLayout.tsx`.
|
||||||
|
2. Include color tokens (`--primary`, `--surface-canvas`, `--surface-card`,
|
||||||
|
`--border-subtle`, `--text-primary`), elevation shadows (`--shadow-sm`,
|
||||||
|
`--shadow-md`), and touch geometries (`--touch-target-min: 48px`,
|
||||||
|
`--radius-md: 10px`).
|
||||||
|
|
||||||
|
### Phase 2: Dual-Mode Navigation Shell
|
||||||
|
|
||||||
|
1. In `ui/components/AuthenticatedLayout.tsx`:
|
||||||
|
- On screens `< 768px`: Render fixed bottom navigation bar containing 4
|
||||||
|
primary destinations (Launchpad, Sessions, Passkeys, and conditionally
|
||||||
|
Admin Console).
|
||||||
|
- Render compact top app bar with Auth-Yes glyph, current screen title, and
|
||||||
|
quick logout button.
|
||||||
|
- On screens `≥ 768px`: Hide bottom navigation and render full desktop sticky
|
||||||
|
header with active pill tabs.
|
||||||
|
2. In `ui/components/AdminLayout.tsx`:
|
||||||
|
- Implement horizontal scrolling segmented pill sub-navigation for mobile
|
||||||
|
admin tools (_Users_, _Invites_, _Apps_, _Roles_, _Audit Logs_).
|
||||||
|
|
||||||
|
### Phase 3: Verification & Quality Gates
|
||||||
|
|
||||||
|
1. Run `deno fmt ui/**/*.tsx`.
|
||||||
|
2. Run `deno task lint` and `deno task check`.
|
||||||
|
3. Run `deno task test` to ensure zero SSR regressions.
|
||||||
@ -0,0 +1,81 @@
|
|||||||
|
# TASK METADATA
|
||||||
|
|
||||||
|
- **Target Files:** `ui/components/LoginPage.tsx`,
|
||||||
|
`ui/components/RegisterPage.tsx`, `ui/components/RecoveryPage.tsx`,
|
||||||
|
`ui/public/auth-client.js`
|
||||||
|
- **Core Objective:** Modernize the login, registration, and recovery screens
|
||||||
|
with one-tap hero passkey trigger, WebAuthn autofill / conditional mediation,
|
||||||
|
and progressive disclosure for fallback options.
|
||||||
|
- **Dependencies:**
|
||||||
|
`tasks/new/2026-0824.04.gem.feat.ui-shell.design-tokens-and-adaptive-nav-2215.md`
|
||||||
|
- **Additional Important Notes:** Must support seamless WebAuthn conditional
|
||||||
|
mediation (`startAuthentication(..., true)`) while gracefully handling devices
|
||||||
|
that do not support autofill.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 1. TASK METADATA
|
||||||
|
|
||||||
|
The header block specifies the authentication templates, client-side WebAuthn
|
||||||
|
handler, core objective, dependencies, and constraints.
|
||||||
|
|
||||||
|
## 2. Architectural Considerations & Risks
|
||||||
|
|
||||||
|
### Risks
|
||||||
|
|
||||||
|
- **Autofill Abort Collisions:** If conditional mediation
|
||||||
|
(`mediation: 'conditional'`) is running in the background and the user
|
||||||
|
explicitly taps "Sign In with Passkey", some browsers can throw an
|
||||||
|
`AbortError` if not handled correctly.
|
||||||
|
- _Mitigation:_ Cancel or ignore active conditional mediation promises before
|
||||||
|
starting explicit user-gesture WebAuthn authentication.
|
||||||
|
- **Missing Recovery Seed Visibility:** If the 12-word BIP39 seed phrase during
|
||||||
|
registration is obscured or difficult to copy on mobile, users could lose
|
||||||
|
account recovery capability.
|
||||||
|
- _Mitigation:_ Provide a clear, high-contrast 12-word grid with a prominent
|
||||||
|
1-tap "Copy All Words" clipboard button.
|
||||||
|
|
||||||
|
### Alternatives
|
||||||
|
|
||||||
|
- **Static Username Input vs Progressive Disclosure:** Showing a prominent
|
||||||
|
username input confuses 95%+ of mobile passkey users whose credentials are
|
||||||
|
discoverable resident keys. Collapsing the username field into an expandable
|
||||||
|
drawer retains full backward compatibility for non-resident keys while
|
||||||
|
providing a clean 1-tap experience for passkeys.
|
||||||
|
|
||||||
|
## 3. Proposed Implementation
|
||||||
|
|
||||||
|
### Phase 1: Hero Passkey Login Screen
|
||||||
|
|
||||||
|
1. Refactor `ui/components/LoginPage.tsx`:
|
||||||
|
- Add a 52px biometric hero button: "Sign In with Passkey" with fingerprint
|
||||||
|
SVG icon and subtle focus/press feedback.
|
||||||
|
- Collapse optional username field and USB instructions behind an accessible
|
||||||
|
`<details>` / toggle trigger.
|
||||||
|
- Add pulse/spinner state when authenticator is active.
|
||||||
|
|
||||||
|
### Phase 2: WebAuthn Client Conditional UI
|
||||||
|
|
||||||
|
1. Update `ui/public/auth-client.js`:
|
||||||
|
- Check `PublicKeyCredential.isConditionalMediationAvailable()` on page load.
|
||||||
|
- If available, trigger
|
||||||
|
`SimpleWebAuthnBrowser.startAuthentication(options, true)` in conditional
|
||||||
|
mode.
|
||||||
|
- On explicit button click, execute modal WebAuthn login.
|
||||||
|
|
||||||
|
### Phase 3: Registration & Recovery Mobile Polish
|
||||||
|
|
||||||
|
1. In `ui/components/RegisterPage.tsx`:
|
||||||
|
- Streamline invite code and username entry into high-contrast inputs.
|
||||||
|
- Format 12-word seed phrase in a 2-column mobile card grid with a 1-tap copy
|
||||||
|
button.
|
||||||
|
2. In `ui/components/RecoveryPage.tsx`:
|
||||||
|
- Support auto-advance input matrix and paste-all text box for seed phrase
|
||||||
|
verification.
|
||||||
|
|
||||||
|
### Phase 4: Verification & Quality Gates
|
||||||
|
|
||||||
|
1. Run `deno fmt ui/**/*.tsx ui/public/**/*.js`.
|
||||||
|
2. Run `deno task lint` and `deno task check`.
|
||||||
|
3. Run `deno task test` to verify zero regression in authentication endpoints
|
||||||
|
and redirects.
|
||||||
@ -0,0 +1,77 @@
|
|||||||
|
# TASK METADATA
|
||||||
|
|
||||||
|
- **Target Files:** `ui/components/AppLaunchpadPage.tsx`,
|
||||||
|
`ui/components/SessionsPage.tsx`, `ui/components/PasskeysPage.tsx`
|
||||||
|
- **Core Objective:** Convert Launchpad, Sessions, and Passkeys views from rigid
|
||||||
|
desktop tables into responsive, touch-friendly card decks with device icons,
|
||||||
|
AAGUID brand chips, and 1-tap revocation actions.
|
||||||
|
- **Dependencies:**
|
||||||
|
`tasks/new/2026-0824.04.gem.feat.ui-shell.design-tokens-and-adaptive-nav-2215.md`
|
||||||
|
- **Additional Important Notes:** Must ensure single-tap revocation and
|
||||||
|
add-passkey actions work flawlessly on mobile touchscreens without accidental
|
||||||
|
mis-clicks.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 1. TASK METADATA
|
||||||
|
|
||||||
|
The header block specifies target user hub templates, core objective,
|
||||||
|
dependencies, and constraints.
|
||||||
|
|
||||||
|
## 2. Architectural Considerations & Risks
|
||||||
|
|
||||||
|
### Risks
|
||||||
|
|
||||||
|
- **Accidental Session Revocation:** Touchscreens have a higher risk of
|
||||||
|
accidental taps on destructive actions (e.g. revoking the active session).
|
||||||
|
- _Mitigation:_ Highlight the "Current Device" with an emerald badge to
|
||||||
|
distinguish it from remote sessions, and provide confirmation feedback on
|
||||||
|
single-tap revocation.
|
||||||
|
- **Information Density vs Screen Space:** Displaying raw UUIDs, AAGUIDs, and
|
||||||
|
long User-Agent strings clutters mobile viewports.
|
||||||
|
- _Mitigation:_ Truncate IDs to 8 characters with a 1-tap copy action, and
|
||||||
|
display friendly device labels (📱 Phone, 💻 Laptop) and known AAGUID vendor
|
||||||
|
names (Google Password Manager, Apple Keychain, YubiKey).
|
||||||
|
|
||||||
|
### Alternatives
|
||||||
|
|
||||||
|
- **Responsive Table Overflow vs Card Decks:** Horizontal scrolling tables on
|
||||||
|
mobile force uncomfortable two-axis panning. Adaptive card stacks provide a
|
||||||
|
native, scannable layout on narrow screens while maintaining full metadata
|
||||||
|
clarity.
|
||||||
|
|
||||||
|
## 3. Proposed Implementation
|
||||||
|
|
||||||
|
### Phase 1: Application Launchpad Card Grid
|
||||||
|
|
||||||
|
1. In `ui/components/AppLaunchpadPage.tsx`:
|
||||||
|
- Structure app items into modern elevated cards with app logo/glyph,
|
||||||
|
application name, domain link, and role badge (`Admin` / `Member` /
|
||||||
|
`Viewer`).
|
||||||
|
- Add full-width 48px "Launch App ↗" button on mobile, switching to fluid
|
||||||
|
grid tiles on desktop.
|
||||||
|
|
||||||
|
### Phase 2: Adaptive Sessions Cards
|
||||||
|
|
||||||
|
1. In `ui/components/SessionsPage.tsx`:
|
||||||
|
- Replace table rows on mobile with structured cards:
|
||||||
|
- Device type icon and IP badge.
|
||||||
|
- "Current Device" badge for active session.
|
||||||
|
- Formatted relative timestamp ("Active now", "Created 2 hours ago").
|
||||||
|
- Single-tap "Revoke Session" button.
|
||||||
|
- Prominent top action: "Revoke All Other Sessions".
|
||||||
|
|
||||||
|
### Phase 3: Adaptive Passkeys Manager
|
||||||
|
|
||||||
|
1. In `ui/components/PasskeysPage.tsx`:
|
||||||
|
- Render passkey cards with authenticator vendor badge (via AAGUID lookup).
|
||||||
|
- Display passkey nickname, truncated credential ID, and creation date.
|
||||||
|
- Large "Add Another Passkey" hero action button for easy multi-device
|
||||||
|
enrollment.
|
||||||
|
- Single-tap "Remove Passkey" button with confirmation.
|
||||||
|
|
||||||
|
### Phase 4: Verification & Quality Gates
|
||||||
|
|
||||||
|
1. Run `deno fmt ui/**/*.tsx`.
|
||||||
|
2. Run `deno task lint` and `deno task check`.
|
||||||
|
3. Run `deno task test` to ensure all dashboard rendering tests pass.
|
||||||
@ -0,0 +1,75 @@
|
|||||||
|
# TASK METADATA
|
||||||
|
|
||||||
|
- **Target Files:** `ui/components/AdminUsersPage.tsx`,
|
||||||
|
`ui/components/AdminUserDetailsPage.tsx`, `ui/components/AdminAppsPage.tsx`,
|
||||||
|
`ui/components/AdminInvitesPage.tsx`, `ui/components/AdminRolesPage.tsx`,
|
||||||
|
`ui/components/AuditLogPage.tsx`
|
||||||
|
- **Core Objective:** Adapt admin management screens (Users, Invites, Apps,
|
||||||
|
Roles, Audit Logs) into responsive mobile card lists with horizontal
|
||||||
|
sub-navigation and quick search filters.
|
||||||
|
- **Dependencies:**
|
||||||
|
`tasks/new/2026-0824.04.gem.feat.ui-shell.design-tokens-and-adaptive-nav-2215.md`
|
||||||
|
- **Additional Important Notes:** Must preserve high-density table views on wide
|
||||||
|
screens while providing seamless mobile card layouts for system administrators
|
||||||
|
on mobile devices.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 1. TASK METADATA
|
||||||
|
|
||||||
|
The header block specifies target admin templates, core objective, dependencies,
|
||||||
|
and constraints.
|
||||||
|
|
||||||
|
## 2. Architectural Considerations & Risks
|
||||||
|
|
||||||
|
### Risks
|
||||||
|
|
||||||
|
- **Audit Log Volume on Mobile:** Large audit log event streams can degrade
|
||||||
|
mobile rendering performance if loaded all at once.
|
||||||
|
- _Mitigation:_ Implement pagination / limit query rendering to recent events
|
||||||
|
with an expandable JSON detail drawer for raw event metadata.
|
||||||
|
- **Admin Action Mis-triggers:** Role modifications or user deletions on mobile
|
||||||
|
touchscreens need clear danger boundaries.
|
||||||
|
- _Mitigation:_ Use color-coded danger buttons (`btn-danger`) with
|
||||||
|
confirmation prompts on high-impact administrative actions.
|
||||||
|
|
||||||
|
### Alternatives
|
||||||
|
|
||||||
|
- **Separate Mobile Admin App vs Adaptive SSR Views:** Building a separate
|
||||||
|
mobile admin view duplicates route handlers. Using adaptive CSS
|
||||||
|
`@media (max-width: 768px)` card transformations preserves a single unified
|
||||||
|
codebase in pure Hono SSR JSX.
|
||||||
|
|
||||||
|
## 3. Proposed Implementation
|
||||||
|
|
||||||
|
### Phase 1: Mobile User & Invite Management
|
||||||
|
|
||||||
|
1. In `ui/components/AdminUsersPage.tsx` and
|
||||||
|
`ui/components/AdminUserDetailsPage.tsx`:
|
||||||
|
- Render user cards on mobile with avatar initials, username, creation date,
|
||||||
|
role grant badges, and 1-tap action buttons (Edit Roles, Revoke).
|
||||||
|
- Add responsive top search filter input.
|
||||||
|
2. In `ui/components/AdminInvitesPage.tsx`:
|
||||||
|
- Render active invite codes as copy-ready cards with 1-tap clipboard action
|
||||||
|
and expiration countdown badges.
|
||||||
|
|
||||||
|
### Phase 2: App Registry & Role Grants
|
||||||
|
|
||||||
|
1. In `ui/components/AdminAppsPage.tsx` and `ui/components/AdminRolesPage.tsx`:
|
||||||
|
- Transform apps list into responsive cards showing domain, bypass paths,
|
||||||
|
SPIFFE ID, and assigned user roles.
|
||||||
|
|
||||||
|
### Phase 3: Audit Log Event Feed
|
||||||
|
|
||||||
|
1. In `ui/components/AuditLogPage.tsx`:
|
||||||
|
- Implement responsive timeline card feed with color-coded event chips
|
||||||
|
(`login_success` in green, `login_failed` in red, `grant_revoked` in
|
||||||
|
amber).
|
||||||
|
- Add expandable JSON detail viewer for raw event payloads.
|
||||||
|
|
||||||
|
### Phase 4: Verification & Quality Gates
|
||||||
|
|
||||||
|
1. Run `deno fmt ui/**/*.tsx`.
|
||||||
|
2. Run `deno task lint` and `deno task check`.
|
||||||
|
3. Run `deno task test` to ensure all admin routes and SSR components pass
|
||||||
|
cleanly.
|
||||||
Loading…
x
Reference in New Issue
Block a user