ianshaloom a897089fdc feat(admin): implement admin auth & authorization system (Phases 0–6)
Complete implementation of the admin authentication and authorization
plan using a separate Clerk instance (App B) for cryptographic isolation
from the storefront.

Convex backend changes:
- auth.config.ts: dual JWT provider (storefront + admin Clerk issuers)
- http.ts: add /clerk-admin-webhook route with separate signing secret
- users.ts: role-aware upsertFromClerk (optional role arg), store reads
  publicMetadata.role from JWT, assertSuperAdmin internal query
- model/users.ts: add requireSuperAdmin helper
- adminInvitations.ts: inviteAdmin action (super_admin gated, Clerk Backend SDK)

Admin app (apps/admin):
- Route groups: (auth) for sign-in, (dashboard) for gated pages
- AdminUserSync, AdminAuthGate, AccessDenied, LoadingSkeleton components
- useAdminAuth hook with loading/authorized/denied state machine
- RequireRole component for super_admin-only UI sections
- useStoreUserEffect hook for Clerk→Convex user sync
- Sidebar shell with nav-main, nav-user, app-sidebar
- clerkMiddleware with /sign-in excluded from auth.protect
- ShadCN UI components (sidebar, dropdown, avatar, etc.)

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-03-04 16:13:07 +03:00

The Pet Loft — Ecommerce Monorepo

A full-stack ecommerce platform for pet supplies built with Next.js, Convex, Clerk, and Turborepo.

Project Structure

ecommerce/
├── apps/
│   ├── storefront/          # Customer-facing store (Next.js + HeroUI) — port 3000
│   └── admin/               # Admin dashboard (Next.js + ShadCN) — port 3001
├── convex/                  # Convex backend (schema, functions, tests)
├── packages/
│   ├── types/               # Shared TypeScript types (Product, Order, User...)
│   ├── utils/               # Shared helper functions (formatPrice, slugify...)
│   └── convex/              # Shared Convex client provider (@repo/convex)
├── docs/                    # Convex reference docs + project documentation
├── package.json             # Root workspace config
└── turbo.json               # Turborepo pipeline config

For detailed documentation, see docs/project-documentation/.

Getting Started

1. Install dependencies

npm install

2. Set up Convex

  1. Go to convex.dev and create a new project
  2. Run npx convex dev from the root — this will prompt you to log in and link your project

3. Set up Clerk

  1. Go to clerk.com and create a new application
  2. In the Clerk Dashboard, create a JWT Template named convex (do not rename it)
  3. Copy your Publishable Key, Secret Key, and the JWT Issuer URL
  4. Set CLERK_JWT_ISSUER_DOMAIN in the Convex Dashboard environment variables

4. Configure environment variables

Copy the example env files and fill in your credentials:

cp apps/storefront/.env.example apps/storefront/.env.local
cp apps/admin/.env.example apps/admin/.env.local

5. Run the development servers

# Terminal 1 — Convex backend
npx convex dev

# Terminal 2 — Both Next.js apps
npm run dev

Packages

@repo/types

All shared TypeScript types used across both apps and the Convex backend.

import type { Product, Order, User } from "@repo/types";

@repo/utils

Shared utility functions.

import { formatPrice, slugify, formatDate } from "@repo/utils";

formatPrice(1999)           // → "$19.99"
slugify("Hello World!")     // → "hello-world"

@repo/convex

Shared Convex + Clerk provider. Both apps wrap their layout with this.

import { ConvexClientProvider } from "@repo/convex";

Authentication

This project uses Clerk for authentication and Convex for the backend.

  • Clerk handles sign-in/sign-up UI and JWT tokens
  • ConvexProviderWithClerk passes the JWT to the Convex backend
  • Convex functions access the user identity via ctx.auth.getUserIdentity()
  • Admin-only functions check the role field via requireAdmin()
  • Clerk webhooks sync user changes to the Convex users table

Scripts

Script What it does
npm run dev Run both apps in parallel via Turbo
npm run dev:storefront Run only the storefront
npm run dev:admin Run only the admin
npm run build Build both apps
npm run type-check TypeScript check across all workspaces
npm run test:once Run all tests once
npm run test Run tests in watch mode

Deployment

App Recommended Platform
Storefront Vercel (root dir: apps/storefront)
Admin Vercel (root dir: apps/admin)
Backend Convex Cloud (npx convex deploy)
Description
No description provided
Readme 27 MiB
Languages
TypeScript 94%
HTML 4.8%
CSS 0.7%
JavaScript 0.5%