A modern web-based softphone application with AI capabilities. Make and receive calls directly from your browser with automatic recording, contact management, and intelligent features. Built with Next.js, Twilio Voice SDK, and PostgreSQL.
Live at: peake.ai
- 📞 Browser-based calling - Make and receive calls directly from your web browser
- 🎙️ Call recording - Record calls with one-click consent
- 📋 Call log - View past calls with metadata, status, and recordings
- 👥 Shared contacts - Team-wide contact management with multi-field support
- 💬 SMS/MMS - Send and receive text messages (Beta)
- 🔍 AI Contact Finder - Discover contact information using AI-powered web search
- 📱 Multi-line support - Multiple phone numbers with user assignment
- 🔢 In-call keypad - DTMF tones for navigating phone menus
- 📥 Bulk import - Import contacts from CSV, TXT, or Markdown files
- 🔒 Secure authentication - Protected routes with NextAuth.js
- Frontend: Next.js 15 (App Router), React 19, Tailwind CSS
- Backend: Next.js API Routes
- Database: PostgreSQL with Prisma ORM
- Authentication: NextAuth.js v5
- Voice: Twilio Voice SDK
- AI: OpenAI GPT-4, Tavily Search API
- Deployment: Vercel
- Node.js 18+
- PostgreSQL database (Neon, Supabase, or local)
- Twilio account with:
- Account SID & Auth Token
- API Key & Secret
- TwiML App SID
- Phone number(s) for caller ID
cd aiphone
npm installCopy the example environment file and fill in your values:
cp .env.example .envRequired environment variables:
# Database
DATABASE_URL="postgresql://..."
# NextAuth
NEXTAUTH_SECRET="your-secret-key"
NEXTAUTH_URL="https://peake.ai"
# Twilio
TWILIO_ACCOUNT_SID="ACxxxxxxxx"
TWILIO_AUTH_TOKEN="your-auth-token"
TWILIO_API_KEY_SID="SKxxxxxxxx"
TWILIO_API_KEY_SECRET="your-api-secret"
TWILIO_TWIML_APP_SID="APxxxxxxxx"
TWILIO_PHONE_NUMBER="+15551234567"
# App
NEXT_PUBLIC_APP_URL="https://peake.ai"
ALLOWED_COUNTRIES="US,CA"# Generate Prisma client
npx prisma generate
# Push schema to database (for development)
npx prisma db push
# Or run migrations (for production)
npx prisma migrate dev --name init
# Seed the database with users
npm run db:seed-
Create a TwiML App in Twilio Console:
- Go to Voice > TwiML Apps
- Create new app
- Set Voice Request URL to:
https://peake.ai/api/twilio/voice - Note the TwiML App SID
-
Create API Key:
- Go to Account > API keys
- Create new Standard API key
- Note the SID and Secret
-
Configure phone numbers:
- Purchase/verify phone numbers for caller ID
- Set webhook URLs on each number
npm run devConfigure these webhook URLs in your Twilio Console:
| Webhook | URL | Method |
|---|---|---|
| Voice (TwiML App) | /api/twilio/voice |
POST |
| Status Callback | /api/twilio/status |
POST |
| Dial Status | /api/twilio/dial-status |
POST |
| Recording Callback | /api/twilio/recording |
POST |
| Voicemail | /api/twilio/voicemail |
POST |
| Incoming SMS | /api/messages/incoming |
POST |
| SMS Status | /api/messages/status |
POST |
For local development, use a tunnel like ngrok:
ngrok http 3000src/
├── app/
│ ├── (protected)/ # Auth-protected routes
│ │ ├── calls/ # Call log page
│ │ ├── contacts/ # Contact management
│ │ ├── dialer/ # Dialer dashboard
│ │ ├── find/ # AI contact finder
│ │ └── messages/ # SMS/MMS (Beta)
│ ├── api/
│ │ ├── auth/ # NextAuth endpoints
│ │ ├── calls/ # Call log API
│ │ ├── contacts/ # Contact CRUD + import
│ │ ├── find/ # AI contact discovery
│ │ ├── messages/ # SMS/MMS API
│ │ ├── phone-numbers/ # Multi-line management
│ │ ├── recordings/ # Recording streaming
│ │ └── twilio/ # Twilio webhooks
│ └── login/ # Login page
├── components/
│ ├── calls/ # Call log components
│ ├── dialer/ # Dialer + sidebar
│ ├── landing/ # Public landing page
│ ├── layout/ # Navigation
│ ├── providers/ # Twilio context provider
│ └── ui/ # Reusable UI components
├── lib/
│ ├── auth.ts # NextAuth config
│ ├── prisma.ts # Database client
│ └── twilio.ts # Twilio utilities
└── scripts/
└── seed.ts # Database seeder
- Recording URLs are proxied through your server (never exposed directly)
- Access tokens have short TTL (1 hour)
- All routes are protected with authentication
- Webhook endpoints use idempotent operations
- Contacts are shared across team members
- Recording disclosure: Users must confirm consent before recording
- Retention: Recordings are stored on Twilio (configure retention in Twilio Console)
- Country restrictions: Configurable via
ALLOWED_COUNTRIESenv var
Jesse Alton at AltonTech, Inc. / Virgent AI
Sick of overpaying for clunky VoIP services with no AI integration, we coded our own phone system. V1 was live in 60 minutes. LangChain automations followed an hour later.
Read the full story:
Proprietary - See LICENSE for details.
This software is the exclusive property of AltonTech, Inc. You may view the source code for educational purposes only. Reproduction, distribution, or commercial use is strictly prohibited.
For inquiries: virgent.ai/about/ai-call-center