177541d96a99

gate Onboarding view ahead of NewVault on first install via peach_onboarded storage flag

time
2026-04-28 04:42 UTC · 6 months ago
machine
koh2
parent
aa954418fa8f
1 file src/popup/App.tsx+33 −6
src/popup/App.tsx+33 −6
@@ -2,6 +2,7 @@22 import { ACCENT_COLORS } from "../shared/types";33 import type { AccentColorName, PasskeyEntry, PendingPasskeyRequest, ProFeature, VaultEntry } from "../shared/types";44 import { LockView } from "./views/Lock";5+import { Onboarding } from "./views/Onboarding";56 import { ProCelebration } from "./views/ProCelebration";67 import { VaultView, type SortOrder } from "./views/Vault";78 import { EntryView } from "./views/Entry";@@ -168,6 +169,7 @@168169   );169170   const [contentTransitioning, setContentTransitioning] = createSignal(false);170171   const [hasVault, setHasVault] = createSignal(false);172+  const [onboarded, setOnboarded] = createSignal(true);171173   const [entries, setEntries] = createSignal<VaultEntry[]>([]);172174   const [selectedEntry, setSelectedEntry] = createSignal<VaultEntry | null>(null);173175   const [editEntry, setEditEntry] = createSignal<VaultEntry | undefined>(undefined);@@ -333,6 +335,22 @@333335       (celebrationResponse as { ok: boolean; data?: boolean }).data334336     );335337     setHasVault(vaultExists);338+    // Onboarding gate — show once on first install, never again. Existing339+    // users (vaultExists) are auto-marked onboarded so they skip the flow340+    // even on the very first popup open after this feature ships.341+    try {342+      const onboardingState = await chrome.storage.local.get("peach_onboarded");343+      const seen = onboardingState.peach_onboarded === true;344+      if (vaultExists && !seen) {345+        await chrome.storage.local.set({ peach_onboarded: true });346+        setOnboarded(true);347+      } else {348+        setOnboarded(seen);349+      }350+    } catch {351+      // storage unavailable — default to onboarded so we never block boot352+      setOnboarded(true);353+    }336354     await Promise.all([restoreSettings(), refreshProStatus()]);337355 338356     // Mark played before any animation so a crash mid-sequence never replays it@@ -838,12 +856,21 @@838856           <Show839857             when={!isLockedView()}840858             fallback={841-              <LockView842-                hasVault={hasVault()}843-                ready={bootState() === "ready"}844-                isPro={proStatus()}845-                onUnlock={handleUnlock}846-              />859+              <Show860+                when={onboarded() || hasVault()}861+                fallback={862+                  <Onboarding863+                    onComplete={() => setOnboarded(true)}864+                  />865+                }866+              >867+                <LockView868+                  hasVault={hasVault()}869+                  ready={bootState() === "ready"}870+                  isPro={proStatus()}871+                  onUnlock={handleUnlock}872+                />873+              </Show>847874             }848875           >849876             <Show

view file