Changelog

What's new in Stashd.

v0.18.0 — Landing Rebrand & A/B Test (Apr 12, 2026)

Landing Page Redesign — Midnight + Electric Mint

  • Full brand rebrand rolled out: Midnight (#080E1F) + Electric Mint (#3EEBA8) palette, Syne 800 display + Inter 400–800 body, dark-first everywhere
  • Retired the old light-mode landing; every marketing / legal page (/blog, /about, /help, /contact, /changelog, /privacy, /terms, /fair-usage-policy, /pocket-alternative) now renders through a shared with the new theme
  • Canonical shared footer applied across both variants AND every marketing / legal page — STASHD wordmark, new tagline "Save anything from anywhere\*", three nav groups, and "Extend Stashd" distribution chips linking to the Chrome extension and @stashdbot Telegram bot
  • Waitlist-aware copy: when the admin toggle is on, the hero / CTAs / pricing card / FAQ flip to invite-only messaging (2 teaser saves, +3 per invite up to 30 bonus, 15/month free once admitted)
  • Supported-platform honesty: all 6 live platforms surfaced (Instagram, TikTok, YouTube, X, Reddit, Threads) with new RedditIcon, ThreadsIcon, and TelegramIcon added to the v2 icon set
  • Real totalSaves / totalUsers wired into the Social Proof bar; /api/og edge route serves a dynamic 1200×630 branded OG image replacing the legacy PNG

A/B Test Infrastructure

  • Variant A (control) — ported from the original landing page, dark-reskinned: navbar, hero with URL-extraction demo, social proof, how-it-works, use cases, comparison table, pricing (monthly/yearly toggle), 9-question FAQ with FAQPage JSON-LD, final CTA, footer
  • Variant B (animated) — Product-Hunt-ready showstopper with all 8 Emil-Kowalski-grade animations (wordmark stagger, canvas particle field, typewriter search demo, scroll reveals, magnetic CTA, card parallax, number counter, cursor glow), prefers-reduced-motion bypass on every single one
  • Vercel Edge Middleware assigns variant server-side (src/middleware.ts + src/lib/experiments/middleware-integration.ts) with a 30-day sticky cookie — zero layout shift, no client-side flicker
  • ?variant=control / ?variant=animated QA bypass + ?ref=producthunt forces the animated variant for Product Hunt hunters
  • PostHog experiment wired with typed event wrappers (page_viewed, cta_clicked, scroll_depth_reached, search_demo_interacted, feature_section_viewed, social_proof_viewed, time_on_page_milestone, animation_visible) + $experiment_started identifier + ab_variant super-property
  • Vercel Analytics + Speed Insights mounted in layout.tsx for per-variant Core Web Vitals tracking

Admin — Landing A/B Signup Tracker

  • New migration: profiles.ab_variant_at_signup (text, CHECK constraint for 'control' | 'animated') stamped once by the auth callback when a brand-new user completes signup
  • src/app/api/cron/analytics/route.ts aggregates signups per variant (all-time + last 7d, share %) and upserts as landing_ab_variant_metrics in admin_analytics_cache
  • New admin dashboard card: "Landing A/B — Signups by Variant" with per-variant progress bars, 🏆 leader indicator, delta footnote, winner pill (requires ≥40 tracked signups), and deep links to preview each variant in a new tab

Product Hunt Launch Prep

  • Complete marketing kit shipped under docs/marketing/: Instagram carousels + reels + stories, TikTok hook scripts + trending formats + 5-part series plan, YouTube Shorts + long-form outlines + community templates, X threads + standalone tweets + launch-day playbook
  • Fresh brand assets in public/: og-image-v2.svg, twitter-card-v2.svg, app-icon-v2.svg, favicon-v2.svg

Chrome Extension v0.4.1

  • Fixed the Google SSO "Opening Google sign-in…" hang via new /api/auth/extension-callback bridge route that handles the PKCE code exchange server-side and bounces back to the extension's chromiumapp.org URL with tokens in the hash fragment
  • Extension now correctly propagates bridge-route errors to the popup instead of hanging

v0.17.0 — Mobile Polish & Chat Fixes (Apr 11, 2026)

Chat

  • Fixed mobile layout breaking when conversation starts — messages area now scrolls correctly instead of pushing the input bar off-screen
  • Conversation list now refetches from the server after deleting a conversation, restoring correct chronological order without a hard refresh
  • Smooth fade-in transitions when switching between the welcome screen and message history

Feed

  • Category chips now show a press/tap effect (active:scale-90) for immediate tactile feedback on mobile
  • Active category chip has a subtle ring glow for clearer selection state
  • Loading spinner appears on the selected category chip while items are being fetched

Settings

  • Added "Admin Dashboard" link in Settings, visible only on mobile (desktop already has it in the sidebar)

AI

  • Markdown rendering in AI answer cards (bold, lists, citations)
  • Search results shortlisted alongside AI answer with disclaimer

v0.16.0 — Conversion Monitor & Feed Polish (Apr 11, 2026)

Share Link Conversion Monitor

  • Attribution tracking: public collection pages set a cookie and CTA links carry ref=collection&slug= params through signup
  • Auth callback records which shared collection drove each signup in new collection_signups table
  • Analytics cron computes overall and per-collection conversion rates (views vs signups)
  • New admin card: "Share Link Conversions" with headline rate, 7-day trend, per-collection breakdown table
  • LLM-powered growth tips: GPT-4o-mini analyzes conversion data and generates 2-3 actionable tips on each admin page load

Feed UX

  • Skeleton loading cards shown while feed loads (5 pulsing placeholder cards)
  • Smooth fade-in transition when items load, instead of abrupt state change
  • Empty state only appears after loading completes, not during

Collection UX

  • Quick "Copy link" button on public collections — one click instead of opening the share dialog
  • Fixed trailing space in share URLs caused by NEXT_PUBLIC_APP_URL env var
  • Toggles (collaboration requests, public comments, add items) aligned with header text

v0.15.0 — Mobile Fixes & Smart Nudges (Apr 11, 2026)

Mobile Fixes

  • Delete/restore buttons now visible on mobile feed items (were hidden behind hover-only state)
  • Chat send button no longer overflows outside input box on mobile — model selector wraps to second row on narrow screens
  • Chat conversation title no longer cut off on mobile — fixed container height with dvh units

Smart Nudges (Save Reminders)

  • Nudge banner now cycles through all undismissed reminders, rotating every ~2 minutes with fade transition
  • Replaced dismiss X with context-aware response buttons:

- Restaurants/places: "Not yet, but soon" / "Yes!" / "Decided not to"

- Recipes: "Haven't tried it" / "Made it!" / "Not for me"

- General: "Not yet" / "Done!" / "Not interested"

  • User responses tracked in database (response + response_at columns)
  • Negative responses ("Not for me" variants) suppress future nudges for that item

v0.14.0 — Rebrand: Gist → Stashd (Apr 11, 2026)

Rebrand

  • Full rebrand from Gist to Stashd across 95 files
  • New domain: trystashd.com (custom domain on Vercel, DNS on Namecheap)
  • New color system: Midnight + Electric Mint palette (OKLCH)
  • Wordmark: STASHD with accent-colored D in Electric Mint (#34D399)
  • New logo/favicon/PWA icons: mint S on midnight background
  • Added Syne 800 font for headings
  • All UI copy, metadata, SEO, emails, legal pages, and i18n (EN/ES) updated
  • Extension v0.4.0: rebranded and submitted to Chrome Web Store
  • Cookie keys renamed: stashd-theme, stashd-locale
  • Telegram bot renamed: @StashdBot
  • Supabase auth URLs + Google OAuth redirects updated for new domain
  • Resend sending domain validated (trystashd.com)

Fixes

  • Railway yt-dlp service redeployed with correct root directory + start command — /download-audio endpoint now live (was 404 due to stale deploy)

v0.13.0 — Onboarding Flow & Sidebar Setup Prompts (Apr 10, 2026)

Onboarding Overlay

  • Dark overlay with white-glow spotlight on the PasteBar — guides first-time users to save their first Gist
  • Triggered on first visit to /feed when onboarding_completed = false
  • Auto-dismisses when user saves their first item, or via "Skip for now" link
  • Celebratory scale-up + fade animation (400ms) on save dismiss; 300ms fade on skip
  • Dynamic tooltip positioning: left of PasteBar on desktop (falls back to below on narrow viewports), below on mobile
  • Self-measuring via ResizeObserver — tooltip repositions live as PasteBar expands (error, loading, manual input)
  • Full accessibility: role="dialog", aria-modal, focus trap (Tab/Shift+Tab cycling), Escape key dismiss, focus restoration on unmount
  • iOS PWA install bottom sheet modal with 3 numbered steps (Share → Add to Home Screen → Add), i18n in EN/ES, Escape key + focus management
  • Existing users with saves_count > 0 are backfilled as onboarding_completed = true (never see the overlay)

Fixes

  • Chrome Web Store URL in setup prompts now points to the real published listing (was placeholder)

Sidebar Setup Prompts

  • Sequenced prompt cards appear in the desktop sidebar after onboarding completes
  • Priority order: Chrome Extension (#1) → Telegram Bot (#2) — one card at a time
  • Each prompt has an icon, one-liner copy, CTA button, and permanent dismiss (X)
  • Telegram prompt auto-dismisses when user links their Telegram account
  • PWA install prompt shown on mobile only (as a horizontal banner at top of feed)
  • Dismissed state persisted in dismissed_prompts text array on profiles table

Analytics

  • 6 new PostHog events: onboarding_shown, onboarding_completed (with method: saved/skipped), time_to_first_save (seconds), setup_prompt_shown, setup_prompt_clicked, setup_prompt_dismissed

Technical

  • New DB columns: onboarding_completed (boolean), dismissed_prompts (text[]) on profiles
  • New API endpoints: POST /api/onboarding/complete, POST /api/onboarding/dismiss-prompt
  • 4 new components: onboarding-overlay, setup-prompt-card, setup-prompts, mobile-setup-banner
  • Full i18n support (English + Spanish)
  • PWA beforeinstallprompt event captured for install prompt trigger

v0.12.0 — Content Scripts, Cross-User Dedup & Knowledge Category (Apr 10, 2026)

Chrome Extension v0.4.0 — Platform Content Scripts

  • New content scripts for TikTok, Twitter/X, and YouTube extract rich metadata directly from the page DOM
  • TikTok: parses __UNIVERSAL_DATA_FOR_REHYDRATION__, SIGI_STATE, JSON-LD, and DOM fallback for caption, author, thumbnail, video URL, likes/comments
  • Twitter/X: parses data-testid DOM selectors, JSON-LD, and meta tags for tweet text, author handle, media URLs, engagement counts
  • YouTube: parses ytInitialPlayerResponse, ytInitialData, and DOM fallback for title, channel, description, thumbnail, likes/comments
  • All content scripts follow the content-instagram.js pattern: 10-min TTL cache, { action: "extract" } message listener, normalized output shape
  • background.js now attempts content script extraction for all 4 platforms (was Instagram-only)
  • Manifest.json updated with content script entries for TikTok, Twitter/X (both domains), and YouTube
  • Published to Chrome Web Store (submitted for review Apr 10, 2026)

Cross-User Content Deduplication

  • New content_cache table stores extraction results (transcript, structured data, embedding) keyed by normalized URL
  • When multiple users save the same URL, the second+ users skip the expensive Apify/Whisper/OpenAI pipeline and reuse cached results
  • Cache integrated into all 3 extraction paths: YouTube, Instagram, and generic (TikTok/Twitter/other)
  • Each user still gets their own saved_items row with independent collections, comments, and entity grouping
  • Thumbnails still stored per-user (CDN URLs expire, Supabase Storage URLs don't)
  • hit_count tracks cache reuse for cost savings analytics
  • PostHog events include cache_hit: true for tracking

Knowledge Category

  • New "knowledge" category for educational videos, documentaries, explainers, opinion pieces, news, and interviews
  • Structured extraction: topic, key_takeaways[], mentions[] (person/company/product/place with context)
  • Dedicated renderer: numbered takeaway points + mention chips with hover tooltips
  • Feed preview shows first 2 key takeaways
  • Blue color scheme, 📚 filter chip
  • GPT prompt updated: prefers "knowledge" over "other" for educational content, never includes channel metadata (subscribers, upload frequency)

Bug Fixes

  • Fixed YouTube video ID extraction failing when normalizeUrl sorts query params (e.g., ?t=8s&v=xxx — regex expected ?v= first, now uses proper URL parsing)
  • Fixed stale YouTube data on SPA navigation — content script now prioritizes DOM extraction over