Spaces:
Runtime error
Runtime error
docs: Introduce comprehensive technical documentation and update planning artifacts to reflect MVP completion and detailed FR implementation status.
d03d74d Vault - Development Guide
Generated: 2026-02-11
Node.js: 20+
Package Manager: npm
Quick Start
Prerequisites
- Node.js 20+ installed
- npm or yarn package manager
- Supabase account (for database)
- Google Cloud project (for OAuth + YouTube API)
- Inngest account (for background jobs)
- Upstash account (for Redis caching)
Installation
# Clone the repository
git clone <repository-url>
cd vault
# Install dependencies
npm install
# Copy environment variables
cp .env.example .env.local
# Edit .env.local with your credentials
Development Server
# Start Next.js development server with Turbopack
npm run dev
# In a separate terminal, start Inngest dev server
npx inngest-cli dev
# Open http://localhost:3000
Environment Variables
Required Variables
# Database (Supabase Postgres)
DATABASE_URL=postgresql://...@aws-0-us-east-1.pooler.supabase.com:6543/postgres
DIRECT_URL=postgresql://...@aws-0-us-east-1.pooler.supabase.com:5432/postgres
# Authentication
BETTER_AUTH_SECRET=your-secret-key-min-32-chars
BETTER_AUTH_URL=http://localhost:3000
GOOGLE_CLIENT_ID=your-google-client-id
GOOGLE_CLIENT_SECRET=your-google-client-secret
# Inngest
INNGEST_EVENT_KEY=your-event-key
INNGEST_SIGNING_KEY=your-signing-key
# Supabase Storage
NEXT_PUBLIC_SUPABASE_URL=https://your-project.supabase.co
NEXT_PUBLIC_SUPABASE_ANON_KEY=your-anon-key
# Redis (Upstash)
UPSTASH_REDIS_REST_URL=https://your-redis.upstash.io
UPSTASH_REDIS_REST_TOKEN=your-token
# AI Vision
GEMINI_API_KEY=your-gemini-api-key
HUGGINGFACE_API_KEY=your-hf-api-key
VISION_PROVIDER=gemini # or 'huggingface'
# Marketplaces
AMAZON_ACCESS_KEY=your-amazon-access-key
AMAZON_SECRET_KEY=your-amazon-secret-key
AMAZON_AFFILIATE_TAG=your-affiliate-tag
EBAY_APP_ID=your-ebay-app-id
EBAY_CERT_ID=your-ebay-cert-id
EBAY_CAMPAIGN_ID=your-campaign-id
ETSY_API_KEY=your-etsy-api-key
# Monitoring
SENTRY_ORG=your-sentry-org
SENTRY_PROJECT=your-sentry-project
# Admin
ADMIN_EMAILS=admin@example.com,admin2@example.com
Optional Variables
# CI/CD
CI=false # Set to true in CI environments
# Development
NODE_ENV=development
Database Setup
Drizzle ORM
Database schema is defined in src/lib/db/schema.ts.
Migrations
# Generate migration from schema changes
npx drizzle-kit generate
# Run migrations
npx drizzle-kit migrate
# Push schema directly (development)
npx drizzle-kit push
# Open Drizzle Studio
npx drizzle-kit studio
Supabase Setup
- Create a new Supabase project
- Get connection strings from Project Settings > Database
- Create storage bucket named
detected-objectsfor thumbnails - Run migrations against the database
Testing
Test Framework
Vitest with React Testing Library.
# Run all tests
npm run test
# Run tests in watch mode
npx vitest
# Run tests with coverage
npx vitest --coverage
Test Structure
Tests are co-located with source files:
src/
βββ features/
β βββ vault/
β βββ services/
β β βββ vault.service.ts
β β βββ __tests__/
β β βββ vault.service.test.ts
β βββ components/
β βββ __tests__/
β βββ vault-grid.test.tsx
Writing Tests
// Service test example
import { describe, it, expect, vi } from 'vitest';
import { VaultService } from '../vault.service';
describe('VaultService', () => {
it('should return vault for valid creator slug', async () => {
const vault = await VaultService.getCreatorVault('test-creator');
expect(vault).toBeDefined();
expect(vault?.channel.channelName).toBe('Test Creator');
});
});
// Component test example
import { render, screen } from '@testing-library/react';
import { describe, it, expect } from 'vitest';
import { ProductCard } from '../product-card';
describe('ProductCard', () => {
it('should render product name', () => {
render(<ProductCard {...mockProps} />);
expect(screen.getByText('Test Product')).toBeInTheDocument();
});
});
Code Quality
Linting
ESLint with Next.js recommended config.
# Run linter
npm run lint
# Fix linting issues
npm run lint -- --fix
Pre-commit Hooks
Husky runs lint-staged on commit:
{
"lint-staged": {
"*.{js,jsx,ts,tsx,mjs}": [
"eslint --fix"
]
}
}
TypeScript
Strict mode enabled. Build will fail on type errors (configurable).
# Type check
npx tsc --noEmit
Deployment
Architecture
- Frontend: Vercel (Edge/Serverless)
- Background Workers: Railway (Docker containers)
- Database: Supabase (Managed Postgres)
- Cache: Upstash Redis
- Workflows: Inngest Cloud
Vercel Deployment
- Connect repository to Vercel
- Configure environment variables
- Deploy on push to main
# Manual deployment
npx vercel deploy --prod
Railway Deployment
- Connect repository to Railway
- Configure environment variables
- Set up Inngest worker service
# Manual deployment
npx @railway/cli up --detach --project <project-id>
CI/CD Pipeline
GitHub Actions workflow: .github/workflows/deploy.yml
Build & Test Job:
- Runs on every push and PR
- Installs dependencies
- Runs lint
- Runs tests
- Builds application
Deploy Job:
- Runs on push to main
- Deploys to Vercel
- Deploys to Railway
Development Workflow
Branch Strategy
main
βββ develop
β βββ feature/xyz
β βββ fix/abc
β βββ refactor/def
Commit Convention
type(scope): description
Types: feat, fix, refactor, docs, test, chore
Pull Request Process
- Create feature branch from
develop - Make changes and write tests
- Run lint and tests locally
- Create PR to
develop - CI must pass before merge
- Squash merge to
develop - Periodic releases from
developtomain
Debugging
Local Debugging
// Console logging with context
console.log('[VaultService] Fetching vault for slug:', creatorSlug);
// Sentry capture for investigation
Sentry.captureException(error, {
tags: { component: 'VaultGrid', action: 'fetch' },
extra: { creatorSlug },
});
Inngest Debugging
- Open Inngest Dev Server UI at
http://localhost:8288 - View function runs, events, and errors
- Replay failed functions
- Inspect step outputs
Database Debugging
# Open Drizzle Studio
npx drizzle-kit studio
# Direct SQL query
psql $DATABASE_URL -c "SELECT * FROM detected_objects LIMIT 10;"
Common Tasks
Add a New Feature Module
- Create directory in
src/features/ - Add subdirectories:
actions/,components/,services/,types/ - Create server actions with
'use server' - Create components with
'use client'where needed - Add types in
types/ - Write tests in
__tests__/
Add a New Inngest Function
- Create file in
src/inngest/functions/ - Define event interface
- Create function with
inngest.createFunction() - Register in
src/app/api/inngest/route.ts - Trigger from server action or other function
Add a New API Route
- Create directory in
src/app/api/ - Create
route.tsfile - Export HTTP method handlers (GET, POST, etc.)
- Add authentication/authorization as needed
Add a New Page
- Create directory in
src/app/ - Create
page.tsxfile - For dynamic routes, use
[param]/page.tsx - Add metadata export for SEO
- Use SSR for public pages, client components for dashboards
Troubleshooting
Common Issues
Database Connection Errors
- Verify DATABASE_URL and DIRECT_URL are correct
- Check Supabase project is not paused
- Ensure SSL is required (
ssl: 'require')
Inngest Functions Not Running
- Verify INNGEST_EVENT_KEY and INNGEST_SIGNING_KEY
- Check Inngest dev server is running locally
- Verify function is registered in API route
YouTube API Quota Exceeded
- Check Google Cloud Console for quota usage
- Request quota increase if needed
- Implement caching to reduce API calls
Marketplace API Rate Limits
- Check Redis cache is working
- Implement backoff strategies
- Consider upgrading API tiers
Getting Help
- Check existing documentation
- Search GitHub issues
- Review Inngest dashboard for errors
- Check Sentry for error details
Related Documentation
- Project Overview - Architecture and features
- Source Tree - File structure
- Data Models - Database schema
- API Contracts - Endpoints and actions
- Inngest Workflows - Background jobs