berrypod/docs/plans/onboarding-ux.md
jamey db130a7155
All checks were successful
deploy / deploy (push) Successful in 1m19s
rework email settings for true progressive enhancement
Render all adapter field sections in the form with CSS :has(:checked)
controlling visibility. Selecting a provider instantly shows its config
fields — no JS, no page reload, no server round-trip needed.

- Render all 6 adapter configs with data-adapter attribute
- CSS :has(:checked) show/hide rules per adapter in admin stylesheet
- Namespace field names per adapter (email[brevo][api_key] etc)
- Drop 4 transactional-only providers (Resend, Postmark, Mailgun, MailPace)
- Remove noscript "Switch provider" button and controller redirect workaround
- Remove configured_adapter hidden input tracking
- Hide JS-only test email button for no-JS users via noscript style
- LiveView progressively enhances with async save and test email

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-04 23:10:37 +00:00

9.2 KiB

Onboarding UX v2

Status: In progress

Supersedes the original onboarding-ux plan. Based on usability testing session (March 2026) covering the setup wizard, launch checklist, email provider setup, and general onboarding flow.

Vision

A non-technical seller should be able to go from zero to a live shop without confusion or frustration. The setup should feel like one cohesive journey, not a scavenger hunt through admin pages. Every step should explain why it's needed, be forgiving of mistakes, and never leave the user stranded.

Current flow

  1. Setup wizard (lib/berrypod_web/live/setup/onboarding.ex): 3 cards — admin account, provider API key, Stripe connection. Gated by secret in prod, auto-login after account creation.
  2. Dashboard checklist (lib/berrypod_web/live/admin/dashboard.ex): 5 items with progress bar. Visible when site_live is false and not dismissed.
  3. Coming soon page: blocks public access before launch.
  4. Setup status (lib/berrypod/setup.ex): setup_status/0 returns booleans for each milestone.

What changes

A. Simplify initial setup to account creation only

The first screen should be dead simple and low-friction: email, password (with confirmation field), shop name. That's it. No provider keys, no Stripe.

  • Live validation on all fields (email format, password strength/match, shop name not blank)
  • Note under shop name: "You can change this later"
  • On submit: create account, log in, redirect to the guided setup flow

Email/password correction after this point is just normal admin account settings — no special "go back to setup" needed.

Files: lib/berrypod_web/live/setup/onboarding.ex, possibly lib/berrypod_web/live/admin/settings.ex

B. Guided setup flow with progress bar

After account creation, the user enters a single multi-step guided journey. This replaces the current approach of separate admin pages.

Intro screen — before any steps, briefly explain what Berrypod does and why you need each thing:

"Berrypod connects your print-on-demand products to your own online shop. To get fully set up, you'll need three things:

  • A print provider account (like Printify or Printful) to make and ship your products
  • A Stripe account to accept payments from customers
  • An email provider account so your shop can send order confirmations and shipping updates"

Then the steps with a clear progress bar at the top. Each step shows: step number, title, whether it can be skipped, estimated time.

Steps:

  1. Connect print provider — allow connecting multiple providers (not forced to pick just one). "Skip for now" available.
  2. Connect Stripe for payments — "Skip for now" available.
  3. Set up email provider — "Skip for now" available.

Each step embeds the same settings UI components that live in the admin pages (shared, not duplicated). The guided flow adds extra context and hand-holding around them.

On completion (or after skipping all): redirect to dashboard with clear status messaging.

Key UX decisions:

  • Progress bar visible at all times, showing completed/current/upcoming steps
  • Each step has a "Skip for now" with a brief, non-naggy note about what won't work without it
  • External service links (create Printify account, etc.) open in new tabs with external-link icon and aria label
  • Users can go back to previous steps to correct mistakes
  • If revisiting (e.g. after closing browser), detect existing state via Setup.setup_status/0 and resume from the first incomplete step

Files: lib/berrypod_web/live/setup/onboarding.ex, lib/berrypod/setup.ex, new shared components

C. Forgiving API key validation

API key entry should be as forgiving as possible:

  • Auto-strip leading/trailing whitespace on paste and submit
  • Validate format where known:
    • Printify: 36-character UUID format
    • Printful: specific prefix/length
    • Stripe: must start with sk_live_ or sk_test_
    • Email providers: provider-specific format checks
  • Specific, helpful error messages: "This looks too short — Printify API keys are usually 36 characters" rather than generic "Invalid"
  • Validate on blur for fast feedback, not just on submit
  • Link to where to find the key: "Find your Printify API key at Settings > Connections"

Files: lib/berrypod_web/live/setup/onboarding.ex, lib/berrypod_web/live/admin/providers.ex, validation logic in contexts

D. Email provider setup UX — done

Reworked the email provider selection and configuration. Changes across two sessions:

Session 1 (commit dd659e4):

  • Recommended pick (Brevo) highlighted with badge
  • Two groups: "Also sends newsletters" vs "Transactional only"
  • One-liner per provider with free tier info
  • Self-hosted/SMTP in collapsible "Advanced" section
  • Guided flow after selection with config fields
  • Send test email button with async delivery
  • Removed masked key display
  • Default from address auto-set from admin email
  • No-JS support via controller POST fallback
  • 17 audit fixes (a11y, error handling, UX)

Session 2 (uncommitted):

  • Dropped 4 transactional-only providers (Resend, Postmark, Mailgun, MailPace) — all are transactional-only and not useful for a shop that needs newsletters. 6 adapters remain: Brevo, SendGrid, Mailjet, MailerSend + SMTP, Postal
  • Removed "Popular providers" heading and description (unnecessary with fewer providers)
  • Fixed no-JS provider switching: noscript submit button always visible with dynamic text
  • Fixed no-JS radio highlight: replaced server-applied card-radio-card-selected class with pure CSS :has(:checked) selector
  • Cleaned up key validation (removed 4 provider clauses, removed 2 known prefixes)
  • Updated all related tests (adapters, key validation, email settings LiveView, controller, mailer)

Files: lib/berrypod_web/live/admin/email_settings.ex, lib/berrypod/mailer/adapters.ex, lib/berrypod/key_validation.ex, assets/css/admin/components.css, lib/berrypod_web/controllers/email_settings_controller.ex

E. Contextual prompts for skipped steps

When a step is skipped, surface the need where it matters — once per context, never as global nags:

  • Products page (no print provider): empty state explaining why products are empty, with link to connect a provider
  • Cart/checkout (no Stripe): checkout button disabled with explanation and link to connect Stripe
  • Order detail (no email provider): note saying "Order confirmation emails aren't being sent. Set up an email provider to send them automatically."
  • Dashboard checklist: always shows outstanding items regardless of skips

Principle: explain what's missing, link to the fix, one instance per context.

Files: lib/berrypod_web/live/admin/dashboard.ex, lib/berrypod_web/live/shop/ (various), lib/berrypod_web/components/

F. Dashboard checklist and messaging

Rework the dashboard checklist to match the guided setup flow:

  • Before setup complete: "Your admin account has been created. Continue the full setup below." with checklist of outstanding items
  • After all steps done and site live: "Your shop is live! Ready to go"
  • Checklist item names match the setup wizard step names exactly (no mismatches)
  • Each checklist item links to its admin settings page (for when they return outside the wizard)
  • Help/FAQ links next to items involving API keys or complicated config
  • Collapsible rather than dismissable (can always get it back)
  • Shipping setup and shop settings as additional checklist items (carried forward from v1 plan)

Files: lib/berrypod_web/live/admin/dashboard.ex, lib/berrypod/setup.ex

G. Coming soon page fixes

  • Fix logo displaying oddly to the side
  • Add a subtle "Admin login" link (footer or corner)

Files: lib/berrypod_web/live/shop/coming_soon.ex, associated template

All links to external services throughout the app get:

  • target="_blank" + rel="noopener noreferrer"
  • Small external-link icon
  • Aria label indicating it opens in a new window

Files: templates throughout lib/berrypod_web/

I. Input styling — WCAG compliance

Increase input field border contrast to meet WCAG AA (3:1 minimum for UI components), aim for AAA. Clear, visible field edges in all contexts.

Files: assets/css/admin/components.css, assets/css/shop/ CSS files

Task breakdown

# Task Est Status
A Simplify initial setup to account creation only 1.5h planned
B Guided setup flow with progress bar 4h planned
C Forgiving API key validation 1.5h planned
D Email provider setup UX rework 2h done
E Contextual prompts for skipped steps 2h done
F Dashboard checklist and messaging rework 2h planned
G Coming soon page fixes (logo + admin link) 30m planned
H External links UX (new tabs, icons, aria) 1h planned
I Input styling — WCAG compliance 1h planned

Total estimate: ~15.5h

Suggested order

  1. A first — simplify the entry point
  2. B — the big piece, the guided flow
  3. C — validation improvements (can be done alongside B)
  4. D — email provider UX (part of the guided flow)
  5. F — dashboard checklist rework (depends on the flow being defined)
  6. E — contextual prompts (depends on knowing what's skippable)
  7. G, H, I — smaller fixes, can be done any time