GadgetWizard
A production-grade full-featured tech e-commerce platform for Australia region built with Next.js 16, React 19, TypeScript, Tailwind CSS v4 and MySQL.

Languages
- TypeScript99%
- CSS1%
- JavaScript0%

Kaium Al Limon
Full-Stack Mobile & Web Software Engineer
initializing experience
000
A production-grade full-featured tech e-commerce platform for Australia region built with Next.js 16, React 19, TypeScript, Tailwind CSS v4 and MySQL.

Australia's trusted tech e-commerce platform for phones, gadgets, accessories, and wearables. GadgetWizard is a production-grade, full-featured online store built with Next.js 16 (App Router), React 19, TypeScript, Tailwind CSS v4, and MySQL — combining a polished public storefront with a comprehensive admin backoffice.
The homepage is a server-rendered, Suspense-bounded page that fetches banners, brands, and up to 48 products in parallel, then curates them into scannable horizontal scroll rows:
| Section | What it shows |
|---|---|
| Banner Showcase | Auto-rotating carousel with scheduled, clickable campaign banners |
| Brand Marquee | Infinite-scroll animated row of featured brand logos |
| Service Highlights | Free Shipping, 24/7 Self Pickup, Online Support, Secure Payment |
| Featured | Handpicked products with strong value and demand |
| New Arrivals | Freshly listed items just added to the storefront |
| Trending | Top trends shoppers are viewing right now |
| Top Rated | Highly rated picks trusted by verified shoppers |
| Best Seller | Most purchased products this week |
| Free Delivery | Products eligible for free shipping |
| Official Warranty | Products backed by official warranty coverage |
| About Gadget Wizard | Informational content blocks about the store |
Each product row uses a horizontally scrollable client component (ProductScrollRow) with left/right navigation arrows and intersection-observer-based scroll state.
/category/[slug]) — Filtered product listing with pagination, facets, and sort options/brand/[slug]) — All products for a given brand/brands) — Directory of all active brands/categories) — Category grid with images and featured flags/new-arrivals) — Latest product additions/best-sellers) — Top-performing products/offers) — Discounted and promotional products/search) — Full-text product search with query parameter support/product/[slug])/cart)/checkout with selected product IDs/checkout)Elements provider wrapperpdf-lib/checkout/success) — Order confirmation with invoice download button/wishlist)/dashboard)/dashboard/orders) — Full order history with status badges, item details, and per-order detail page/dashboard/orders/[id]) — Line items, delivery status, shipping address, payment info/dashboard/addresses) — Saved address book with add/edit/delete and default flag/dashboard/wishlist) — Manage saved products with pagination and search/dashboard/business-account) — Apply for wholesale account with detailed form (business info, contact, documents), view application status/login) — NextAuth v5 Credentials provider with JWT sessions/forgot-password, /reset-password) — Email-based reset via SMTP with one-time JWT tokens and SHA-256 token fingerprint storage in MySQL?auth=login or ?auth=signup query paramsDisabledAccountError for blocked users/faqs) — Public FAQ list with admin-managed content/about-us) — Store information/privacy-policy)/terms-and-conditions)LiveChatWidget)chat-realtime.tssourceType + optional sourceRef)/admin)All admin pages are role-gated (requireServerRole(["admin"])) and redirect non-admins to /dashboard.
/admin)/admin/revenue)/admin/products)/admin/products/new, /admin/products/[id]) — Full product form using ProductForm component:
/admin/categories)/admin/categories/new, /admin/categories/[id]) — Form with name, slug, icon selector, image URL, sort order, header category flag (max 8 enforced), featured flag, active flag/admin/brands)/admin/brands/new, /admin/brands/[id]) — Form with name, slug, image URL, description, sort order, featured flag, active flag/admin/banners)/admin/orders)/admin/orders/[id]) — Full order view with:
AdminOrderPartialFulfillment component/admin/refunds)/admin/customers)/admin/users)/admin/business-accounts)/admin/business-accounts/[id]) — Full application details including legal info, documents, purchase volume, product categories/admin/reviews)/admin/faqs)/api/faqs) served to the storefront FAQ page/admin/live-chat)/admin/newsletter)/admin/inventory)/admin/cdn)/admin/activity)RouteAudit middleware wrapper for all admin mutating routes/admin/wishlist)/api/auth/register POST Register new user
/api/auth/logout POST Logout
/api/auth/session GET Get current session
/api/auth/password-reset/* POST Request/verify/confirm password reset
/api/auth/callback/credentials POST NextAuth credentials sign-in
/api/me GET Get current user profile
/api/products GET List public products (paginated, filterable)
/api/products/[slug] GET Get product by slug
/api/categories GET List public categories
/api/brands GET List public brands
/api/banners GET List active banners
/api/faqs GET List public FAQs
/api/cart GET Get user cart
/api/cart/add POST Add item to cart
/api/cart/update PATCH Update cart item quantity
/api/cart/remove DELETE Remove item from cart
/api/wishlist GET Get wishlist
/api/wishlist POST Add to wishlist
/api/wishlist/remove DELETE Remove from wishlist
/api/checkout POST Create payment intent + order
/api/checkout/validate POST Pre-checkout validation (stock, pricing)
/api/orders GET List user orders
/api/orders/[id] GET Get order detail
/api/chat/conversations GET List conversations
/api/chat/conversations POST Create conversation
/api/chat/conversations/[id] GET Get conversation + messages
/api/chat/conversations/[id] POST Send message
/api/chat/stream GET SSE stream for real-time events
/api/chat/unread-count GET Unread conversation count
/api/newsletter/subscribe POST Subscribe email
All admin endpoints require authentication + admin role:
/api/admin/analytics GET Dashboard analytics summary
/api/admin/revenue GET Revenue snapshot with time range
/api/admin/products GET List all products
/api/admin/products POST Create product
/api/admin/products/[id] PUT Update product
/api/admin/products/[id] DELETE Delete product
/api/admin/categories GET List all categories
/api/admin/categories POST Create category
/api/admin/categories/[id] PUT Update category
/api/admin/categories/[id] DELETE Delete category
/api/admin/brands GET List all brands
/api/admin/brands POST Create brand
/api/admin/brands/[id] PUT Update brand
/api/admin/brands/[id] DELETE Delete brand
/api/admin/banners GET List all banners
/api/admin/banners POST Create banner
/api/admin/banners/[id] PUT Update banner
/api/admin/banners/[id] DELETE Delete banner
/api/admin/orders GET List all orders (paginated, filterable)
/api/admin/orders/[id] GET Get order detail
/api/admin/orders/[id] PATCH Update order status
/api/admin/orders/[id]/fulfill POST Partial fulfillment
/api/admin/orders/[id]/refund POST Process refund
/api/admin/reviews GET List all reviews
/api/admin/reviews/[id] PATCH Update review status + admin note
/api/admin/faqs GET List all FAQs
/api/admin/faqs POST Create FAQ
/api/admin/faqs/[id] PUT Update FAQ
/api/admin/faqs/[id] DELETE Delete FAQ
/api/admin/users GET List admin users
/api/admin/users POST Create admin user
/api/admin/users/[id] PUT Update admin user status
/api/admin/users/[id] DELETE Delete admin user
/api/admin/customers GET List regular users
/api/admin/customers/[id] PUT Update user active status
/api/admin/business-accounts GET List applications (paginated, filterable)
/api/admin/business-accounts/[id] GET Get application detail
/api/admin/business-accounts/[id] PATCH Review application (approve/reject)
/api/admin/live-chat/conversations GET List all conversations
/api/admin/live-chat/conversations/[id] GET Conversation detail + messages
/api/admin/live-chat/conversations/[id] POST Send admin message
/api/admin/live-chat/conversations/[id] PATCH Close conversation
/api/admin/newsletter GET Get subscriber stats
/api/admin/newsletter/send POST Send campaign email
/api/admin/inventory GET List all inventory
/api/admin/wishlist GET List all wishlist entries
/api/admin/cdn/stats GET CDN dashboard stats
/api/admin/cdn/upload POST Upload file
/api/admin/activity GET List activity log entries
app/api/*/route.ts ← HTTP handlers (thin, parse → call service → return)
lib/server/services/ ← Business logic (validation, orchestration, error handling)
lib/server/repositories/ ← SQL data access (parameterized queries via mysql2)
lib/server/core/ ← Foundational (env, db pool, errors, HTTP helpers, validation)
lib/server/auth/ ← Authentication (NextAuth, JWT, RBAC guards, sessions)
lib/server/mail/ ← SMTP email sending + HTML template rendering
lib/server/realtime/ ← WebSocket/SSE hub for real-time chat
lib/server/middleware/ ← Route audit logging wrapper
POST /api/auth/register → bcrypt hash + authUid stored in MySQLnext-authgetServerSession() or readSession() for API routesrequireRole(request, ["admin"]) in admin routesjti, stored as SHA-256 hash in MySQL for one-time useDisabledAccountError34 sequential SQL migrations cover the full schema:
jti hash, email, expiry, used flag per user? placeholders via mysql2 for injection safetywithTransaction() helper for atomic operations (checkout, order creation)HttpError class with status code + error code; handleRouteError() converts to JSON responsesparseJsonBody() and parseSearchParams()X-Content-Type-Options, X-Frame-Options, Referrer-Policy on all API responsesinsertSystemActivityLog() via RouteAudit wrapper for admin mutating endpointscomponents/
├── ui/ Primitive UI (shadcn-style, Radix-based)
│ ├── avatar.tsx User avatar
│ ├── badge.tsx Status badges
│ ├── breadcrumb.tsx Navigation breadcrumbs
│ ├── button.tsx Variant-based button system
│ ├── card.tsx Card container
│ ├── dialog.tsx Modal dialog (Radix)
│ ├── dropdown-menu.tsx Dropdown menu (Radix)
│ ├── input.tsx Text input
│ ├── label.tsx Form label
│ ├── pagination.tsx Page navigation
│ ├── rich-text-editor.tsx Tiptap editor wrapper
│ ├── select.tsx Dropdown select (Radix)
│ ├── separator.tsx Visual separator
│ ├── sheet.tsx Slide-over panel (Radix)
│ ├── sonner.tsx Toast notification (sonner)
│ ├── table.tsx Data table
│ ├── tabs.tsx Tab container (Radix)
│ └── textarea.tsx Multiline text input
├── storefront/ Public-facing components
│ ├── product-scroll-row.tsx Horizontal product scroller
│ ├── storefront-motion.tsx GSAP scroll animations
│ └── storefront-skeletons.tsx Loading skeletons
├── admin/ Admin-specific components
│ ├── admin-overview-dashboard.tsx
│ ├── admin-revenue-dashboard.tsx
│ ├── admin-orders-manager.tsx
│ ├── admin-order-partial-fulfillment.tsx
│ ├── admin-business-account-requests-manager.tsx
│ ├── admin-inventory-manager.tsx
│ ├── admin-live-chat-manager.tsx
│ ├── admin-reviews-manager.tsx
│ ├── admin-user-manager.tsx
│ ├── regular-user-manager.tsx
│ ├── product-form.tsx
│ ├── product-list-manager.tsx
│ ├── category-create-form.tsx / category-edit-form.tsx / category-list-manager.tsx
│ ├── brand-create-form.tsx / brand-edit-form.tsx / brand-list-manager.tsx
│ ├── faq-manager.tsx
│ ├── newsletter-manager.tsx
│ ├── cdn-upload-button.tsx
│ └── admin-error-toast.tsx
├── layout-chrome.tsx Root layout wrapper (header/footer for public, full-screen for admin/dashboard)
├── site-header.tsx Responsive header with search, categories dropdown, user menu, cart icon, wishlist
├── site-footer.tsx Footer with links, social, newsletter subscribe
├── auth-dialog.tsx Modal login/signup
├── banner-showcase.tsx Banner carousel
├── product-card.tsx Product card with add-to-cart, wishlist toggle, badges
├── product-gallery.tsx Image viewer with mouse zoom
├── product-reviews-section.tsx Review display
├── add-to-cart-inline.tsx Qty selector + color picker + add button
├── cart-client.tsx Cart page with selection, quantity, removal
├── checkout-form.tsx Stripe checkout form with address, fulfillment, purchase mode
├── checkout-page-client.tsx Checkout page wrapper (Stripe Elements)
├── checkout-invoice-download.tsx PDF invoice download
├── order-review-panel.tsx Order review component
├── dashboard-shell.tsx Dashboard layout shell
├── address-manager.tsx Address CRUD component
├── live-chat-widget.tsx Full live chat widget with SSE, typing, history
├── newsletter-subscribe-form.tsx Email subscription form
├── admin-console.tsx Admin sidebar navigation
├── category-filters.tsx Category filter sidebar
└── business-account-application-manager.tsx Business account application form
| Store | Key State | Persistence |
|---|---|---|
auth-store | token, session, user | localStorage (gw-auth) |
cart-store | cart object | localStorage (gw-cart) |
wishlist-store | loadedForUserId, productIds, items | In-memory (lazy-loaded per user) |
lib/client/api.ts is a centralized API client (apiClient object) that:
credentials: "include"Authorization: Bearer <token> header when providedApiError class--accent), zinc-based neutrals, orange/amber gradientsstorefront-motion.tsx), CSS transitions for hover states, marquee animation for brand row| Integration | Purpose | Implementation |
|---|---|---|
| Stripe | Payment processing, refunds | stripe SDK + @stripe/react-stripe-js + @stripe/stripe-js; PaymentIntent lifecycle with webhook-ready design |
| NextAuth v5 | Authentication | Credentials provider with JWT strategy, callbacks for token/session augmentation |
| Nodemailer (SMTP) | Email delivery | Password reset emails, admin welcome emails, newsletter campaigns, order fulfillment notifications; with TLS, connection verification, and error classification |
| Server-Sent Events | Real-time chat | Custom SSE hub with in-memory client registry, heartbeat pings, presence tracking, typing indicators |
| Tiptap | Rich text editing | StarterKit, Highlight, Image, Link, TextAlign, Underline extensions for product descriptions |
| GSAP | Animations | Scroll-triggered entrance animations on storefront sections |
| pdf-lib + html2pdf.js | PDF generation | Invoice PDF download from checkout success page |
| Zod | Validation | Schema validation on all API inputs (body + search params) and environment variables |
| mysql2 | Database | Connection pool with retry logic, parameterized queries, transaction support |
| bcryptjs | Password hashing | Cost factor 12 for user passwords |
| jose | JWT | Password reset token signing and verification |
| Zustand | Client state | Auth, cart, and wishlist stores with localStorage persistence |
| Radix UI | Headless primitives | Dialog, DropdownMenu, Tabs, Avatar, Slot |
gadgetwizard/
├── app/ Next.js App Router
│ ├── layout.tsx Root layout (fonts, chrome, toaster)
│ ├── page.tsx Homepage (server-rendered, Suspense-bounded)
│ ├── globals.css Tailwind + custom CSS
│ ├── about-us/ About page
│ ├── admin/ Admin panel (19 sections)
│ │ ├── page.tsx Overview dashboard
│ │ ├── layout.tsx Admin layout (auth guard + shell)
│ │ ├── products/ Product CRUD (list, new, edit)
│ │ ├── categories/ Category CRUD (list, new, edit)
│ │ ├── brands/ Brand CRUD (list, new, edit)
│ │ ├── banners/ Banner CRUD
│ │ ├── orders/ Order management (list, detail)
│ │ ├── refunds/ Refund history
│ │ ├── reviews/ Review moderation
│ │ ├── faqs/ FAQ CRUD
│ │ ├── revenue/ Revenue dashboard
│ │ ├── live-chat/ Real-time chat management
│ │ ├── business-accounts/ Business account approval
│ │ ├── customers/ User management
│ │ ├── users/ Admin user management
│ │ ├── inventory/ Stock management
│ │ ├── newsletter/ Campaign management
│ │ ├── cdn/ File asset dashboard
│ │ ├── activity/ Audit log viewer
│ │ └── wishlist/ Wishlist viewer
│ ├── api/ HTTP route handlers (14 resource groups)
│ │ ├── auth/ Registration, password reset, NextAuth
│ │ ├── products/ Public product listing + detail
│ │ ├── cart/ Add/update/remove items
│ │ ├── wishlist/ Add/remove items
│ │ ├── checkout/ Validate + create payment intent
│ │ ├── orders/ User order history
│ │ ├── chat/ Conversations, messages, SSE stream
│ │ ├── admin/ Admin CRUD (15 resource groups)
│ │ └── ... Banners, brands, categories, faqs, me, newsletter
│ ├── brand/[slug]/ Brand product listing
│ ├── brands/ Brand directory
│ ├── category/[slug]/ Category product listing
│ ├── categories/ Category grid
│ ├── cart/ Cart page
│ ├── checkout/ Checkout + success
│ ├── dashboard/ User dashboard (overview, orders, addresses, wishlist, business-account)
│ ├── login/ Auth page
│ ├── product/[slug]/ Product detail
│ ├── search/ Product search
│ ├── wishlist/ Wishlist page
│ ├── forgot-password/ Password reset request
│ ├── reset-password/ Password reset confirm
│ ├── faqs/ FAQ page
│ ├── new-arrivals/ New arrivals listing
│ ├── best-sellers/ Best sellers listing
│ ├── offers/ Offers listing
│ └── ... Privacy policy, terms, about
├── components/ React components
│ ├── ui/ 18 primitive components
│ ├── storefront/ 3 components
│ ├── admin/ 22 admin components
│ └── ... 20+ feature components
├── lib/
│ ├── client/
│ │ ├── api.ts Centralized API client (985 lines, covers all endpoints)
│ │ └── types.ts TypeScript interfaces (446 lines)
│ ├── server/
│ │ ├── core/ db.ts, env.ts, errors.ts, http.ts, validation.ts
│ │ ├── auth/ next-auth.ts, guards.ts, session.ts, jwt.ts, cookie.ts, server-session.ts
│ │ ├── repositories/ 21 repository modules
│ │ ├── services/ 19 service modules
│ │ ├── mail/ smtp.ts, templates.ts
│ │ ├── realtime/ chat-realtime.ts (SSE hub)
│ │ ├── middleware/ route-audit.ts
│ │ ├── types.ts Server-side types
│ │ ├── schemas.ts Zod validation schemas
│ │ └── utils/ slug, CDN helpers
│ ├── shared/
│ │ ├── checkout.ts Checkout math (delivery charge, totals, pickup snapshot)
│ │ ├── return-to.ts Auth redirect URL sanitization
│ │ └── slug.ts Slug generation
│ └── stores/ Zustand stores (auth, cart, wishlist)
├── migrations/ 34 sequential SQL files
├── types/ next-auth.d.ts
├── public/ Static assets
├── next.config.ts Next.js configuration
├── tailwind.config.ts Tailwind configuration
├── components.json shadcn/ui config
├── tsconfig.json TypeScript configuration
├── eslint.config.mjs ESLint flat config
└── postcss.config.mjs PostCSS config
The application validates all environment variables at startup via Zod (lib/server/core/env.ts):
| Variable | Required | Description |
|---|---|---|
DB_HOST | Yes | MySQL host |
DB_PORT | No (default: 3306) | MySQL port |
DB_USER | Yes | MySQL user |
DB_PASSWORD | No (default: "") | MySQL password |
DB_NAME | Yes | MySQL database name |
DB_POOL_LIMIT | No (default: 3) | Connection pool size |
AUTH_SECRET | Yes (min 32 chars) | NextAuth secret |
JWT_SECRET | Yes (min 32 chars) | JWT signing secret |
CDN_BASE_URL | Yes | CDN base URL |
CDN_API_BASE_URL | No | CDN API base URL |
CDN_API_KEY | No | CDN API key |
STRIPE_SECRET_KEY | No | Stripe secret key |
STRIPE_PUBLISHABLE_KEY | No | Stripe publishable key |
STRIPE_WEBHOOK_SECRET | No | Stripe webhook secret |
SMTP_HOST | No | SMTP server host |
SMTP_PORT | No (default: 465) | SMTP port |
SMTP_USER / SMTP_USERNAME | No | SMTP username |
SMTP_PASS / SMTP_PASSWORD | No | SMTP password |
SMTP_FROM_EMAIL | No | Sender email address |
SMTP_FROM_NAME | No (default: "GadgetWizard") | Sender name |
APP_BASE_URL | No | Base URL for links in emails |
PASSWORD_RESET_TOKEN_EXPIRES_MINUTES | No (default: 30) | Token lifetime |
#f36523 (orange) used across buttons, links, gradients, highlightsfrom-[#f36523] via-orange-400 to-amber-400 for accent text and decorative elementszinc-50 through zinc-900) for UI surfaces and typographyrounded-2xl / rounded-3xl for cards and containers; rounded-full for pills and badgesshadow-sm on cards; none on admin/dashboard to maintain flat aesthetic