Automate lead qualification, website verification, and WhatsApp outreach at scale
- Overview
- Core Features
- Architecture
- Technology Stack
- Phase 1: Foundation β
- Phase 2: Multi-Tenant SaaS β
- Phase 3: WhatsApp Integration π
- Getting Started
- Security & Compliance
- Roadmap
LeadFlux is a production-ready, multi-tenant SaaS platform designed to help businesses:
- Import leads from Excel/CSV files with intelligent column mapping
- Verify websites automatically to qualify leads based on online presence
- Send targeted WhatsApp messages via the onhandi.com gateway
- Track campaigns with real-time analytics and isolated user workspaces
Built for marketing agencies, sales teams, and entrepreneurs who need to:
- β Qualify leads at scale without manual research
- β Personalize outreach based on website status
- β Maintain data isolation between clients/teams
- β Scale messaging while avoiding WhatsApp bans
- Smart Excel/CSV Import: Auto-detect columns (Name, Phone, Website)
- Website Verification Engine:
- Tests HTTP/HTTPS endpoints
- Handles Facebook URLs, redirects, and edge cases
- Returns detailed status:
WORKING,NOT_WORKING,NO_WEBSITE,ERROR
- Live Progress Tracking: Modal with progress bar during bulk verification
- Verification Results Dashboard: Filterable table with targeting recommendations
- Complete Data Isolation: Every query scoped to
user_id - Per-User Workspaces: Custom names, slugs, timezones, branding
- Subscription System: Free/Starter/Pro/Enterprise plans with feature limits
- Tenant Settings: Per-user WhatsApp credentials, daily limits, working hours
- Admin Tools: Database management, migration runner, SQL executor (with safety confirmations)
- Modern Responsive UI: Bootstrap 5, custom CSS, mobile-optimized
- Real-Time Notifications: Toast system for actions, alerts, and system updates
- Profile Management: Update info, change password, manage preferences
- Onboarding Flow: 3-step workspace setup with timezone and use-case selection
- Authentication: Email/password login with OTP phone verification
- CSRF Protection: Token validation on all state-changing requests
- Role-Based Access: Admin vs. regular user permissions
- Error Handling: Graceful failures with user-friendly messages
- Logging: Comprehensive activity logs for audit trails
/home3/nyumban9/app.onhandi.com/
β
βββ app/
β βββ Controllers/
β β βββ AuthController.php (handles login, register, OTP via middleware)
β β βββ DashboardController.php
β β βββ WhatsAppController.php
β β βββ LeadController.php
β β βββ CampaignController.php
β β βββ ContactController.php
β β βββ HistoryController.php
β β βββ SettingsController.php
β β βββ ProfileController.php
β β βββ DatabaseController.php
β β βββ CronController.php
β β βββ NotificationController.php
β β βββ DatabaseToolsController.php
β β βββ OnboardingController.php
β β βββ PromoteController.php
β β βββ TroubleshootController.php
β β
β βββ Middleware/
β β βββ Auth.php (authentication middleware)
β β βββ Tenant.php (multi-tenant middleware)
β β
β βββ Models/
β β βββ Lead.php
β β βββ Campaign.php
β β βββ Contact.php
β β βββ Log.php
β β
β βββ Services/
β β βββ WhatsAppGateway.php
β β βββ LeadProcessor.php
β β βββ MessageTemplates.php
β β βββ Campaign.php
β β βββ ExportService.php
β β βββ WebsiteVerifier.php
β β
β βββ Views/
β β βββ layouts/
β β β βββ main.php (main dashboard layout)
β β β βββ auth.php (login/register/OTP layout)
β β β
β β βββ dashboard/
β β β βββ content.php (main dashboard content with WhatsApp)
β β β
β β βββ auth/
β β β βββ login.php
β β β βββ register.php (if exists, or handled by middleware)
β β β βββ verify-otp.php
β β β
β β βββ onboarding/
β β β βββ index.php
β β β
β β βββ marketing/
β β β βββ verify.php (import & verify leads)
β β β βββ campaigns.php
β β β βββ contacts.php
β β β
β β βββ settings/
β β β βββ index.php
β β β
β β βββ profile/
β β β βββ index.php
β β β
β β βββ history/
β β β βββ index.php
β β β
β β βββ admin/
β β β βββ database-tools.php
β β β
β β βββ whatsapp/
β β βββ sessions.php (if separate page exists)
β β
β βββ Core/
β βββ Controller.php (base controller with tenant methods)
β βββ Router.php
β βββ Database.php
β βββ Logger.php
β
βββ public/
β βββ index.php (main entry point with .env loader)
β βββ .htaccess
β βββ assets/ (CSS, JS, images)
β
βββ storage/
β βββ logs/
β β βββ app.log
β βββ cache/
β β βββ whatsapp/
β βββ exports/
β
βββ .env (environment variables)
βββ vendor/
βββ composer.json
User Uploads Excel
β
LeadController::processMapped()
β
WebsiteVerifier::checkDetailed() β HTTP/HTTPS requests
β
Results saved to `leads` table (scoped to user_id)
β
Dashboard displays user's isolated data
β
[Phase 3] WhatsAppGateway sends messages via onhandi.com API
π₯ Qualified Leads (88 imported)
β
ββπ± STEP 1: WhatsApp Number Verification
β ββ POST to https://tools.onhandi.com/api/number-checker/check
β ββ Batch up to 100 numbers per API call
β ββ Cache results for 24h to avoid redundant checks
β ββ ONLY proceed if response: {"isValid": true}
β
ββπ¨ STEP 2: Send Personalized Messages (Anti-Ban Protected)
β ββ IF website WORKING β
β β "Hi {name}, noticed your site is live! We offer maintenance, SEO, social media management. Interested?"
β ββ IF website MISSING/NOT_WORKING β
β β "Hi {name}, saw your business could use a professional website. We design affordable, mobile-friendly sites. Free consultation?"
β ββ Anti-ban logic:
β β β’ Random delay: sleep(rand(5,15)) between each message
β β β’ Batch cooldown: sleep(rand(120,300)) after every 15 messages
β β β’ Daily limits: 30/day (new number) / 70/day (warmed) tracked in DB
β β β’ Working hours: Only send 09:00-18:00 Africa/Nairobi
β β β’ Message rotation: Cycle 3-5 templates randomly
β ββ POST to https://tools.onhandi.com/api/sessions/{sessionId}/send
β
ββπ STEP 3: Log & Track
β ββ Log every action: WHATSAPP_CHECKED β MESSAGE_SENT/FAILED
β ββ Store messageId for delivery tracking
β ββ Dashboard shows real-time progress via AJAX
β
ββποΈ STEP 4: Dashboard Controls
ββ WhatsApp session status indicator (π’ Connected / π΄ Disconnected)
ββ "Send Test Message" button for manual triggers
ββ Live send progress with success/fail counters
ββ Anti-ban status panel: "Today: X/30 sent β’ Next allowed: HH:MM"
β
app/Messaging/WhatsAppGateway.php
- Full onhandi.com API client (number checker + message sender)
- Batch processing (100 numbers max per call)
- 24h result caching to avoid redundant API calls
- Error handling with retries
β
app/Services/LeadProcessor.php
- Complete workflow: Verify β Qualify β Check WhatsApp β Send
- Anti-ban logic:
β’ Random delay: sleep(rand(5,15)) between messages
β’ Batch cooldown: sleep(rand(120,300)) every 15 messages
β’ Daily limits: 30/day (new) / 70/day (warmed) tracked in DB
β’ Working hours: Only send 09:00-18:00 Africa/Nairobi
- Message rotation: Cycle 3-5 templates randomly via MessageRotator
β
app/Controllers/WhatsAppController.php
- AJAX endpoints: /api/whatsapp/status, /api/whatsapp/send-test
- Real-time progress updates for dashboard
- Session management for onhandi.com gateway
β
Updated Dashboard UI
- WhatsApp session status indicator (π’ Connected / π΄ Disconnected)
- "Send Test Message" button for qualified leads
- Live send progress with success/fail counters
- Anti-ban status panel (today's count, next allowed send time)
β
Message Templates (Your Business Logic)
β’ IF website WORKING β
"Hi {name}, noticed your site is live! We offer maintenance, SEO, social media management. Interested?"
β’ IF website MISSING/NOT_WORKING β
"Hi {name}, saw your business could use a professional website. We design affordable, mobile-friendly sites. Free consultation?"
Great! the exact file structure and complete code for your Lead flux API system. π Complete File Structure
app.onhandi.com/
βββ app/
β βββ Controllers/
β β βββ Api/
β β β βββ ApiController.php β Base API controller
β β β βββ LeadsController.php β Leads endpoints
β β β βββ NumbersController.php β Number verification
β β β βββ CampaignsController.php β Campaign management
β β β βββ WhatsAppController.php β WhatsApp messaging
β β β βββ ApiKeysController.php β API key management
β β βββ ... (existing controllers)
β β
β βββ Middleware/
β β βββ ApiAuth.php β API authentication
β β βββ ... (existing middleware)
β β
β βββ Services/
β β βββ ApiRateLimiter.php β Rate limiting service
β β βββ ... (existing services)
β β
β βββ Views/
β βββ api/
β βββ documentation.php β API docs page
β βββ keys.php β API key management UI
β
βββ public/
β βββ api/
β βββ docs.php β Public API documentation
β
βββ storage/
βββ logs/
βββ api.log β API usage logs
- π Campaign Creation Wizard Step-by-step flow:
[Step 1: Basics]
ββ Campaign Name (required)
ββ Description (optional)
ββ Campaign Type:
β ββ One-time broadcast
β ββ Scheduled campaign
β ββ Recurring (daily/weekly)
ββ Tags/Labels for organization
[Step 2: Recipients]
ββ Select Source:
β ββ All contacts
β ββ Specific groups
β ββ Custom filters (qualifier, website status, tags)
β ββ Upload CSV list
β ββ API-provided lead IDs
ββ Preview recipient count
ββ Exclude duplicates/already-messaged
ββ Test send to 1-5 numbers first
[Step 3: Message Content]
ββ Message Type Selector:
β ββ π Text (with emoji support)
β ββ πΌοΈ Image + caption
β ββ π¬ Video + caption
β ββ π Document (PDF, DOC, etc.)
β ββ π΅ Audio message
β ββ π Location share
β ββ π€ Contact card (vCard)
β ββ π³οΈ Interactive poll
β ββ ποΈ View-once media
ββ Rich Text Editor:
β ββ Variables: {name}, {phone}, {custom_field}
β ββ Emoji picker
β ββ Character counter (WhatsApp limits)
β ββ Preview on phone mockup
ββ Media Upload:
β ββ Drag & drop
β ββ URL import
β ββ Library of previously uploaded media
β ββ Auto-compress for WhatsApp limits
ββ Fallback message (if media fails)
[Step 4: Sending Strategy]
ββ Delivery Mode:
β ββ π Sequential (one-by-one, slow)
β ββ π² Random order (avoid patterns)
β ββ π Round-robin (across sessions)
β ββ βοΈ Balanced (by gateway health)
β ββ π₯ Burst (fast, for small lists)
ββ Rate Limiting:
β ββ Messages per minute (10-100)
β ββ Daily cap per session
β ββ Pause between batches
β ββ Business hours only toggle
ββ Anti-Ban Protections:
β ββ Random delay (500ms-3000ms)
β ββ Simulate typing indicator
β ββ Rotate WhatsApp sessions
β ββ Auto-pause on high error rate
β ββ Human-like sending patterns
ββ Retry Logic:
ββ Max retries per message (0-3)
ββ Exponential backoff
ββ Skip after N failures
[Step 5: Schedule & Launch]
ββ Send Options:
β ββ π Send now
β ββ π
Schedule for later (date/time picker)
β ββ β° Recurring schedule (cron-like)
ββ Notifications:
β ββ Email on completion
β ββ Webhook on status change
β ββ In-app alerts for failures
ββ Review Summary:
β ββ Recipient count
β ββ Estimated duration
β ββ Cost estimate (if applicable)
β ββ Compliance checklist
ββ [Launch Campaign] button
| Layer | Technology | Purpose |
|---|---|---|
| Backend | PHP 8.3+ | Server-side logic |
| Framework | Custom MVC | Lightweight, no bloat |
| Database | MySQL 8+/MariaDB | Data persistence |
| Frontend | Bootstrap 5 + Vanilla JS | Responsive UI |
| HTTP Client | cURL | External API calls |
| Excel Parsing | PhpSpreadsheet | Import .xlsx/.csv files |
| Session Management | Native PHP Sessions | Authentication state |
| Hosting | Shared Hosting (cPanel) | Deployment target |
| WhatsApp API | tools.onhandi.com | Message sending |
- β Core MVC Framework: Router, Controller, Database, Logger
- β Authentication System: Login, registration, CSRF protection
- β Lead Import Pipeline: Excel upload β column mapping β database insert
- β
Website Verification Service:
- Robust URL parsing with
parse_url() - HTTP/HTTPS fallback testing
- Detailed result objects (status, HTTP code, response time)
- Robust URL parsing with
- β Dashboard UI: Stats cards, verification results table, live logs
- β Progress Modal: Real-time feedback during bulk operations
- β Error Handling: User-friendly messages, logging, graceful failures
app/Core/Controller.php
app/Core/Router.php
app/Controllers/LeadController.php
app/Services/WebsiteVerifier.php
app/Views/dashboard.php
- β
Tenant Isolation Middleware:
Tenant::requireTenant()enforces data scoping - β
Database Schema Updates:
user_idcolumns on all data tables (leads,campaigns,contacts, etc.)tenant_settingstable for per-user configsubscriptionstable for plan management
- β Workspace Onboarding: 3-step setup flow with slug generation
- β Per-User Settings: WhatsApp credentials, timezone, daily limits, working hours
- β
Admin Database Tools:
- Migration runner with one-click execution
- Safe SQL executor with dangerous operation warnings
- Real query results display (SELECT, DESCRIBE, SHOW)
- β Notification System: Toast alerts for all user actions
- β Responsive Header: Workspace selector, user menu, notification badge
- β Profile Management: Update info, change password, view stats
app/Middleware/Tenant.php
app/Controllers/OnboardingController.php
app/Controllers/DatabaseToolsController.php
app/Services/NotificationService.php
app/Views/onboarding/index.php
app/Views/admin/database-tools.php
database/migrations.sql (tenant isolation)
- π Query Scoping: All data queries include
WHERE user_id = :user_id - π Session Validation:
$_SESSION['user_id']cast to int to prevent injection - π Admin-Only Routes: Database tools protected by
Auth::requireAdmin() - π SQL Safety: Dangerous operations require explicit confirmation modal
Enable automated, compliant WhatsApp messaging to qualified leads using the onhandi.com API, with anti-ban protections and per-user configuration.
class WhatsAppGateway
{
// API Client for tools.onhandi.com
- checkNumber(string $phone): array // Verify WhatsApp availability
- sendMessage(string $phone, string $message, array $options): array // Send message
- getDeliveryStatus(string $messageId): array // Track delivery
// Anti-Ban Logic
- applyRandomDelay(int $min, int $max): void // Sleep between messages
- checkDailyLimit(int $userId): bool // Enforce per-user limits
- isWithinWorkingHours(string $timezone): bool // Respect business hours
// Caching
- cacheNumberCheck(string $phone, array $result, int $ttl): void // 24h cache
- getCachedResult(string $phone): ?array // Avoid redundant API calls
}class LeadProcessor
{
// Complete workflow
public function processQualifiedLeads(int $userId, int $batchSize = 10): array
{
// 1. Fetch qualified leads (scoped to user)
// 2. Check WhatsApp availability via gateway
// 3. Apply anti-ban logic (delays, limits, hours)
// 4. Send personalized message based on website status:
// - WORKING β "SEO/Maintenance" offer
// - NOT_WORKING/NO_WEBSITE β "Web Design" offer
// 5. Log results to activity_logs (user-scoped)
// 6. Update lead status (SENT/FAILED)
}
}class WhatsAppController extends Controller
{
// AJAX endpoints for dashboard
public function getStatus(): void // Check gateway connection
public function sendTest(): void // Send test message to phone
public function startCampaign(): void // Begin bulk send with progress
public function getProgress(): void // Poll for real-time updates
}- π’ Connection Status Indicator: WhatsApp gateway status (Connected/Disconnected)
- π€ Send Test Message: Input phone + send hardcoded "LeadFlux is up and running"
- π Live Send Progress: Progress bar + success/fail counters during campaigns
- βοΈ Anti-Ban Panel: "Today: X/30 sent β’ Next: HH:MM" with limit controls
- π Message Templates: Rotate 3-5 templates randomly to avoid spam detection
// Message selection based on website verification
if ($lead['website_status'] === 'WORKING') {
$message = "Hi {name}, noticed your site is live! π We offer maintenance, SEO, and social media management. Interested in a free audit?";
} elseif (in_array($lead['website_status'], ['NOT_WORKING', 'NO_WEBSITE', 'ERROR'])) {
$message = "Hi {name}, saw your business could use a professional website. π We design affordable, mobile-friendly sites. Free consultation?";
}- π₯
with_website.csv: Leads with working websites (SEO/maintenance offers) - π₯
without_website.csv: Leads without/broken websites (web design offers) - π
campaign_report.csv: Send results with timestamps and status codes
| Technique | Implementation | Purpose |
|---|---|---|
| Random Delays | sleep(rand(5, 15)) between messages |
Mimic human behavior |
| Batch Cooldowns | sleep(rand(120, 300)) after 15 messages |
Avoid rate limiting |
| Daily Limits | Track sends in DB; enforce per-plan limits | Prevent account flags |
| Working Hours | Only send 09:00-18:00 Africa/Nairobi (configurable) | Respect recipient time |
| Message Rotation | Cycle 3-5 templates randomly | Avoid spam pattern detection |
| Number Validation | Pre-check via Number Checker API | Avoid sending to invalid numbers |
βββββββββββββββββββββββββββββββββββββββββββ
β π’ WhatsApp: Connected β’ Today: 12/30 β
βββββββββββββββββββββββββββββββββββββββββββ€
β [Send Test Message] [Start Campaign] β
β β
β Progress: [ββββββββββββ] 80% β
β β
Sent: 24 β Failed: 2 β³ Pending: 4 β
β β
β Next Send: 14:32 (in 8 min) β
β Anti-Ban: Random delay β’ Batch cooldownβ
βββββββββββββββββββββββββββββββββββββββββββ
Endpoint: https://tools.onhandi.com/api/sessions/{sessionId}/send
Headers:
X-API-Key: {user_configured_key}
Content-Type: application/json
Request Body:
{
"to": "254712345678",
"message": "Your personalized message here",
"skipValidation": false
}Response Handling:
- β
200-299: Message queued/sent β log asSENT - β
401/403: Auth error β alert user to check credentials - β
404: Invalid endpoint β alert user to check base URL - β
429: Rate limited β apply exponential backoff - β Other: Log error, mark as
FAILED, continue batch
- PHP 8.3+ with extensions:
curl,pdo_mysql,mbstring,zip,xml - MySQL 8+ or MariaDB 10.5+
- Composer for dependency management
- cPanel or similar hosting with cron support
# 1. Clone repository
git clone https://github.com/yourorg/leadflux.git
cd leadflux
# 2. Install dependencies
composer install
# 3. Configure environment
cp .env.example .env
# Edit .env with your database credentials and WhatsApp API details
# 4. Run migrations
php artisan migrate
# 5. Set permissions
chmod -R 755 storage bootstrap/cache
# 6. Setup cron (for scheduled tasks)
* * * * * /usr/local/bin/php /path/to/leadflux/artisan schedule:run >> /dev/null 2>&1
# 7. Access application
# Visit: https://yourdomain.com/public- Register admin account (first user auto-promoted to admin)
- Complete workspace onboarding (name, slug, timezone)
- Configure WhatsApp credentials in Settings β WhatsApp Gateway
- Import leads via Marketing β Verify
- Start campaigns from Dashboard β WhatsApp Panel
- π Encryption: Passwords hashed with
password_hash()(bcrypt) - π Input Sanitization: All user inputs escaped with
htmlspecialchars() - π SQL Injection Prevention: Prepared statements with bound parameters
- π XSS Protection: Output encoding on all dynamic content
- β Opt-In Requirement: Only message leads who provided phone numbers
- β Unsubscribe Handling: Include opt-out instructions in messages
- β Rate Limiting: Respect WhatsApp's messaging policies via anti-ban logic
- β Data Retention: Configurable log retention periods
- π Query Scoping: Middleware enforces
user_idisolation on all data access - π Session Validation: User ID cast to int to prevent session fixation
- π Admin Separation: Admin features protected by role checks
- π Audit Logging: All sensitive actions logged with user context
- WhatsAppGateway API client with error handling
- LeadProcessor workflow with anti-ban logic
- Real-time campaign progress dashboard
- Message template rotation system
- Export qualified leads by website status
- Stripe/PayPal integration for subscription payments
- Usage-based billing (messages sent, leads imported)
- Plan upgrade/downgrade flow
- Invoice generation and payment history
- Campaign performance dashboards
- Lead conversion tracking
- A/B testing for message templates
- Exportable reports (PDF/CSV)
- Multi-user workspaces with roles (Admin, Member, Viewer)
- Shared lead pools and assignment
- Team activity feeds and notifications
- Audit trails for compliance
- Fork the repository
- Create a feature branch:
git checkout -b feature/amazing-feature - Commit changes:
git commit -m 'Add amazing feature' - Push to branch:
git push origin feature/amazing-feature - Open a Pull Request
- Follow PSR-12 coding style
- Use strict types:
declare(strict_types=1); - Document public methods with PHPDoc
- Write tests for new features (future)
LeadFlux is proprietary software. All rights reserved.
- π§ Email: support@leadflux.app
- π Issues: GitHub Issues
- π Docs: Wiki
LeadFlux β Turn leads into conversations, automatically. π
Built with β€οΈ by kinflux digital