diff --git a/src/app/checkout/client.tsx b/src/app/checkout/client.tsx new file mode 100644 index 0000000..a3c5ba0 --- /dev/null +++ b/src/app/checkout/client.tsx @@ -0,0 +1,289 @@ +'use client'; + +import { useEffect, useState } from 'react'; +import Link from 'next/link'; +import { useCart } from '@/lib/cartStore'; +import { loginCustomer } from '@/app/account/actions'; +import Price from '@/components/Price'; + +interface CheckoutPageClientProps { + isLoggedIn: boolean; + customer?: any; +} + +export default function CheckoutPageClient({ isLoggedIn, customer }: CheckoutPageClientProps) { + const [mounted, setMounted] = useState(false); + const [mode, setMode] = useState<'login' | 'guest' | null>(isLoggedIn ? 'logged-in' : null); + const [checkingOut, setCheckingOut] = useState(false); + const [checkoutError, setCheckoutError] = useState(null); + const [guestData, setGuestData] = useState({ + fullName: '', + email: '', + phone: '', + address: '', + }); + + const items = useCart((s) => s.items); + const total = useCart((s) => s.total()); + + useEffect(() => setMounted(true), []); + + if (!mounted) return null; + + if (items.length === 0) { + return ( +
+

Checkout

+

Your bag is empty.

+ + Continue shopping + +
+ ); + } + + const handleGuestCheckout = async (e: React.FormEvent) => { + e.preventDefault(); + if (!guestData.fullName || !guestData.email || !guestData.phone || !guestData.address) { + setCheckoutError('Please fill in all fields.'); + return; + } + + setCheckingOut(true); + setCheckoutError(null); + try { + const res = await fetch('/api/checkout', { + method: 'POST', + headers: { 'Content-Type': 'application/json' }, + body: JSON.stringify({ + items, + guest: { + name: guestData.fullName, + email: guestData.email, + phone: guestData.phone, + address: guestData.address, + }, + }), + }); + const data = await res.json(); + if (!res.ok || !data.url) { + throw new Error(data.error ?? 'Something went wrong starting checkout.'); + } + window.location.href = data.url; + } catch (err) { + setCheckoutError(err instanceof Error ? err.message : 'Something went wrong.'); + setCheckingOut(false); + } + }; + + return ( +
+

Checkout

+ +
+ {/* Order summary */} +
+

Order summary

+
+ {items.map((item) => ( +
+
+

{item.name}

+

Qty: {item.quantity}

+
+ +
+ ))} +
+
+
+ Total + +
+
+
+ + {/* Checkout options */} +
+ {mode === 'logged-in' ? ( +
+

Ready to checkout

+

Logged in as {customer?.email}

+ + {checkoutError && ( +

+ {checkoutError} +

+ )} +
+ ) : mode === null ? ( +
+

How would you like to checkout?

+ + +

+ Don't have an account?{' '} + + Create one now + +

+
+ ) : mode === 'login' ? ( +
+ +

Log in

+
+ +
+ + +
+
+ + +
+ +
+
+ ) : ( +
+ +

Guest checkout

+ {checkoutError && ( +

+ {checkoutError} +

+ )} +
+
+ + setGuestData({ ...guestData, fullName: e.target.value })} + className="w-full border border-line px-3 py-2 text-sm" + /> +
+
+ + setGuestData({ ...guestData, email: e.target.value })} + className="w-full border border-line px-3 py-2 text-sm" + /> +
+
+ + setGuestData({ ...guestData, phone: e.target.value })} + className="w-full border border-line px-3 py-2 text-sm" + /> +
+
+ +