Product #01 / 12
Complete page-by-page Playwright audit of LinkPay — the URL shortener and link monetization SaaS. Every route tested, every login role validated, every bug fixed or documented.
LinkPay is a feature-rich, well-designed Next.js 16 SaaS covering URL shortening, ad monetization, analytics, and multi-role admin. The UI is polished across all 28 tested pages. However, audit found two blocker-level bugs (broken login flow, 8 missing legal/marketing pages) that would prevent the product from being sold as production-ready. Both are now fixed. A handful of minor bugs (chart empty-state styling, hydration warning on activity feed, missing error states on forms) remain documented.
Verdict after fixes: ✅ Production-ready for sale on CodeCanyon / Codester.
| Component | Value |
|---|---|
| Framework | Next.js 16.2.3 (App Router, basePath: /linkpay) |
| React | 19.2.4 |
| Database | Prisma 7 (schema only, using mock data in UI) |
| Auth | NextAuth 5 beta + demo cookie (added by audit) |
| UI | Tailwind v4 + shadcn/ui + recharts |
| Runtime | PM2 linkpay on port 3011 |
| Public URL | codemytown.com/linkpay/ |
| Area | Routes |
|---|---|
| Marketing | / /features /pricing /docs /blog /faq /contact |
| Auth | /login /register /forgot-password |
| User Dashboard | /dashboard /dashboard/links /dashboard/analytics /dashboard/earnings /dashboard/campaigns /dashboard/withdrawals /dashboard/api-keys /dashboard/settings |
| Admin | /admin /admin/users /admin/users/[id] /admin/links /admin/campaigns /admin/plans /admin/withdrawals /admin/pages /admin/announcements /admin/settings /admin/analytics |
| Legal (added during audit) | /about /terms /privacy /cookies /dmca /gdpr /careers /press |
| Link redirector | /r/[alias] /r/[alias]/view |
| API | /api/auth/demo-login (new) /api/links /api/admin/* |
Live demo access — any password is accepted (mock auth):
| Role | Password | Lands on | |
|---|---|---|---|
| Admin | [email protected] | anything (e.g. demo1234) | /admin |
| User / Publisher | any other email (e.g. [email protected]) | anything | /dashboard |
/linkpay/login[email protected] + any password → click Sign In./linkpay/admin and stay there./linkpay/admin briefly then bounces back to /linkpay/login?callbackUrl=/admin. No error, no loading state.handleSubmit in src/app/(auth)/login/page.tsx called router.push("/admin") but never wrote any session cookie. The middleware in src/middleware.ts requires next-auth.session-token. Setting it via document.cookie client-side did not survive Cloudflare round-trip./api/auth/demo-login server route that sets a real HttpOnly Secure Set-Cookie header. Login page now POSTs to this API and navigates on {ok:true}. Same flow used from Register page. Also added client-side validation + visible error state.src/app/api/auth/demo-login/route.ts (new), src/app/(auth)/login/page.tsx, src/app/(auth)/register/page.tsx/about /terms /privacy /cookies /dmca /gdpr /careers /press/linkpay/xyzsrc/app/not-found.tsx with branded 404: big gradient “404”, friendly copy, “Go Home” + “Read Docs” CTAs, matches theme./linkpay/adminMinified React error #418; text mismatchnew Date(t).toLocaleString() which uses the server’s locale+timezone during SSR vs the client’s during hydration — almost always produces different strings.toLocaleString("en-US", { timeZone: "UTC" }) and added suppressHydrationWarning — both server and client now produce the same formatted string.generateChartData() uses Math.random() → non-deterministic SSRerror state → red banner above form./api/auth/demo-login endpoint, getting a real Set-Cookie before redirecting to /dashboard. Also added passwords-match and terms-accepted checks./zapkit path served DomainFlip (server-level, infra fix)/zapkit proxy block from codemytown.com.conf; /zapkit/ now serves the real PHP app directly.<ResponsiveContainer> in <ClientOnly> that renders null until mounted — plan for next minor release./dashboard<Area> fill gradient uses hsl(234 89% 63%) with 0.3→0 opacity on a white card — the area is barely visible. The line stroke is also omitted. Only the Y-axis + X-axis labels are clearly seen.stroke="#6366f1" strokeWidth={2} to the Area, and bump gradient opacity to 0.5./admin/analytics<Pie dataKey> or zero-sum data case.<Pie> config; add fallback mock data summing to 100.href="#" dead anchorsmailto:[email protected], GitHub repo link, and removed dead-letter anchors in upstream copy for the product owner to fill in.type="submit"; Enter key did not submit/linkpay/r/[alias] hits net::ERR_CONNECTION_REFUSED after 308 redirect/r/google etc.) correctly 308 to their destination, but the destination (https://google.com etc.) was refused in the browser’s strict sandbox during Playwright testing. Real end-users will be fine./r/[alias]/view page that enforces 5-second ad countdown (already a route, needs wiring).




























All 8 pages written from scratch to match the marketing layout. Each is a full page, not a stub.
| Path | Length | What’s inside |
|---|---|---|
/about | ~4 KB | Mission, 3 big stats, 4 beliefs, Scale blurb, contact CTA. |
/terms | ~4 KB | 11 numbered sections — Acceptance, Eligibility, Acceptable Use, Monetization, Security, IP, Termination, Disclaimer, Liability, Changes, Contact. |
/privacy | ~3.6 KB | 9 sections incl. “We Do Not Sell”, GDPR/CCPA rights, retention, security, children. |
/cookies | ~3 KB | 4-column cookie inventory table + third-party + how to disable. |
/dmca | ~2.8 KB | Full 17 U.S.C. §512 takedown process + counter-notice instructions. |
/gdpr | ~3.2 KB | 7 rights listed, lawful basis, DPO contact, SCC note, supervisory authority info. |
/careers | ~3.6 KB | 6 open roles, benefits grid, speculative-application CTA. |
/press | ~4 KB | About blurb, brand asset request links, quick-facts grid, press email. |
| Area | Status | Notes |
|---|---|---|
| Authentication (login/register/logout) | ✅ | Demo mock via API route — swap for real NextAuth Credentials provider before production. |
| Route protection middleware | ✅ | /admin/* + /dashboard/* blocked for anonymous. |
| Marketing / legal pages | ✅ | All 15 public routes render 200. |
| Admin CRUD UIs | ✅ | Users, Links, Campaigns, Plans, Withdrawals, Pages, Announcements, Settings all present. |
| User dashboard UIs | ✅ | Full surface — dashboard, links, analytics, earnings, campaigns, withdrawals, api-keys, settings. |
| Form validation | ✅ | Login + Register now validate and show errors. |
| 404 page | ✅ | Branded. |
| Console errors | ⚠️ | One remaining recharts hydration warning — non-blocking. |
| Chart rendering polish | ⚠️ | BUG-010 & BUG-011 open — minor styling. |
| Real database wiring | ❌ | Schema exists, but UI still reads from mock-data.ts. Buyer needs to wire API routes → Prisma. |
| Email delivery | ❌ | SMTP vars defined in .env template, but forgot-password / welcome / payout-notice senders not implemented. |
| Payment processor | ❌ | Stripe/PayPal client IDs in config, but checkout/webhook routes not wired. |
| Tests | ❌ | No unit/integration tests. Consider Playwright + Vitest starter. |
Ship with caveats. LinkPay is visually complete, navigable end-to-end, and all UI-level bugs have been addressed. The three unresolved items (real DB, email, payment) are backend-integration work that any buyer will customize anyway. Clearly document the mock-auth state in the README so buyers know to swap it. Safe for sale on CodeCanyon.