System Architecture
v1Four-level architecture, domain management, and Supabase project structure.
On this page
- App Factory Platform - Architecture Documentation
- π― Executive Summary
- Key Features
- ποΈ Four-Level Architecture
- π Detailed Architecture Breakdown
- Level 1: Platform Infrastructure
- Level 2: Customer Organizations
- Level 3: Customer Applications
- Level 4: End Users (Public)
- π Authentication Architecture
- Three Separate Auth Contexts
- ποΈ Database Architecture
- Single Supabase Project Strategy
- Database Organization
- Naming Convention
- Row-Level Security (RLS)
- π Domain Management System
- Custom Domain Architecture
- Domain Setup Flow
- Domain Verification
- SSL Certificate Management
- π¨ Forge CLI Architecture
- Purpose
- Core Commands
- Forge Workflow
- Forge Configuration
- π¦ Technology Stack
- Frontend
- Backend
- Infrastructure
- Payments
- Monitoring
- π Deployment Architecture
- Platform Apps (Landing, Dashboard)
- Customer Apps
- Environment Strategy
- π Data Flow Examples
- Example 1: Customer Signs Up
- Example 2: Customer Creates App
- Example 3: End User Plays Game
- π Security Considerations
- Authentication Security
- Database Security
- API Security
- Domain Security
- π Scalability Considerations
- Current Limits (Free/Pro Tier)
- Scaling Strategy
- π― Key Design Decisions
- Decision 1: Single Supabase Project
- Decision 2: Prefixed Tables for Apps
- Decision 3: Custom Domains Only
- Decision 4: Vercel Deployment
- Decision 5: Multi-Tenant Dashboard
- π οΈ Development Workflow
- Local Development
- Adding a New App Type
- π¨ Common Pitfalls & Solutions
- Pitfall 1: DNS Propagation Delays
- Pitfall 2: Supabase RLS Policy Conflicts
- Pitfall 3: Prefixed Table Name Conflicts
- Pitfall 4: Cross-Origin Auth Issues
- Pitfall 5: Large Database Schema
- π Additional Resources
- Internal Documentation
- External Resources
- π For AI Agents
- Quick Context Summary
App Factory Platform - Architecture Documentation
Version: 1.0
Last Updated: 2025-01-14
Purpose: High-level architecture guide for AI agents, developers, and stakeholders
π― Executive Summary
App Factory is a multi-tenant SaaS platform that enables customers to rapidly create, deploy, and manage web and mobile applications through a unified dashboard. The platform handles infrastructure provisioning, authentication, database management, and custom domain configuration automatically.
Key Features
- Rapid App Generation: Create apps via Forge CLI or Dashboard UI
- Custom Domain Support: Deploy apps to customer-owned domains
- Unified Authentication: Supabase-powered auth across all levels
- Multi-Tenant Architecture: Shared platform with org-level isolation
- Database Management: Prefixed tables for app data isolation
- Infrastructure as Code: Pulumi-managed cloud resources
ποΈ Four-Level Architecture
App Factory operates across four distinct levels:
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β Level 1: Platform Infrastructure β
β - Landing & Dashboard (infiniteapps.ai) β
β - Shared by all customers β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β Level 2: Customer Organizations β
β - Users sign up and create organizations β
β - All use same dashboard URL β
β - Data isolated via RLS β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β Level 3: Customer Applications β
β - Apps created via Forge CLI or Dashboard β
β - Deployed to CUSTOM DOMAINS (customer-owned) β
β - Prefixed database tables per app β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β Level 4: End Users β
β - Public users who visit customer apps β
β - Sign up on custom domains β
β - Isolated per app β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
π Detailed Architecture Breakdown
Level 1: Platform Infrastructure
Purpose: Core platform that serves all customers
Components:
-
Landing App (
landing.infiniteapps.ai)- Marketing and customer acquisition
- Stripe billing integration
- Sign-up flow
- Hosted on Vercel
-
Dashboard App (
dashboard.infiniteapps.ai)- Multi-tenant admin interface
- Organization management
- App creation and deployment UI
- Secret management
- Hosted on Vercel
Technology Stack:
- Framework: Next.js 14 (App Router)
- Authentication: Supabase Auth
- Database: Supabase PostgreSQL
- Payments: Stripe
- Hosting: Vercel
- CDN: Vercel Edge Network
Key Files:
apps/landing/- Landing page applicationapps/dashboard/- Dashboard applicationops/apps.yaml- Platform configuration
Level 2: Customer Organizations
Purpose: Multi-tenant organization management with data isolation
User Flow:
1. User visits landing.infiniteapps.ai
2. Signs up with Google/GitHub OAuth
3. Creates/joins organization
4. Accesses dashboard.infiniteapps.ai
5. All orgs use SAME dashboard URL
6. Data scoped via organization_id
Data Model:
-- Platform users (customers using the dashboard)
users
ββ id (UUID)
ββ email
ββ name
ββ created_at
-- Customer organizations
organizations
ββ id (UUID)
ββ name
ββ slug (unique)
ββ owner_id β users.id
-- Organization membership
organization_members
ββ id (UUID)
ββ user_id β users.id
ββ organization_id β organizations.id
ββ role (OWNER, ADMIN, MEMBER)
Isolation Strategy:
- Row-Level Security (RLS) policies
- All queries filtered by
organization_id - Users only see their org's data
- No cross-org data access
Example RLS Policy:
CREATE POLICY "Users see own org data"
ON apps FOR SELECT
USING (organization_id = (
SELECT organization_id
FROM organization_members
WHERE user_id = auth.uid()
));
Level 3: Customer Applications
Purpose: Apps created and deployed by customers
Critical Distinction: Apps deploy to CUSTOMER-OWNED DOMAINS, not platform domains!
Examples:
- β
User A's game:
memory-game.acmegames.com(User A's domain) - β
User B's blog:
blog.betacompany.io(User B's domain) - β
Platform owner:
app.infiniteapps.ai(platform owner's domain) - β NO customer apps on
infiniteapps.ai(except platform owner)
App Creation Flow:
1. User logs into dashboard.infiniteapps.ai
2. Clicks "Create New App"
3. Selects a template from the gallery (backed by `ops/apps.yaml`)
4. Confirms name, platforms, and IDs prefilled from the template
5. Forge queues a provisioning job (Supabase, code scaffolding, env bundles)
6. Domain configuration is handled afterwards from the app workspace (βDomainsβ tab)
7. Platform verifies DNS and issues SSL cert
8. Forge generates and deploys app code
9. App goes live at the customerβs domain
Data Model:
-- Apps registry
apps
ββ id (UUID)
ββ organization_id β organizations.id
ββ name
ββ slug
ββ custom_domain (e.g., "acmegames.com")
ββ subdomain (e.g., "memory-game")
ββ full_domain (e.g., "memory-game.acmegames.com")
ββ dns_configured (boolean)
ββ ssl_certificate_issued (boolean)
ββ created_at
-- Domain verification
domain_verifications
ββ id (UUID)
ββ app_id β apps.id
ββ domain
ββ verification_token
ββ verified_at
ββ created_at
Database Table Strategy: Prefixed Tables
Each app gets its own prefixed tables:
-- User A's memory game
CREATE TABLE memory_game_saves (
id UUID PRIMARY KEY,
user_id UUID REFERENCES app_users(id),
level INTEGER,
score INTEGER,
created_at TIMESTAMPTZ
);
CREATE TABLE memory_game_leaderboards (
id UUID PRIMARY KEY,
user_id UUID REFERENCES app_users(id),
score INTEGER,
rank INTEGER,
created_at TIMESTAMPTZ
);
-- User B's blog
CREATE TABLE myblog_posts (
id UUID PRIMARY KEY,
author_id UUID REFERENCES app_users(id),
title TEXT,
content TEXT,
published BOOLEAN,
created_at TIMESTAMPTZ
);
CREATE TABLE myblog_comments (
id UUID PRIMARY KEY,
post_id UUID REFERENCES myblog_posts(id),
author_id UUID REFERENCES app_users(id),
content TEXT,
created_at TIMESTAMPTZ
);
Why Prefixed Tables?
- β Complete isolation per app
- β Easy to export/migrate apps
- β No accidental cross-app queries
- β Simpler to drop an app (just drop its tables)
- β App-specific indexing and optimization
Level 4: End Users (Public)
Purpose: Public users who interact with customer applications
Key Distinction: End users are NOT platform customers. They are users of the apps created by platform customers.
User Flow:
1. End user visits customer's domain (e.g., memory-game.acmegames.com)
2. Signs up with email or OAuth (on THAT domain)
3. Uses the app (plays game, reads blog, etc.)
4. Data stored in app-specific tables
5. Cannot access other apps or platform dashboard
Data Model:
-- End users (NOT platform users)
app_users
ββ id (UUID)
ββ email
ββ display_name
ββ avatar_url
ββ created_at
-- App-specific data references app_users
-- (see prefixed tables above)
Isolation:
- Each app's users stored in shared
app_userstable - App data stored in prefixed tables (e.g.,
memory_game_saves) - No cross-app data access via table separation
- RLS policies optional (already isolated by table prefix)
π Authentication Architecture
Three Separate Auth Contexts
1. Platform Authentication (Levels 1-2)
- Domain:
landing.infiniteapps.ai,dashboard.infiniteapps.ai - Provider: Supabase Auth
- Users: Platform customers (organization owners/members)
- OAuth: Google, GitHub
- Session: Stored in Supabase, shared across landing/dashboard
2. App User Authentication (Levels 3-4)
- Domain: Customer domains (e.g.,
memory-game.acmegames.com) - Provider: Supabase Auth (same project, different context)
- Users: End users (public)
- OAuth: Configurable per app
- Session: Scoped to app domain
3. Authentication Flow:
// Platform auth (Dashboard/Landing)
import { createServerSupabaseClient } from '@/lib/supabase/server';
async function getCurrentUser() {
const supabase = createServerSupabaseClient();
const { data: { user } } = await supabase.auth.getUser();
// Returns platform user (customer)
return user;
}
// App auth (Customer's app)
import { createClient } from '@supabase/supabase-js';
async function getAppUser() {
const supabase = createClient(url, anonKey);
const { data: { user } } = await supabase.auth.getUser();
// Returns app user (end user)
return user;
}
ποΈ Database Architecture
Single Supabase Project Strategy
Decision: ONE Supabase project for entire platform
Rationale:
- Cost-effective ($25/month vs $25/customer/month)
- Simplified management
- Shared authentication
- Cross-platform analytics
- Easy RLS implementation
Database Organization
Platform Supabase Project
ββ Platform Tables
β ββ users (platform customers)
β ββ organizations
β ββ organization_members
β ββ apps (registry)
β ββ domain_verifications
β
ββ Shared Tables
β ββ app_users (all end users)
β
ββ App-Specific Tables (Prefixed)
ββ memory_game_saves
ββ memory_game_leaderboards
ββ myblog_posts
ββ myblog_comments
ββ [app_name]_[table_name]
Naming Convention
Platform tables: No prefix (users, organizations, apps)
Shared tables: No prefix (app_users)
App tables: {sanitized_app_slug}_{table_name}
Examples:
- memory_game_saves
- awesome_blog_posts
- my_store_products
Row-Level Security (RLS)
Platform Tables:
-- Users only see their org's apps
CREATE POLICY "org_isolation" ON apps
FOR SELECT USING (
organization_id IN (
SELECT organization_id
FROM organization_members
WHERE user_id = auth.uid()
)
);
App Tables:
-- App users only see their own data
CREATE POLICY "user_owns_data" ON memory_game_saves
FOR ALL USING (user_id = auth.uid());
-- Anyone can view leaderboards
CREATE POLICY "public_leaderboard" ON memory_game_leaderboards
FOR SELECT USING (true);
π Domain Management System
Custom Domain Architecture
Infrastructure Setup:
Customer's Domain (acmegames.com)
ββ DNS CNAME: memory-game β apps.infiniteapps.ai
Platform Load Balancer (apps.infiniteapps.ai)
ββ SSL Termination (Let's Encrypt/AWS ACM)
ββ Host Header Routing
ββ Routes to App Deployment
App Deployment
ββ Vercel/Netlify (recommended)
ββ Custom domain configured per app
Domain Setup Flow
1. User provides domain in dashboard
β
2. Platform generates DNS instructions
- Type: CNAME
- Name: [subdomain]
- Value: apps.infiniteapps.ai
β
3. User configures DNS at registrar
β
4. Platform verifies DNS propagation
- Polls DNS every 30s
- Timeout after 30 minutes
β
5. Platform issues SSL certificate
- Via Let's Encrypt (automatic)
- Or AWS Certificate Manager
β
6. App deployed to custom domain
- Vercel: Add domain via API
- AWS: Update CloudFront distribution
β
7. App goes live!
Domain Verification
async function verifyDomain(appId: string, domain: string): Promise<boolean> {
// 1. Generate verification token
const token = crypto.randomUUID();
await saveDomainVerification(appId, domain, token);
// 2. Check DNS resolution
const dns = require('dns').promises;
const records = await dns.resolveCname(domain);
// 3. Verify CNAME points to platform
if (records.includes('apps.infiniteapps.ai')) {
await markDomainVerified(appId, domain);
return true;
}
return false;
}
SSL Certificate Management
Option A: Let's Encrypt (Self-Managed)
# Automated via certbot
certbot certonly --dns-cloudflare \
--dns-cloudflare-credentials /etc/letsencrypt/cloudflare.ini \
-d memory-game.acmegames.com
Option B: AWS Certificate Manager (Recommended)
import { ACM } from '@aws-sdk/client-acm';
async function requestCertificate(domain: string) {
const acm = new ACM({ region: 'us-east-1' });
const result = await acm.requestCertificate({
DomainName: domain,
ValidationMethod: 'DNS',
});
return result.CertificateArn;
}
Option C: Vercel/Netlify (Easiest)
// Vercel handles SSL automatically
await vercel.domains.add(projectId, domain);
π¨ Forge CLI Architecture
Purpose
Command-line tool for app generation, deployment, and management
Core Commands
# Create new app
forge create <app-name> [options]
--type <game|blog|ecommerce|custom>
--domain <custom-domain>
--subdomain <subdomain>
--supabase <platform|new|existing>
--table-strategy <prefixed|app_id>
# Examples
forge create memory-game \
--type game \
--domain acmegames.com \
--subdomain memory-game \
--supabase platform \
--table-strategy prefixed
# Deploy app
forge deploy [app-name]
--environment <dev|staging|prod>
# Manage domains
forge domain add <domain>
forge domain verify <domain>
forge domain remove <domain>
# Database operations
forge db migrate <app-name>
forge db seed <app-name>
forge db reset <app-name>
Forge Workflow
forge create memory-game
β
1. Validate inputs
- Check app name availability
- Validate domain format
- Check org permissions
β
2. Create app record in platform DB
- Insert into apps table
- Generate app_id
β
3. Generate app code
- Clone template (Next.js + Supabase)
- Configure environment variables
- Set up database schema (prefixed tables)
β
4. Initialize database
- Create prefixed tables
- Apply RLS policies
- Seed initial data
β
5. Deploy app
- Push to Git
- Trigger Vercel deployment
- Configure custom domain
β
6. Verify deployment
- Check app health
- Verify SSL certificate
- Test DNS resolution
β
7. Done! π
Forge Configuration
// forge.config.ts (per app)
export default {
app: {
name: 'memory-match-game',
type: 'game',
slug: 'memory-match-game',
},
domain: {
custom: 'acmegames.com',
subdomain: 'memory-game',
full: 'memory-game.acmegames.com',
},
database: {
provider: 'supabase',
strategy: 'prefixed',
tablePrefix: 'memory_game_',
},
deployment: {
platform: 'vercel',
region: 'us-east-1',
environment: 'production',
},
};
π¦ Technology Stack
Frontend
- Framework: Next.js 14 (App Router)
- Language: TypeScript
- UI Library: React 18
- Styling: Tailwind CSS
- Components: Radix UI / shadcn/ui
- State Management: React Context / Zustand
Backend
- API: Next.js API Routes
- Database: Supabase (PostgreSQL)
- Authentication: Supabase Auth
- ORM: Prisma (for Dashboard/Landing)
- Real-time: Supabase Realtime
Infrastructure
- Hosting: Vercel (Landing, Dashboard, Customer Apps)
- CDN: Vercel Edge Network / CloudFront
- DNS: Cloudflare / Route53
- IaC: Pulumi (TypeScript)
- Secrets: Doppler
Payments
- Provider: Stripe
- Products: Subscription-based pricing
- Webhooks: Stripe webhooks for billing events
Monitoring
- Analytics: Vercel Analytics / Mixpanel
- Errors: Sentry
- Logs: Vercel Logs / CloudWatch
- Uptime: Better Uptime / Checkly
π Deployment Architecture
Platform Apps (Landing, Dashboard)
GitHub Repository
β
Vercel Integration (Auto-deploy)
β
Vercel Edge Network
ββ landing.infiniteapps.ai
ββ dashboard.infiniteapps.ai
Customer Apps
Forge CLI
β
Generate App Code
β
Push to Git (Customer repo or Platform repo)
β
Vercel/Netlify Deployment
ββ Auto-deploy on push
ββ Custom domain configuration
ββ SSL certificate issuance
β
Custom Domain (e.g., memory-game.acmegames.com)
Environment Strategy
Development
ββ Local: localhost:3000
ββ DB: Local Supabase / Dev branch
ββ Branch: feature/*
Staging
ββ URL: staging-*.infiniteapps.ai
ββ DB: Staging Supabase project
ββ Branch: staging
Production
ββ URL: infiniteapps.ai (platform)
β customer-domains.com (apps)
ββ DB: Production Supabase project
ββ Branch: main
π Data Flow Examples
Example 1: Customer Signs Up
1. User visits landing.infiniteapps.ai
2. Clicks "Sign Up with Google"
3. Redirected to Supabase Auth (Google OAuth)
4. User authorizes
5. Redirected back with auth code
6. Supabase creates user record
7. Landing creates organization record
8. Redirected to dashboard.infiniteapps.ai
9. User sees empty dashboard (no apps yet)
Example 2: Customer Creates App
1. User in dashboard clicks "Create App"
2. Fills form:
- Name: Memory Match Game
- Type: Web Game
- Domain: acmegames.com
- Subdomain: memory-game
3. Submits form
4. Dashboard calls API: POST /api/apps
5. API validates inputs
6. API creates app record in Supabase
7. API triggers Forge CLI (via job queue)
8. Forge generates app code
9. Forge creates prefixed DB tables
10. Forge deploys to Vercel
11. Forge configures custom domain
12. Forge waits for DNS verification
13. Domain verified β SSL issued
14. App goes live!
15. User sees "App Created" confirmation
Example 3: End User Plays Game
1. End user visits memory-game.acmegames.com
2. App loads from Vercel CDN
3. User sees "Sign Up" button
4. User signs up with email
5. Supabase Auth creates app_user record
6. User redirected to game
7. User plays and scores 100 points
8. App saves to memory_game_saves table
9. App updates memory_game_leaderboards table
10. User sees updated leaderboard
π Security Considerations
Authentication Security
- OAuth 2.0 with Google/GitHub
- Secure cookie-based sessions
- CSRF protection via Supabase
- HTTP-only cookies
- SameSite=Lax policy
Database Security
- Row-Level Security (RLS) enabled
- Prepared statements (Prisma)
- Connection pooling
- Encrypted at rest (Supabase)
- Encrypted in transit (TLS)
API Security
- Rate limiting (Vercel)
- CORS configuration
- Input validation (Zod)
- Environment variable encryption (Doppler)
- API key authentication (for Forge CLI)
Domain Security
- DNS verification required
- SSL/TLS enforced
- HSTS headers
- Content Security Policy
- XSS protection headers
π Scalability Considerations
Current Limits (Free/Pro Tier)
- Supabase: 500MB DB / 8GB Pro
- Vercel: 100GB bandwidth / Unlimited Pro
- Users: No hard limit (RLS scales)
- Apps: No hard limit (prefixed tables scale)
Scaling Strategy
Phase 1: Single Supabase Project (Current)
- Handles: 100-1000 customers
- Cost: $25-100/month
- Bottleneck: Database size
Phase 2: Read Replicas
- Handles: 1000-10,000 customers
- Cost: $100-500/month
- Bottleneck: Write throughput
Phase 3: Database Sharding
- Handles: 10,000+ customers
- Cost: $500-2000/month
- Shard by: organization_id or app_id
Phase 4: Multi-Region
- Handles: Global scale
- Cost: Variable
- Regions: US, EU, Asia
π― Key Design Decisions
Decision 1: Single Supabase Project
Why: Cost-effective for MVP, easier management
Trade-off: Shared resources, need RLS
Alternative: Supabase project per customer (expensive)
Decision 2: Prefixed Tables for Apps
Why: Complete isolation, easy to export apps
Trade-off: Schema "explosion" with many apps
Alternative: Shared tables with app_id column
Decision 3: Custom Domains Only
Why: Professional, allows white-labeling
Trade-off: Complex DNS/SSL management
Alternative: Subdomains on platform (simpler but less flexible)
Decision 4: Vercel Deployment
Why: Automatic SSL, global CDN, easy integration
Trade-off: Vendor lock-in
Alternative: AWS (more control, more complexity)
Decision 5: Multi-Tenant Dashboard
Why: Standard SaaS pattern, cost-effective
Trade-off: Limited white-labeling
Alternative: Dashboard instance per customer (expensive)
π οΈ Development Workflow
Local Development
# Clone repository
git clone https://github.com/yourusername/app-factory
cd app-factory
# Install dependencies
pnpm install
# Setup environment variables
cp .env.example .env.local
# Edit .env.local with your Supabase credentials
# Run landing page
cd apps/landing
pnpm dev
# Visit http://localhost:3000
# Run dashboard (in new terminal)
cd apps/dashboard
pnpm dev
# Visit http://localhost:3001
# Run Supabase locally (optional)
npx supabase start
Adding a New App Type
// 1. Add to Forge templates
// packages/forge/templates/[app-type]/
// 2. Update Forge CLI
// packages/forge/src/commands/create.ts
// 3. Add to Dashboard UI
// apps/dashboard/src/components/AppTypeSelector.tsx
// 4. Define database schema
// apps/dashboard/prisma/migrations/[timestamp]_add_[app_type].sql
// 5. Test end-to-end
forge create test-app --type [app-type]
π¨ Common Pitfalls & Solutions
Pitfall 1: DNS Propagation Delays
Problem: Custom domains take 5-30 minutes to propagate
Solution: Implement polling with progress indicator, timeout after 30min
Pitfall 2: Supabase RLS Policy Conflicts
Problem: Overlapping policies can cause unexpected access denials
Solution: Test policies thoroughly, use explicit naming conventions
Pitfall 3: Prefixed Table Name Conflicts
Problem: Two apps with similar names create conflicting table names
Solution: Sanitize app names, append UUID if needed
Pitfall 4: Cross-Origin Auth Issues
Problem: Auth sessions don't work across different domains
Solution: Use Supabase's cookie-based auth, proper CORS configuration
Pitfall 5: Large Database Schema
Problem: 100+ apps = 500+ tables (slow schema operations)
Solution: Consider table partitioning or migration to app_id strategy
π Additional Resources
Internal Documentation
/docs/API.md- API reference/docs/FORGE_CLI.md- Forge CLI guide/docs/DEPLOYMENT.md- Deployment guide/docs/SUPABASE_SETUP.md- Supabase configuration
External Resources
π For AI Agents
Quick Context Summary
What is this platform?
Multi-tenant SaaS for rapid app creation and deployment with custom domains.
Who are the users?
- Level 1-2: Platform customers (organizations) using the dashboard
- Level 3-4: End users visiting customer-created apps
How does data flow?
Platform Supabase (shared) β Organizations (isolated via RLS) β Apps (isolated via prefixed tables) β App Users (isolated via app tables)
What's unique?
- Customers deploy apps to THEIR domains, not platform domain
- Single Supabase project with prefixed tables per app
- Complete isolation via table naming, not just RLS
Key files to understand:
docs/ARCHITECTURE.md(this file)apps/landing/- Landing pageapps/dashboard/- Multi-tenant dashboardops/apps.yaml- Platform configurationinfra/pulumi-supabase/- Supabase infrastructure
End of Architecture Documentation
This is a living document. Update as architecture evolves.