Add password reset, order confirmation email with editable templates, and fix missing account entry points
Password reset uses Payload's built-in forgot/reset-password flow, customized to link to this app instead of the Payload admin. Order confirmation email and the password-reset email's wording both come from a new Payload email-templates collection, editable without a deploy and previewable via Live Preview at /email-preview/[type] (same mechanism as Posts/LegalPages/Testimonials, sample data instead of a real document). Also: order numbers get a random suffix (prevents guessing, motivated by a considered-and-deferred guest order-lookup feature); the discount code field only shows in the cart when a code is actually active (codes now apply via a ?code= link instead of manual entry); and three navigation gaps found while testing — no reachable login link with an empty cart, no logout link anywhere, no way back from profile to order history. Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
This commit is contained in:
@@ -71,6 +71,53 @@ function isNavLinkActive(href: string, pathname: string, activeSection: string):
|
||||
return pathname === href || pathname.startsWith(`${href}/`);
|
||||
}
|
||||
|
||||
// Account icon — no Figma source exists for this yet (added outside the
|
||||
// normal Figma-first workflow, see the assistant's own project notes on
|
||||
// why: without it there was no reachable way to log in at all once the
|
||||
// cart was empty and no recent order existed — /checkout's own login
|
||||
// toggle never even renders in that state, see CheckoutContent.tsx's
|
||||
// early "Warenkorb ist leer" return). Fetches auth state client-side via
|
||||
// /api/account/me rather than through the server-rendered layout — this
|
||||
// component's parent (app/layout.tsx) is otherwise static/ISR-cacheable,
|
||||
// and reading the session cookie there (next/headers' cookies()) would
|
||||
// force the entire site into per-request dynamic rendering just for this.
|
||||
// `loggedIn === null` is the brief "not checked yet" state on first paint.
|
||||
function AccountLink({ variant }: { variant: "icon" | "mobile" }) {
|
||||
const [loggedIn, setLoggedIn] = useState<boolean | null>(null);
|
||||
|
||||
useEffect(() => {
|
||||
fetch("/api/account/me")
|
||||
.then((res) => setLoggedIn(res.ok))
|
||||
.catch(() => setLoggedIn(false));
|
||||
}, []);
|
||||
|
||||
const href = loggedIn ? "/konto/bestellungen" : "/konto/login";
|
||||
|
||||
if (variant === "mobile") {
|
||||
return (
|
||||
<Link
|
||||
href={href}
|
||||
className="min-h-11 flex items-center justify-center px-6 py-4 rounded-sm border border-[#868686] text-h4 font-bold text-text-primary hover:border-brand hover:text-brand active:scale-[0.97] transition-all"
|
||||
>
|
||||
{loggedIn ? "Mein Konto" : "Anmelden"}
|
||||
</Link>
|
||||
);
|
||||
}
|
||||
|
||||
return (
|
||||
<Link
|
||||
href={href}
|
||||
aria-label={loggedIn ? "Mein Konto" : "Anmelden"}
|
||||
className="relative flex h-11 w-11 items-center justify-center shrink-0 active:scale-[0.9] transition-transform"
|
||||
>
|
||||
<svg viewBox="0 0 24 24" className="h-6 w-6 text-text-primary" fill="none" aria-hidden="true">
|
||||
<circle cx="12" cy="8" r="3.6" stroke="currentColor" strokeWidth="1.8" />
|
||||
<path d="M4.5 20c1.2-4 4-6 7.5-6s6.3 2 7.5 6" stroke="currentColor" strokeWidth="1.8" strokeLinecap="round" />
|
||||
</svg>
|
||||
</Link>
|
||||
);
|
||||
}
|
||||
|
||||
// Cart icon + count badge — traced from the Figma Navbar/Default component's
|
||||
// btn-cart (icon-cart 32x30 + cart-count-badge, node 4849:24). Visible at
|
||||
// every breakpoint tier (unlike the nav links / CTA buttons, which move into
|
||||
@@ -390,6 +437,7 @@ export function Navbar({ singleActiveProduct }: { singleActiveProduct: boolean }
|
||||
(below lg). Grouped so spacing stays consistent as individual
|
||||
children hide/show across the three breakpoint tiers. */}
|
||||
<div className="flex items-center gap-2">
|
||||
<AccountLink variant="icon" />
|
||||
<CartLink />
|
||||
|
||||
{/* CTA buttons — inline from md (768px) up, i.e. through both
|
||||
@@ -519,6 +567,9 @@ export function Navbar({ singleActiveProduct }: { singleActiveProduct: boolean }
|
||||
>
|
||||
7-Tage-Challenge
|
||||
</Link>
|
||||
<div onClick={closeMobile}>
|
||||
<AccountLink variant="mobile" />
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</header>
|
||||
|
||||
Reference in New Issue
Block a user