FILE 5: /home/ai-prank-caller.digitalprank.com/public_html/help.md
code
Markdown
# Help & Documentation: AI Prank Call Bot
Welcome to the AI Prank Call Bot! This guide will help you get started with sending hilarious, AI-powered prank calls to your friends.
## Quick Start Guide
Getting started is easy. Just follow these simple steps:
1. **Step 1: Type your prank idea or script.**
- In the "Enter your prank script or idea" box, describe the funny scenario you want the AI to act out. Be creative!
2. **Step 2: Pick a hilarious voice style.**
- Use the "Voice Style" dropdown to select from a list of characters like 'Annoying Robot' or 'Angry Neighbor'.
3. **Step 3: Enter your victim's phone number (Pro).**
- If you're a Pro user, enter the full international phone number of the person you want to prank (e.g., +15551234567).
4. **Step 4: Click 'Send Prank Call'!**
- Hit the big orange button to launch your prank.
5. **Step 5: Enjoy the chaos.**
- Your friend will receive a call from our system, and the AI will deliver your custom script.
## Feature Descriptions
- **Prank Script/Idea:** The core of your prank. You can write a full script or just give the AI an idea to work with. (Free & Pro)
- **Voice Style:** Choose from a wide variety of pre-set AI voices to make your prank call more believable and fun. (Free & Pro)
- **Victim's Phone Number:** The destination for your prank call. This is a **Pro feature**. Free users can generate scripts and listen to voice previews.
- **Custom Caller ID:** Gold tier and above Pro users can specify the phone number that appears on the recipient's phone. Use this feature responsibly.
- **Schedule Call:** Pro users can schedule a prank call to be sent at a specific date and time in the future.
- **Use AI-Generated Voice:** By default, our AI reads your script. Pro users can uncheck this box to upload their own audio file instead.
## Frequently Asked Questions (FAQ)
**Q: Is this legal?**
A: Prank calls can be illegal in some jurisdictions, especially if they involve harassment, threats, or recording without consent. This tool is for entertainment purposes only. Use it responsibly and only with friends who have a good sense of humor. You are responsible for complying with all local and federal laws.
**Q: Can I use my own voice?**
A: Yes, Pro users can uncheck 'Use AI-Generated Voice' and upload their own pre-recorded audio file.
**Q: What if the call doesn't go through?**
A: You will not be charged any credits for failed or unanswered calls. You can try again without penalty.
## Usage Examples
Here are a couple of ideas to get your creativity flowing:
### Example 1: Wrong Pizza Delivery
- **Description:** A confused pizza guy calls the wrong number with a strange request.
- **Input:**
- `script_prompt`: "Hello? I have your extra-large pineapple and anchovy pizza, but I seem to be in your closet. Should I just leave it on the shoe rack?"
- `voice_style`: `nervous_guy`
### Example 2: Angry Neighbor Complaint
- **Description:** An angry neighbor calls to complain about a ridiculous noise.
- **Input:**
- `script_prompt`: "Yeah, hi, this is your neighbor from 3B. I need you to stop teaching your parrot to sing opera. It's scaring my cat, and frankly, you're both off-key."
- `voice_style`: `angry_neighbor`
---
*Have fun and prank responsibly!*
FILE 6: /home/digitalprank.com/public_html/blog/data/tools/ai-prank-caller.json
code
JSON
{
"post": {
"slug": "ai-prank-caller",
"title": "Unleash Hilarious Chaos with the AI Prank Call Bot",
"author": "The PrankMaster",
"date": "2025-09-25",
"tags": ["ai tools", "prank call", "entertainment", "phone pranks", "voice generator"],
"meta_description": "Discover how to send hilarious, automated prank calls with AI-generated voices. Our guide to the AI Prank Call Bot covers features, legal considerations, and funny script ideas.",
"canonical_url": "https://digitalprank.com/tools/ai-prank-caller",
"content": {
"introduction": {
"heading": "The Ultimate AI-Powered Prank Calling Tool",
"paragraph": "Ever wanted to prank a friend with a perfectly timed, hilarious phone call but didn't want to use your own voice? The AI Prank Call Bot is your new best friend. This tool lets you type a script, choose a funny AI voice, and send an automated call to any phone number. From an angry neighbor complaining about a non-existent barking dog to a confused pizza delivery guy who's somehow in their closet, the possibilities are endless."
},
"features_section": {
"heading": "Core Features",
"features": [
{
"name": "Custom Prank Scripts",
"description": "Simply type out your prank scenario. Whether it's a single line or a short monologue, our AI takes your text and brings it to life. The system supports scripts up to 500 characters, giving you plenty of room for creativity.",
"tier": "Free"
},
{
"name": "Diverse Voice Library",
"description": "Choose from a wide selection of hilarious voice styles, including 'Squeaky Chipmunk', 'Movie Narrator', 'Confused Old Lady', and more. Find the perfect voice to match your prank.",
"tier": "Free"
},
{
"name": "Direct-to-Phone Sending",
"description": "Our Pro plan allows you to enter your friend's phone number and send the prank call directly to their device. The prank is fully automated.",
"tier": "Pro"
},
{
"name": "Custom Caller ID",
"description": "Gold and Ultimate tier users can set a custom phone number to appear as the Caller ID, making the prank even more believable. (Use responsibly!)",
"tier": "Gold+"
},
{
"name": "Scheduled Prank Calls",
"description": "Want to make sure your prank lands at the perfect moment? Pro users can schedule calls for a future date and time.",
"tier": "Pro"
},
{
"name": "Upload Your Own Audio",
"description": "For ultimate customization, Pro users can uncheck the AI voice option and upload their own pre-recorded MP3 or WAV file.",
"tier": "Pro"
}
]
},
"how_to_guide": {
"heading": "How to Send Your First Prank Call",
"steps": [
"Write your prank idea in the 'Enter your prank script or idea' field.",
"Select a 'Voice Style' from the dropdown menu.",
"For Pro users, enter the target 'Victim's Phone Number' in international format.",
"Optionally, set a 'Caller ID' or 'Schedule Time' if you have the required plan.",
"Click 'Send Prank Call' and wait for the laughter."
]
},
"technical_docs": {
"heading": "Technical Specifications",
"specs": [
{ "name": "API Access", "value": "Available for Ultimate tier users." },
{ "name": "Backend APIs", "value": "Integrates with Twilio for call delivery and XTTS for voice synthesis." },
{ "name": "Supported Audio Uploads", "value": "MP3, WAV (Pro users only)" },
{ "name": "Daily Limits", "value": "2 (Free), 15 (Basic), 150 (Gold), Unlimited (Ultimate)" }
]
},
"faq_section": {
"heading": "Important Questions Answered",
"faqs": [
{
"question": "Is this legal?",
"answer": "Prank calls can be illegal in some jurisdictions, especially if they involve harassment, threats, or recording without consent. This tool is for entertainment purposes only. Use it responsibly and only with friends who have a good sense of humor. You are responsible for complying with all local and federal laws."
},
{
"question": "Can I use my own voice?",
"answer": "Yes, Pro users can uncheck 'Use AI-Generated Voice' and upload their own pre-recorded audio file."
},
{
"question": "What if the call doesn't go through?",
"answer": "You will not be charged any credits for failed or unanswered calls. You can try again without penalty."
}
]
}
},
"schema_org": {
"@context": "https://schema.org",
"@type": "WebApplication",
"name": "AI Prank Call Bot",
"description": "Send funny, automated prank calls using AI voices. Type a prank script, pick a voice, and watch the chaos unfold.",
"applicationCategory": "Entertainment",
"operatingSystem": "Any (Web-based)",
"url": "https://digitalprank.com/tools/ai-prank-caller",
"offers": {
"@type": "Offer",
"price": "0.00",
"priceCurrency": "USD"
},
"publisher": {
"@type": "Organization",
"name": "DigitalPrank.com"
}
}
}
}
FILE 7: /home/ai-prank-caller.digitalprank.com/public_html/deploy.sh
code
Bash
#!/bin/bash
# Deployment script for the AI Prank Caller tool
set -e
TOOL_SLUG="ai-prank-caller"
VHOST_DIR="/home/${TOOL_SLUG}.digitalprank.com/public_html"
APACHE_CONF_DIR="/etc/litespeed/vhosts"
LOG_DIR="/var/log/${TOOL_SLUG}"
VENV_DIR="${VHOST_DIR}/venv"
DB_NAME="digitalprank_db"
DB_USER="dp_user"
DB_PASS="#$Dealer2355"
echo "--- Starting deployment for ${TOOL_SLUG} ---"
# 1. Install System Packages
echo "Updating package lists and installing system dependencies..."
apt-get update
apt-get install -y ffmpeg sox
# 2. Install PHP Extensions
# This part is environment-dependent. Assuming a Docker-like env or manual enabling.
echo "Ensuring PHP extensions (curl, json, mbstring) are enabled..."
# Example for docker: docker-php-ext-install curl json mbstring
# On a standard server, you might use 'phpenmod' or edit php.ini.
# We'll assume they are available for this script.
# 3. Create Python Virtual Environment and Install Packages
echo "Setting up Python virtual environment..."
if [ -d "$VENV_DIR" ]; then
echo "Virtual environment already exists. Skipping creation."
else
python3 -m venv "$VENV_DIR"
fi
echo "Activating virtual environment and installing packages..."
source "${VENV_DIR}/bin/activate"
pip install --upgrade pip
pip install xtts pydub twilio
deactivate
echo "Python setup complete."
# 4. Create Tool-Specific Database Table
echo "Creating tool-specific database table 'prank_call_history'..."
SQL_CREATE_TABLE="CREATE TABLE IF NOT EXISTS \`prank_call_history\` (
\`id\` BIGINT PRIMARY KEY AUTO_INCREMENT,
\`user_id\` BIGINT NULL,
\`victim_phone\` VARCHAR(20) NOT NULL,
\`caller_id\` VARCHAR(20),
\`script_prompt\` TEXT NOT NULL,
\`voice_style\` VARCHAR(50) NOT NULL,
\`audio_url\` VARCHAR(255),
\`twilio_sid\` VARCHAR(255) UNIQUE,
\`status\` VARCHAR(50) DEFAULT 'pending',
\`scheduled_for\` DATETIME NULL,
\`created_at\` TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
\`updated_at\` TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
INDEX \`user_id_idx\` (\`user_id\`),
INDEX \`twilio_sid_idx\` (\`twilio_sid\`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"
# Execute SQL using credentials
mysql -u"${DB_USER}" -p"${DB_PASS}" "${DB_NAME}" -e "${SQL_CREATE_TABLE}"
echo "Database table check/creation complete."
# 5. OpenLiteSpeed Virtual Host Configuration
echo "Configuring OpenLiteSpeed virtual host..."
VHOST_CONF_PATH="${APACHE_CONF_DIR}/${TOOL_SLUG}.conf"
# Using a heredoc to create the config file
cat > "${VHOST_CONF_PATH}" < "${LOGROTATE_CONF}" <setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
$pdo->setAttribute(PDO::ATTR_EMULATE_PREPARES, false);
} catch (PDOException $e) {
http_response_code(500);
echo json_encode(['success' => false, 'message' => 'Database connection failed. Please contact support.']);
exit;
}
// --- CDN & Universal Functions ---
require_once '/home/cdn.digitalprank.com/public_html/php/analytics_functions.php';
// Placeholder for universal functions - normally in the CDN file
function getUserAccessLevel($pdo, $user_id, $tool_slug) {
// This is a mock. In production, this would be a complex query.
// For this example, we'll assume a user is 'free' unless a specific `user_id` is passed.
if (!empty($user_id) && is_numeric($user_id)) {
$stmt = $pdo->prepare("SELECT subscription_plan_id, status FROM wp_pms_member_subscriptions WHERE user_id = :user_id AND status = 'active' ORDER BY id DESC LIMIT 1");
$stmt->execute(['user_id' => $user_id]);
$sub = $stmt->fetch(PDO::FETCH_ASSOC);
if ($sub) {
$plan_id = $sub['subscription_plan_id'];
if (in_array($plan_id, [176, 186])) return ['level' => 'ultimate', 'has_pro_access' => true, 'tier_name' => 'Ultimate'];
if (in_array($plan_id, [175, 185])) return ['level' => 'gold', 'has_pro_access' => true, 'tier_name' => 'Gold'];
if (in_array($plan_id, [174, 184])) return ['level' => 'basic', 'has_pro_access' => true, 'tier_name' => 'Basic'];
}
}
return ['level' => 'free', 'has_pro_access' => false, 'tier_name' => 'Free'];
}
function logUsage($pdo, $tool_slug, $user_ip, $user_id, $action_type, $input_data, $output_data, $processing_time, $status = 'success') {
try {
$stmt = $pdo->prepare(
"INSERT INTO wp_digitalprank_usage_log (user_id, tool_slug, action_type, ip_address, session_id, user_agent, input_data, output_data, processing_time, status) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?)"
);
$stmt->execute([
$user_id,
$tool_slug,
$action_type,
$user_ip,
session_id(),
$_SERVER['HTTP_USER_AGENT'] ?? 'N/A',
json_encode($input_data),
json_encode($output_data),
$processing_time,
$status
]);
} catch (PDOException $e) {
// Fail silently so as not to interrupt user experience. Log this error elsewhere.
error_log("Failed to log usage for $tool_slug: " . $e->getMessage());
}
}
// --- Initial Response Structure ---
$response = [
'success' => false,
'message' => 'An unknown error occurred.',
'data' => null,
'usage' => ['credits_used' => 0],
'access' => null,
'features' => null,
];
try {
// --- Load Tool Configuration ---
$config_path = __DIR__ . '/tool_config.json';
if (!file_exists($config_path)) {
throw new Exception('Configuration file is missing.');
}
$config = json_decode(file_get_contents($config_path), true);
if (json_last_error() !== JSON_ERROR_NONE) {
throw new Exception('Invalid configuration file.');
}
// --- User & Request Information ---
$user_id = isset($_SESSION['user_id']) ? intval($_SESSION['user_id']) : null;
$user_ip = $_SERVER['REMOTE_ADDR'];
$input = $_POST;
// --- Access Control & Permissions ---
$access = getUserAccessLevel($pdo, $user_id, $tool_slug);
$response['access'] = $access;
$response['features'] = $config['tool']['features'];
// --- Input Sanitization & Validation ---
$sanitized_input = [];
$errors = [];
// Query for field overrides
$stmt = $pdo->prepare("SELECT field_id, tier_required FROM wp_digitalprank_tool_overrides WHERE tool_id = (SELECT tool_id FROM wp_digitalprank_tools WHERE slug = ?) AND is_active = 1");
$stmt->execute([$tool_slug]);
$overrides = $stmt->fetchAll(PDO::FETCH_KEY_PAIR);
$access_levels = ['free' => 0, 'basic' => 1, 'gold' => 2, 'ultimate' => 3];
$user_level_index = $access_levels[$access['level']];
foreach ($config['tool']['fields'] as $field) {
$id = $field['id'];
$value = isset($input[$id]) ? trim($input[$id]) : null;
// Check if field is required
if ($field['required'] && empty($value)) {
$errors[] = "Field '{$field['label']}' is required.";
continue;
}
// Skip validation for non-required empty fields
if (!$field['required'] && empty($value)) {
$sanitized_input[$id] = $field['type'] === 'checkbox' ? false : null;
continue;
}
// Pro/Tier check
$tier_required = $overrides[$id] ?? ($field['pro_only'] ? 'basic' : 'free');
$required_level_index = $access_levels[$tier_required];
if ($user_level_index < $required_level_index) {
$errors[] = "Field '{$field['label']}' requires at least a " . ucfirst($tier_required) . " plan.";
continue;
}
// Type-specific validation
switch ($field['type']) {
case 'text':
if (isset($field['validation']['min_length']) && mb_strlen($value) < $field['validation']['min_length']) {
$errors[] = "{$field['label']} must be at least {$field['validation']['min_length']} characters.";
}
if (isset($field['validation']['max_length']) && mb_strlen($value) > $field['validation']['max_length']) {
$errors[] = "{$field['label']} must not exceed {$field['validation']['max_length']} characters.";
}
if (isset($field['validation']['pattern']) && !preg_match("/{$field['validation']['pattern']}/", $value)) {
$errors[] = "Invalid format for {$field['label']}.";
}
$sanitized_input[$id] = htmlspecialchars($value, ENT_QUOTES, 'UTF-8');
break;
case 'tel':
// E.164 format-like validation
if (!preg_match('/^\+[1-9]\d{1,14}$/', $value)) {
$errors[] = "{$field['label']} must be in the international format (e.g., +15551234567).";
}
$sanitized_input[$id] = filter_var($value, FILTER_SANITIZE_NUMBER_INT);
break;
case 'select':
$valid_options = array_column($field['options'], 'value');
if (!in_array($value, $valid_options)) {
$errors[] = "Invalid option selected for {$field['label']}.";
}
$sanitized_input[$id] = $value;
break;
case 'datetime':
$d = DateTime::createFromFormat('Y-m-d\TH:i', $value);
if (!$d || $d->format('Y-m-d\TH:i') !== $value) {
$errors[] = "Invalid format for {$field['label']}.";
}
$sanitized_input[$id] = $value;
break;
case 'checkbox':
$sanitized_input[$id] = filter_var($value, FILTER_VALIDATE_BOOLEAN);
break;
default:
$sanitized_input[$id] = htmlspecialchars($value, ENT_QUOTES, 'UTF-8');
break;
}
}
// Blocked Domains check for phone numbers
$phone_fields = ['victim_phone', 'caller_id'];
foreach($phone_fields as $pf) {
if(isset($sanitized_input[$pf])) {
foreach($config['tool']['security']['blocked_domains'] as $domain) {
if(strpos($sanitized_input[$pf], $domain) !== false) { // Naive check
$errors[] = "Phone numbers associated with restricted domains (.{$domain}) are not allowed.";
}
}
}
}
if (!empty($errors)) {
throw new Exception(implode("\n", $errors));
}
// {{TOOL_PROCESSING_START}}
// --- AI Prank Caller Logic ---
$output_data = [];
$status = 'failed';
// Simulate API interactions
// In a real application, these would be classes that handle HTTP requests to external services.
// 1. Generate Audio from Script
$audio_url = null;
$use_ai_voice = $sanitized_input['use_ai_voice'] ?? true;
if ($use_ai_voice) {
// This simulates calling an XTTS or similar AI voice generation service.
// It would take the script and voice style, and return a URL to the generated MP3.
$script = $sanitized_input['script_prompt'];
$voice = $sanitized_input['voice_style'];
// Simulate a successful audio generation
$audio_file_name = md5($script . $voice . time()) . '.mp3';
$audio_url = "https://cdn.digitalprank.com/audio/generated/{$audio_file_name}";
// Pretend to save the file
// file_put_contents("/path/to/cdn/audio/generated/{$audio_file_name}", $generated_audio_data);
$output_data['audio_generation'] = [
'status' => 'success',
'voice' => $voice,
'url' => $audio_url
];
} else {
// Logic for user-uploaded audio (Pro feature)
if (!$access['has_pro_access']) {
throw new Exception("Uploading your own audio is a Pro feature.");
}
// Assume an upload handler provides the URL
// $audio_url = handle_audio_upload();
$output_data['audio_generation'] = ['status' => 'user_upload_skipped_for_demo'];
}
// 2. Initiate or Schedule the Call via Twilio
$victim_phone = $sanitized_input['victim_phone'];
$caller_id = !empty($sanitized_input['caller_id']) ? $sanitized_input['caller_id'] : '+15550001234'; // Platform's default number
// Caller ID is a "Gold" tier feature in this example
if (!empty($sanitized_input['caller_id'])) {
$required_level_index = $access_levels['gold'];
if ($user_level_index < $required_level_index) {
throw new Exception("Custom Caller ID requires a Gold tier plan or higher.");
}
}
// Simulate Twilio API call
// In production:
// $twilio = new Twilio\Rest\Client($sid, $token);
// $call = $twilio->calls->create(...)
$call_sid = 'CA' . bin2hex(random_bytes(16));
$twilio_options = [
'from' => $caller_id,
'to' => $victim_phone,
'twiml' => '' . htmlspecialchars($audio_url) . ''
];
$call_status = 'queued';
if (!empty($sanitized_input['schedule_time'])) {
// Logic for scheduling the call
$call_status = 'scheduled';
$output_data['schedule_status'] = [
'scheduled_for' => $sanitized_input['schedule_time'],
'job_id' => 'job_' . bin2hex(random_bytes(8))
];
}
$output_data['twilio_call'] = [
'sid' => $call_sid,
'status' => $call_status,
'options' => $twilio_options
];
// 3. Store results in the database if configured
if ($config['tool']['database']['store_results']) {
$history_stmt = $pdo->prepare(
"INSERT INTO prank_call_history (user_id, victim_phone, caller_id, script_prompt, voice_style, audio_url, twilio_sid, status, scheduled_for, created_at) VALUES (:user_id, :victim_phone, :caller_id, :script_prompt, :voice_style, :audio_url, :twilio_sid, :status, :scheduled_for, NOW())"
);
$history_stmt->execute([
':user_id' => $user_id,
':victim_phone' => $victim_phone,
':caller_id' => $caller_id,
':script_prompt' => $sanitized_input['script_prompt'],
':voice_style' => $sanitized_input['voice_style'],
':audio_url' => $audio_url,
':twilio_sid' => $call_sid,
':status' => $call_status,
':scheduled_for' => !empty($sanitized_input['schedule_time']) ? $sanitized_input['schedule_time'] : null
]);
}
$status = 'success';
$response['success'] = true;
$response['message'] = $call_status === 'scheduled' ? 'Prank call successfully scheduled!' : 'Prank call successfully initiated!';
$response['data'] = $output_data;
$response['usage']['credits_used'] = $config['tool']['billing']['credit_cost'];
// {{TOOL_PROCESSING_END}}
} catch (Exception $e) {
$status = 'failed';
$response['success'] = false;
$response['message'] = $e->getMessage();
http_response_code(400); // Bad Request
}
// --- Finalization & Logging ---
$processing_time = microtime(true) - $start_time;
logUsage($pdo, $tool_slug, $user_ip, $user_id, 'prank_call_sent', $input, $response, $processing_time, $status);
echo json_encode($response);
exit;
FILE 3: /home/ai-prank-caller.digitalprank.com/public_html/tool_form.php
code
PHP
- DigitalPrank.com
FILE 5: /home/ai-prank-caller.digitalprank.com/public_html/help.md
code
Markdown
# Help & Documentation: AI Prank Call Bot
Welcome to the AI Prank Call Bot! This guide will help you get started with sending hilarious, AI-powered prank calls to your friends.
## Quick Start Guide
Getting started is easy. Just follow these simple steps:
1. **Step 1: Type your prank idea or script.**
- In the "Enter your prank script or idea" box, describe the funny scenario you want the AI to act out. Be creative!
2. **Step 2: Pick a hilarious voice style.**
- Use the "Voice Style" dropdown to select from a list of characters like 'Annoying Robot' or 'Angry Neighbor'.
3. **Step 3: Enter your victim's phone number (Pro).**
- If you're a Pro user, enter the full international phone number of the person you want to prank (e.g., +15551234567).
4. **Step 4: Click 'Send Prank Call'!**
- Hit the big orange button to launch your prank.
5. **Step 5: Enjoy the chaos.**
- Your friend will receive a call from our system, and the AI will deliver your custom script.
## Feature Descriptions
- **Prank Script/Idea:** The core of your prank. You can write a full script or just give the AI an idea to work with. (Free & Pro)
- **Voice Style:** Choose from a wide variety of pre-set AI voices to make your prank call more believable and fun. (Free & Pro)
- **Victim's Phone Number:** The destination for your prank call. This is a **Pro feature**. Free users can generate scripts and listen to voice previews.
- **Custom Caller ID:** Gold tier and above Pro users can specify the phone number that appears on the recipient's phone. Use this feature responsibly.
- **Schedule Call:** Pro users can schedule a prank call to be sent at a specific date and time in the future.
- **Use AI-Generated Voice:** By default, our AI reads your script. Pro users can uncheck this box to upload their own audio file instead.
## Frequently Asked Questions (FAQ)
**Q: Is this legal?**
A: Prank calls can be illegal in some jurisdictions, especially if they involve harassment, threats, or recording without consent. This tool is for entertainment purposes only. Use it responsibly and only with friends who have a good sense of humor. You are responsible for complying with all local and federal laws.
**Q: Can I use my own voice?**
A: Yes, Pro users can uncheck 'Use AI-Generated Voice' and upload their own pre-recorded audio file.
**Q: What if the call doesn't go through?**
A: You will not be charged any credits for failed or unanswered calls. You can try again without penalty.
## Usage Examples
Here are a couple of ideas to get your creativity flowing:
### Example 1: Wrong Pizza Delivery
- **Description:** A confused pizza guy calls the wrong number with a strange request.
- **Input:**
- `script_prompt`: "Hello? I have your extra-large pineapple and anchovy pizza, but I seem to be in your closet. Should I just leave it on the shoe rack?"
- `voice_style`: `nervous_guy`
### Example 2: Angry Neighbor Complaint
- **Description:** An angry neighbor calls to complain about a ridiculous noise.
- **Input:**
- `script_prompt`: "Yeah, hi, this is your neighbor from 3B. I need you to stop teaching your parrot to sing opera. It's scaring my cat, and frankly, you're both off-key."
- `voice_style`: `angry_neighbor`
---
*Have fun and prank responsibly!*
FILE 6: /home/digitalprank.com/public_html/blog/data/tools/ai-prank-caller.json
code
JSON
{
"post": {
"slug": "ai-prank-caller",
"title": "Unleash Hilarious Chaos with the AI Prank Call Bot",
"author": "The PrankMaster",
"date": "2025-09-25",
"tags": ["ai tools", "prank call", "entertainment", "phone pranks", "voice generator"],
"meta_description": "Discover how to send hilarious, automated prank calls with AI-generated voices. Our guide to the AI Prank Call Bot covers features, legal considerations, and funny script ideas.",
"canonical_url": "https://digitalprank.com/tools/ai-prank-caller",
"content": {
"introduction": {
"heading": "The Ultimate AI-Powered Prank Calling Tool",
"paragraph": "Ever wanted to prank a friend with a perfectly timed, hilarious phone call but didn't want to use your own voice? The AI Prank Call Bot is your new best friend. This tool lets you type a script, choose a funny AI voice, and send an automated call to any phone number. From an angry neighbor complaining about a non-existent barking dog to a confused pizza delivery guy who's somehow in their closet, the possibilities are endless."
},
"features_section": {
"heading": "Core Features",
"features": [
{
"name": "Custom Prank Scripts",
"description": "Simply type out your prank scenario. Whether it's a single line or a short monologue, our AI takes your text and brings it to life. The system supports scripts up to 500 characters, giving you plenty of room for creativity.",
"tier": "Free"
},
{
"name": "Diverse Voice Library",
"description": "Choose from a wide selection of hilarious voice styles, including 'Squeaky Chipmunk', 'Movie Narrator', 'Confused Old Lady', and more. Find the perfect voice to match your prank.",
"tier": "Free"
},
{
"name": "Direct-to-Phone Sending",
"description": "Our Pro plan allows you to enter your friend's phone number and send the prank call directly to their device. The prank is fully automated.",
"tier": "Pro"
},
{
"name": "Custom Caller ID",
"description": "Gold and Ultimate tier users can set a custom phone number to appear as the Caller ID, making the prank even more believable. (Use responsibly!)",
"tier": "Gold+"
},
{
"name": "Scheduled Prank Calls",
"description": "Want to make sure your prank lands at the perfect moment? Pro users can schedule calls for a future date and time.",
"tier": "Pro"
},
{
"name": "Upload Your Own Audio",
"description": "For ultimate customization, Pro users can uncheck the AI voice option and upload their own pre-recorded MP3 or WAV file.",
"tier": "Pro"
}
]
},
"how_to_guide": {
"heading": "How to Send Your First Prank Call",
"steps": [
"Write your prank idea in the 'Enter your prank script or idea' field.",
"Select a 'Voice Style' from the dropdown menu.",
"For Pro users, enter the target 'Victim's Phone Number' in international format.",
"Optionally, set a 'Caller ID' or 'Schedule Time' if you have the required plan.",
"Click 'Send Prank Call' and wait for the laughter."
]
},
"technical_docs": {
"heading": "Technical Specifications",
"specs": [
{ "name": "API Access", "value": "Available for Ultimate tier users." },
{ "name": "Backend APIs", "value": "Integrates with Twilio for call delivery and XTTS for voice synthesis." },
{ "name": "Supported Audio Uploads", "value": "MP3, WAV (Pro users only)" },
{ "name": "Daily Limits", "value": "2 (Free), 15 (Basic), 150 (Gold), Unlimited (Ultimate)" }
]
},
"faq_section": {
"heading": "Important Questions Answered",
"faqs": [
{
"question": "Is this legal?",
"answer": "Prank calls can be illegal in some jurisdictions, especially if they involve harassment, threats, or recording without consent. This tool is for entertainment purposes only. Use it responsibly and only with friends who have a good sense of humor. You are responsible for complying with all local and federal laws."
},
{
"question": "Can I use my own voice?",
"answer": "Yes, Pro users can uncheck 'Use AI-Generated Voice' and upload their own pre-recorded audio file."
},
{
"question": "What if the call doesn't go through?",
"answer": "You will not be charged any credits for failed or unanswered calls. You can try again without penalty."
}
]
}
},
"schema_org": {
"@context": "https://schema.org",
"@type": "WebApplication",
"name": "AI Prank Call Bot",
"description": "Send funny, automated prank calls using AI voices. Type a prank script, pick a voice, and watch the chaos unfold.",
"applicationCategory": "Entertainment",
"operatingSystem": "Any (Web-based)",
"url": "https://digitalprank.com/tools/ai-prank-caller",
"offers": {
"@type": "Offer",
"price": "0.00",
"priceCurrency": "USD"
},
"publisher": {
"@type": "Organization",
"name": "DigitalPrank.com"
}
}
}
}
```### FILE 7: /home/ai-prank-caller.digitalprank.com/public_html/deploy.sh
```bash
#!/bin/bash
# Deployment script for the AI Prank Caller tool
set -e
TOOL_SLUG="ai-prank-caller"
VHOST_DIR="/home/${TOOL_SLUG}.digitalprank.com/public_html"
APACHE_CONF_DIR="/etc/litespeed/vhosts"
LOG_DIR="/var/log/${TOOL_SLUG}"
VENV_DIR="${VHOST_DIR}/venv"
DB_NAME="digitalprank_db"
DB_USER="dp_user"
DB_PASS="#$Dealer2355"
echo "--- Starting deployment for ${TOOL_SLUG} ---"
# 1. Install System Packages
echo "Updating package lists and installing system dependencies..."
apt-get update
apt-get install -y ffmpeg sox
# 2. Install PHP Extensions
# This part is environment-dependent. Assuming a Docker-like env or manual enabling.
echo "Ensuring PHP extensions (curl, json, mbstring) are enabled..."
# Example for docker: docker-php-ext-install curl json mbstring
# On a standard server, you might use 'phpenmod' or edit php.ini.
# We'll assume they are available for this script.
# 3. Create Python Virtual Environment and Install Packages
echo "Setting up Python virtual environment..."
if [ -d "$VENV_DIR" ]; then
echo "Virtual environment already exists. Skipping creation."
else
python3 -m venv "$VENV_DIR"
fi
echo "Activating virtual environment and installing packages..."
source "${VENV_DIR}/bin/activate"
pip install --upgrade pip
pip install xtts pydub twilio
deactivate
echo "Python setup complete."
# 4. Create Tool-Specific Database Table
echo "Creating tool-specific database table 'prank_call_history'..."
SQL_CREATE_TABLE="CREATE TABLE IF NOT EXISTS \`prank_call_history\` (
\`id\` BIGINT PRIMARY KEY AUTO_INCREMENT,
\`user_id\` BIGINT NULL,
\`victim_phone\` VARCHAR(20) NOT NULL,
\`caller_id\` VARCHAR(20),
\`script_prompt\` TEXT NOT NULL,
\`voice_style\` VARCHAR(50) NOT NULL,
\`audio_url\` VARCHAR(255),
\`twilio_sid\` VARCHAR(255) UNIQUE,
\`status\` VARCHAR(50) DEFAULT 'pending',
\`scheduled_for\` DATETIME NULL,
\`created_at\` TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
\`updated_at\` TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
INDEX \`user_id_idx\` (\`user_id\`),
INDEX \`twilio_sid_idx\` (\`twilio_sid\`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"
# Execute SQL using credentials
mysql -u"${DB_USER}" -p"${DB_PASS}" "${DB_NAME}" -e "${SQL_CREATE_TABLE}"
echo "Database table check/creation complete."
# 5. OpenLiteSpeed Virtual Host Configuration
echo "Configuring OpenLiteSpeed virtual host..."
VHOST_CONF_PATH="${APACHE_CONF_DIR}/${TOOL_SLUG}.conf"
# Using a heredoc to create the config file
cat > "${VHOST_CONF_PATH}" < "${LOGROTATE_CONF}" <setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
$pdo->setAttribute(PDO::ATTR_EMULATE_PREPARES, false);
} catch (PDOException $e) {
http_response_code(500);
echo json_encode(['success' => false, 'message' => 'Database connection failed. Please contact support.']);
exit;
}
// --- CDN & Universal Functions ---
require_once '/home/cdn.digitalprank.com/public_html/php/analytics_functions.php';
function getUserAccessLevel($pdo, $user_id, $tool_slug) {
if (!empty($user_id) && is_numeric($user_id)) {
$stmt = $pdo->prepare("SELECT subscription_plan_id, status FROM wp_pms_member_subscriptions WHERE user_id = :user_id AND status = 'active' ORDER BY id DESC LIMIT 1");
$stmt->execute(['user_id' => $user_id]);
$sub = $stmt->fetch(PDO::FETCH_ASSOC);
if ($sub) {
$plan_id = $sub['subscription_plan_id'];
if (in_array($plan_id, [176, 186])) return ['level' => 'ultimate', 'has_pro_access' => true, 'tier_name' => 'Ultimate'];
if (in_array($plan_id, [175, 185])) return ['level' => 'gold', 'has_pro_access' => true, 'tier_name' => 'Gold'];
if (in_array($plan_id, [174, 184])) return ['level' => 'basic', 'has_pro_access' => true, 'tier_name' => 'Basic'];
}
}
return ['level' => 'free', 'has_pro_access' => false, 'tier_name' => 'Free'];
}
function logUsage($pdo, $tool_slug, $user_ip, $user_id, $action_type, $input_data, $output_data, $processing_time, $status = 'success') {
try {
$stmt = $pdo->prepare(
"INSERT INTO wp_digitalprank_usage_log (user_id, tool_slug, action_type, ip_address, session_id, user_agent, input_data, output_data, processing_time, status) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?)"
);
$stmt->execute([ $user_id, $tool_slug, $action_type, $user_ip, session_id(), $_SERVER['HTTP_USER_AGENT'] ?? 'N/A', json_encode($input_data), json_encode($output_data), $processing_time, $status ]);
} catch (PDOException $e) { error_log("Failed to log usage for $tool_slug: " . $e->getMessage()); }
}
// --- Initial Response Structure ---
$response = [ 'success' => false, 'message' => 'An unknown error occurred.', 'data' => null, 'usage' => ['credits_used' => 0], 'access' => null, 'features' => null ];
try {
$config_path = __DIR__ . '/tool_config.json';
if (!file_exists($config_path)) throw new Exception('Configuration file is missing.');
$config = json_decode(file_get_contents($config_path), true);
if (json_last_error() !== JSON_ERROR_NONE) throw new Exception('Invalid configuration file.');
$user_id = isset($_SESSION['user_id']) ? intval($_SESSION['user_id']) : null;
$user_ip = $_SERVER['REMOTE_ADDR'];
$input = $_POST;
$access = getUserAccessLevel($pdo, $user_id, $tool_slug);
$response['access'] = $access;
$response['features'] = $config['tool']['features'];
$sanitized_input = [];
$errors = [];
$stmt = $pdo->prepare("SELECT field_id, tier_required FROM wp_digitalprank_tool_overrides WHERE tool_id = (SELECT tool_id FROM wp_digitalprank_tools WHERE slug = ?) AND is_active = 1");
$stmt->execute([$tool_slug]);
$overrides = $stmt->fetchAll(PDO::FETCH_KEY_PAIR);
$access_levels = ['free' => 0, 'basic' => 1, 'gold' => 2, 'ultimate' => 3];
$user_level_index = $access_levels[$access['level']];
foreach ($config['tool']['fields'] as $field) {
$id = $field['id'];
$value = isset($input[$id]) ? trim($input[$id]) : null;
if ($field['required'] && empty($value)) { $errors[] = "Field '{$field['label']}' is required."; continue; }
if (!$field['required'] && empty($value)) { $sanitized_input[$id] = $field['type'] === 'checkbox' ? false : null; continue; }
$tier_required = $overrides[$id] ?? ($field['pro_only'] ? 'basic' : 'free');
$required_level_index = $access_levels[$tier_required];
if ($user_level_index < $required_level_index) { $errors[] = "Field '{$field['label']}' requires at least a " . ucfirst($tier_required) . " plan."; continue; }
switch ($field['type']) {
case 'text':
if (isset($field['validation']['min_length']) && mb_strlen($value) < $field['validation']['min_length']) $errors[] = "{$field['label']} must be at least {$field['validation']['min_length']} characters.";
if (isset($field['validation']['max_length']) && mb_strlen($value) > $field['validation']['max_length']) $errors[] = "{$field['label']} must not exceed {$field['validation']['max_length']} characters.";
if (isset($field['validation']['pattern']) && !preg_match("/{$field['validation']['pattern']}/", $value)) $errors[] = "Invalid format for {$field['label']}.";
$sanitized_input[$id] = htmlspecialchars($value, ENT_QUOTES, 'UTF-8');
break;
case 'tel':
if (!preg_match('/^\+[1-9]\d{1,14}$/', $value)) $errors[] = "{$field['label']} must be in the international format (e.g., +15551234567).";
$sanitized_input[$id] = filter_var($value, FILTER_SANITIZE_NUMBER_INT);
break;
case 'select':
if (!in_array($value, array_column($field['options'], 'value'))) $errors[] = "Invalid option selected for {$field['label']}.";
$sanitized_input[$id] = $value;
break;
case 'datetime':
$d = DateTime::createFromFormat('Y-m-d\TH:i', $value);
if (!$d || $d->format('Y-m-d\TH:i') !== $value) $errors[] = "Invalid format for {$field['label']}.";
$sanitized_input[$id] = $value;
break;
case 'checkbox': $sanitized_input[$id] = filter_var($value, FILTER_VALIDATE_BOOLEAN); break;
default: $sanitized_input[$id] = htmlspecialchars($value, ENT_QUOTES, 'UTF-8'); break;
}
}
foreach(['victim_phone', 'caller_id'] as $pf) {
if(isset($sanitized_input[$pf])) {
foreach($config['tool']['security']['blocked_domains'] as $domain) {
if(strpos($sanitized_input[$pf], $domain) !== false) $errors[] = "Phone numbers associated with restricted domains (.{$domain}) are not allowed.";
}
}
}
if (!empty($errors)) throw new Exception(implode("\n", $errors));
// {{TOOL_PROCESSING_START}}
$output_data = [];
$status = 'failed';
// 1. Generate or Retrieve Audio URL
$audio_url = null;
$use_ai_voice = $sanitized_input['use_ai_voice'] ?? true;
if ($use_ai_voice) {
$voice_gen = new VoiceGenerator();
$audio_generation_result = $voice_gen->generateAudio($sanitized_input['script_prompt'], $sanitized_input['voice_style']);
$audio_url = $audio_generation_result['url'];
$output_data['audio_generation'] = $audio_generation_result;
} else {
if (!$access['has_pro_access']) throw new Exception("Uploading your own audio is a Pro feature.");
// In a real app, you would handle the file upload here.
// $audio_url = handle_audio_upload($_FILES['user_audio']);
$audio_url = "https://cdn.digitalprank.com/audio/user_uploads/placeholder.mp3"; // Placeholder
$output_data['audio_generation'] = ['status' => 'user_upload', 'url' => $audio_url];
}
if (empty($audio_url)) throw new Exception("Failed to generate or locate audio for the call.");
// 2. Initiate or Schedule Call
if (empty($sanitized_input['victim_phone'])) throw new Exception("Victim's phone number is required for Pro users.");
$caller_id = !empty($sanitized_input['caller_id']) ? $sanitized_input['caller_id'] : '+15550001234';
if (!empty($sanitized_input['caller_id'])) {
if ($user_level_index < $access_levels['gold']) throw new Exception("Custom Caller ID requires a Gold tier plan or higher.");
}
$twilio_handler = new TwilioHandler();
$call_result = $twilio_handler->initiateCall(
$sanitized_input['victim_phone'],
$caller_id,
$audio_url
);
$call_sid = $call_result['sid'];
$call_status = $call_result['status'];
$output_data['twilio_call'] = $call_result;
// Handle scheduling
if (!empty($sanitized_input['schedule_time'])) {
if ($user_level_index < $access_levels['basic']) throw new Exception("Scheduling calls is a Pro feature.");
$call_status = 'scheduled';
// In a real app, a cron job or queue worker would process this.
// For now, we just update the status and log it.
$output_data['schedule_status'] = ['scheduled_for' => $sanitized_input['schedule_time']];
}
// 3. Store Results in Database
if ($config['tool']['database']['store_results']) {
$stmt = $pdo->prepare(
"INSERT INTO prank_call_history (user_id, victim_phone, caller_id, script_prompt, voice_style, audio_url, twilio_sid, status, scheduled_for, created_at) VALUES (:uid, :vp, :cid, :sp, :vs, :au, :tsid, :st, :sf, NOW())"
);
$stmt->execute([
':uid' => $user_id, ':vp' => $sanitized_input['victim_phone'], ':cid' => $caller_id,
':sp' => $sanitized_input['script_prompt'], ':vs' => $sanitized_input['voice_style'],
':au' => $audio_url, ':tsid' => $call_sid, ':st' => $call_status,
':sf' => !empty($sanitized_input['schedule_time']) ? $sanitized_input['schedule_time'] : null
]);
}
$status = 'success';
$response['success'] = true;
$response['message'] = $call_status === 'scheduled' ? 'Prank call successfully scheduled!' : 'Prank call successfully initiated!';
$response['data'] = $output_data;
$response['usage']['credits_used'] = $config['tool']['billing']['credit_cost'];
// {{TOOL_PROCESSING_END}}
} catch (Exception $e) {
$status = 'failed';
$response['success'] = false;
$response['message'] = $e->getMessage();
http_response_code(400);
}
$processing_time = microtime(true) - $start_time;
logUsage($pdo, $tool_slug, $user_ip, $user_id, 'prank_call_sent', $input, $response, $processing_time, $status);
echo json_encode($response);
exit;
FILE 3: /home/ai-prank-caller.digitalprank.com/public_html/tool_form.php
code
PHP
- DigitalPrank.com
FILE 5: /home/ai-prank-caller.digitalprank.com/public_html/help.md
code
Markdown
# Help & Documentation: AI Prank Call Bot
Welcome to the AI Prank Call Bot! This guide will help you get started with sending hilarious, AI-powered prank calls to your friends.
## Quick Start Guide
Getting started is easy. Just follow these simple steps:
1. **Step 1: Type your prank idea or script.**
- In the "Enter your prank script or idea" box, describe the funny scenario you want the AI to act out. Be creative!
2. **Step 2: Pick a hilarious voice style.**
- Use the "Voice Style" dropdown to select from a list of characters like 'Annoying Robot' or 'Angry Neighbor'.
3. **Step 3: Enter your victim's phone number (Pro).**
- If you're a Pro user, enter the full international phone number of the person you want to prank (e.g., +15551234567).
4. **Step 4: Click 'Send Prank Call'!**
- Hit the big orange button to launch your prank.
5. **Step 5: Enjoy the chaos.**
- Your friend will receive a call from our system, and the AI will deliver your custom script.
## Feature Descriptions
- **Prank Script/Idea:** The core of your prank. You can write a full script or just give the AI an idea to work with. (Free & Pro)
- **Voice Style:** Choose from a wide variety of pre-set AI voices to make your prank call more believable and fun. (Free & Pro)
- **Victim's Phone Number:** The destination for your prank call. This is a **Pro feature**. Free users can generate scripts and listen to voice previews.
- **Custom Caller ID:** Gold tier and above Pro users can specify the phone number that appears on the recipient's phone. Use this feature responsibly.
- **Schedule Call:** Pro users can schedule a prank call to be sent at a specific date and time in the future.
- **Use AI-Generated Voice:** By default, our AI reads your script. Pro users can uncheck this box to upload their own audio file instead.
## Frequently Asked Questions (FAQ)
**Q: Is this legal?**
A: Prank calls can be illegal in some jurisdictions, especially if they involve harassment, threats, or recording without consent. This tool is for entertainment purposes only. Use it responsibly and only with friends who have a good sense of humor. You are responsible for complying with all local and federal laws.
**Q: Can I use my own voice?**
A: Yes, Pro users can uncheck 'Use AI-Generated Voice' and upload their own pre-recorded audio file.
**Q: What if the call doesn't go through?**
A: You will not be charged any credits for failed or unanswered calls. You can try again without penalty.
## Usage Examples
Here are a couple of ideas to get your creativity flowing:
### Example 1: Wrong Pizza Delivery
- **Description:** A confused pizza guy calls the wrong number with a strange request.
- **Input:**
- `script_prompt`: "Hello? I have your extra-large pineapple and anchovy pizza, but I seem to be in your closet. Should I just leave it on the shoe rack?"
- `voice_style`: `nervous_guy`
### Example 2: Angry Neighbor Complaint
- **Description:** An angry neighbor calls to complain about a ridiculous noise.
- **Input:**
- `script_prompt`: "Yeah, hi, this is your neighbor from 3B. I need you to stop teaching your parrot to sing opera. It's scaring my cat, and frankly, you're both off-key."
- `voice_style`: `angry_neighbor`
---
*Have fun and prank responsibly!*
FILE 6: /home/digitalprank.com/public_html/blog/data/tools/ai-prank-caller.json
code
JSON
{
"post": {
"slug": "ai-prank-caller",
"title": "Unleash Hilarious Chaos with the AI Prank Call Bot",
"author": "The PrankMaster",
"date": "2025-09-25",
"tags": ["ai tools", "prank call", "entertainment", "phone pranks", "voice generator"],
"meta_description": "Discover how to send hilarious, automated prank calls with AI-generated voices. Our guide to the AI Prank Call Bot covers features, legal considerations, and funny script ideas.",
"canonical_url": "https://digitalprank.com/tools/ai-prank-caller",
"content": {
"introduction": {
"heading": "The Ultimate AI-Powered Prank Calling Tool",
"paragraph": "Ever wanted to prank a friend with a perfectly timed, hilarious phone call but didn't want to use your own voice? The AI Prank Call Bot is your new best friend. This tool lets you type a script, choose a funny AI voice, and send an automated call to any phone number. From an angry neighbor complaining about a non-existent barking dog to a confused pizza delivery guy who's somehow in their closet, the possibilities are endless."
},
"features_section": {
"heading": "Core Features",
"features": [
{
"name": "Custom Prank Scripts",
"description": "Simply type out your prank scenario. Whether it's a single line or a short monologue, our AI takes your text and brings it to life. The system supports scripts up to 500 characters, giving you plenty of room for creativity.",
"tier": "Free"
},
{
"name": "Diverse Voice Library",
"description": "Choose from a wide selection of hilarious voice styles, including 'Squeaky Chipmunk', 'Movie Narrator', 'Confused Old Lady', and more. Find the perfect voice to match your prank.",
"tier": "Free"
},
{
"name": "Direct-to-Phone Sending",
"description": "Our Pro plan allows you to enter your friend's phone number and send the prank call directly to their device. The prank is fully automated.",
"tier": "Pro"
},
{
"name": "Custom Caller ID",
"description": "Gold and Ultimate tier users can set a custom phone number to appear as the Caller ID, making the prank even more believable. (Use responsibly!)",
"tier": "Gold+"
},
{
"name": "Scheduled Prank Calls",
"description": "Want to make sure your prank lands at the perfect moment? Pro users can schedule calls for a future date and time.",
"tier": "Pro"
},
{
"name": "Upload Your Own Audio",
"description": "For ultimate customization, Pro users can uncheck the AI voice option and upload their own pre-recorded MP3 or WAV file.",
"tier": "Pro"
}
]
},
"how_to_guide": {
"heading": "How to Send Your First Prank Call",
"steps": [
"Write your prank idea in the 'Enter your prank script or idea' field.",
"Select a 'Voice Style' from the dropdown menu.",
"For Pro users, enter the target 'Victim's Phone Number' in international format.",
"Optionally, set a 'Caller ID' or 'Schedule Time' if you have the required plan.",
"Click 'Send Prank Call' and wait for the laughter."
]
},
"technical_docs": {
"heading": "Technical Specifications",
"specs": [
{ "name": "API Access", "value": "Available for Ultimate tier users." },
{ "name": "Backend APIs", "value": "Integrates with Twilio for call delivery and XTTS for voice synthesis." },
{ "name": "Supported Audio Uploads", "value": "MP3, WAV (Pro users only)" },
{ "name": "Daily Limits", "value": "2 (Free), 15 (Basic), 150 (Gold), Unlimited (Ultimate)" }
]
},
"faq_section": {
"heading": "Important Questions Answered",
"faqs": [
{
"question": "Is this legal?",
"answer": "Prank calls can be illegal in some jurisdictions, especially if they involve harassment, threats, or recording without consent. This tool is for entertainment purposes only. Use it responsibly and only with friends who have a good sense of humor. You are responsible for complying with all local and federal laws."
},
{
"question": "Can I use my own voice?",
"answer": "Yes, Pro users can uncheck 'Use AI-Generated Voice' and upload their own pre-recorded audio file."
},
{
"question": "What if the call doesn't go through?",
"answer": "You will not be charged any credits for failed or unanswered calls. You can try again without penalty."
}
]
}
},
"schema_org": {
"@context": "https://schema.org",
"@type": "WebApplication",
"name": "AI Prank Call Bot",
"description": "Send funny, automated prank calls using AI voices. Type a prank script, pick a voice, and watch the chaos unfold.",
"applicationCategory": "Entertainment",
"operatingSystem": "Any (Web-based)",
"url": "https://digitalprank.com/tools/ai-prank-caller",
"offers": {
"@type": "Offer",
"price": "0.00",
"priceCurrency": "USD"
},
"publisher": {
"@type": "Organization",
"name": "DigitalPrank.com"
}
}
}
}
FILE 7: /home/ai-prank-caller.digitalprank.com/public_html/deploy.sh
code
Bash
#!/bin/bash
# Deployment script for the AI Prank Caller tool v1.2
set -e
TOOL_SLUG="ai-prank-caller"
VHOST_DIR="/home/${TOOL_SLUG}.digitalprank.com/public_html"
APACHE_CONF_DIR="/etc/litespeed/vhosts"
LOG_DIR="/var/log/${TOOL_SLUG}"
VENV_DIR="${VHOST_DIR}/venv"
DB_NAME="digitalprank_db"
DB_USER="dp_user"
DB_PASS="#$Dealer2355"
echo "--- Starting deployment for ${TOOL_SLUG} ---"
# 1. Install System Packages
echo "Updating package lists and installing system dependencies..."
apt-get update
apt-get install -y ffmpeg sox python3-venv
# 2. Install PHP Extensions
echo "Ensuring PHP extensions (curl, json, mbstring) are enabled..."
# This is environment-specific. On a standard server, you might use:
# apt-get install -y php8.1-curl php8.1-mbstring
# We assume they are available.
# 3. Create Python Virtual Environment and Install Packages
echo "Setting up Python virtual environment at ${VENV_DIR}..."
if [ ! -d "$VENV_DIR" ]; then
python3 -m venv "$VENV_DIR"
fi
echo "Activating virtual environment and installing/upgrading packages..."
source "${VENV_DIR}/bin/activate"
pip install --upgrade pip
pip install xtts pydub twilio
deactivate
echo "Python setup complete."
# 4. Create/Update Tool-Specific Database Table
echo "Creating/updating tool-specific database table 'prank_call_history'..."
SQL_CREATE_TABLE="CREATE TABLE IF NOT EXISTS \`prank_call_history\` (
\`id\` BIGINT PRIMARY KEY AUTO_INCREMENT,
\`user_id\` BIGINT NULL,
\`victim_phone\` VARCHAR(20) NOT NULL,
\`caller_id\` VARCHAR(20),
\`script_prompt\` TEXT NOT NULL,
\`voice_style\` VARCHAR(50) NOT NULL,
\`audio_url\` VARCHAR(255),
\`twilio_sid\` VARCHAR(255) UNIQUE,
\`status\` VARCHAR(50) DEFAULT 'pending',
\`scheduled_for\` DATETIME NULL,
\`created_at\` TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
\`updated_at\` TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
INDEX \`user_id_idx\` (\`user_id\`),
INDEX \`twilio_sid_idx\` (\`twilio_sid\`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"
mysql -u"${DB_USER}" -p"${DB_PASS}" "${DB_NAME}" -e "${SQL_CREATE_TABLE}"
echo "Database table check/creation complete."
# 5. OpenLiteSpeed Virtual Host Configuration
echo "Configuring OpenLiteSpeed virtual host..."
VHOST_CONF_PATH="${APACHE_CONF_DIR}/${TOOL_SLUG}.conf"
cat > "${VHOST_CONF_PATH}" < "${LOGROTATE_CONF}" <api_sid = getenv('TWILIO_SID') ?: 'ACxxxxxxxxxxxxxxxxxxxxxxxxxxxxx';
$this->api_token = getenv('TWILIO_TOKEN') ?: 'your_auth_token';
}
/**
* Simulates initiating a phone call via Twilio.
*
* In a production environment, this method would use the Twilio PHP SDK
* to make a real API call.
*
* @param string $toPhoneNumber The E.164 formatted number of the recipient.
* @param string $fromPhoneNumber The E.164 formatted number to use as Caller ID.
* @param string $audioUrl The publicly accessible URL of the audio file to play.
* @return array An associative array containing the simulated call SID and status.
* @throws Exception if input parameters are invalid.
*/
public function initiateCall($toPhoneNumber, $fromPhoneNumber, $audioUrl) {
if (empty($toPhoneNumber) || empty($fromPhoneNumber) || empty($audioUrl)) {
throw new Exception("To, From, and Audio URL are required to initiate a call.");
}
// --- PRODUCTION CODE EXAMPLE ---
// require_once '/path/to/vendor/autoload.php';
// use Twilio\Rest\Client;
//
// $client = new Client($this->api_sid, $this->api_token);
//
// try {
// $call = $client->calls->create(
// $toPhoneNumber,
// $fromPhoneNumber,
// [
// 'twiml' => '' . htmlspecialchars($audioUrl) . ''
// ]
// );
// return ['sid' => $call->sid, 'status' => 'queued'];
// } catch (\Twilio\Exceptions\TwilioException $e) {
// error_log("Twilio API Error: " . $e->getMessage());
// throw new Exception("Could not initiate the call. Please check the phone number and try again.");
// }
// -------------------------------
// --- SIMULATION FOR THIS EXAMPLE ---
// We simulate a successful API call without making a real request.
// This avoids the need for real credentials and SDK installation for this demonstration.
$simulatedSid = 'CA' . hash('sha256', $toPhoneNumber . $fromPhoneNumber . microtime());
$simulatedSid = substr($simulatedSid, 0, 34); // Twilio SIDs are 34 chars starting with CA
return [
'sid' => $simulatedSid,
'status' => 'queued',
'options' => [
'to' => $toPhoneNumber,
'from' => $fromPhoneNumber,
'twiml' => '' . htmlspecialchars($audioUrl) . ''
]
];
}
}
FILE 9: /home/ai-prank-caller.digitalprank.com/public_html/voice_generator.php
code
PHP
'success',
'voice' => $voiceStyle,
'url' => $publicUrl
];
}
}
Model
ThinkingThoughts
(experimental)
Auto
Expand to view model thoughts
chevron_right
FILE 1: /home/ai-prank-caller.digitalprank.com/public_html/tool_config.json
code
JSON
{
"tool": {
"identity": {
"slug": "ai-prank-caller",
"name": "AI Prank Call Bot",
"category": "prank",
"tagline": "Unleash hilarious, AI-powered prank calls on your friends!",
"description": "Send funny, automated prank calls using AI voices. Type a prank script, pick a voice, and watch the chaos unfold.",
"keywords": ["prank call", "ai voice", "funny calls", "voice changer", "digital prank", "api"]
},
"features": {
"bulk_enabled": false,
"history_enabled": true,
"export_enabled": true,
"api_enabled": true
},
"fields": [
{
"id": "script_prompt",
"type": "text",
"label": "Enter your prank script or idea",
"placeholder": "e.g., A pizza guy who got lost in your closet.",
"required": true,
"validation": {
"pattern": "^.{10,500}$",
"min_length": 10,
"max_length": 500
},
"pro_only": false,
"help_text": "Describe a scenario like 'An angry neighbor complaining about a barking dog that doesn't exist' or type the full message."
},
{
"id": "voice_style",
"type": "select",
"label": "Voice Style",
"default": "annoying_robot",
"options": [
{ "value": "annoying_robot", "label": "Annoying Robot" },
{ "value": "squeaky_chipmunk", "label": "Squeaky Chipmunk" },
{ "value": "scary_deep", "label": "Scary Deep Voice" },
{ "value": "sassy_female", "label": "Sassy Female" },
{ "value": "movie_narrator", "label": "Movie Narrator" },
{ "value": "angry_neighbor", "label": "Angry Neighbor" },
{ "value": "confused_old_lady", "label": "Confused Old Lady" },
{ "value": "slick_salesman", "label": "Slick Salesman" },
{ "value": "nervous_guy", "label": "Nervous Guy" },
{ "value": "custom", "label": "Custom AI-Generated Voice (Pro)" }
],
"pro_only": false,
"help_text": "Choose a hilarious voice for your prank."
},
{
"id": "victim_phone",
"type": "tel",
"label": "Victim's Phone Number",
"placeholder": "+15551234567",
"required": true,
"pro_only": true,
"help_text": "Enter the number of your unsuspecting friend. International format required. Pro users only."
},
{
"id": "caller_id",
"type": "tel",
"label": "Caller ID to Display (Optional)",
"placeholder": "e.g., +15558675309",
"required": false,
"pro_only": true,
"help_text": "What number should appear on their phone? Gold tier and above. Use responsibly."
},
{
"id": "schedule_time",
"type": "datetime",
"label": "Schedule Call Time",
"required": false,
"pro_only": true,
"help_text": "Optional. Leave blank to send immediately."
},
{
"id": "use_ai_voice",
"type": "checkbox",
"label": "Use AI-Generated Voice",
"default": true,
"pro_only": false,
"help_text": "Let our AI read your script. Uncheck to upload your own audio file (Pro feature)."
}
],
"limits": {
"tier_daily": { "free": 2, "basic": 15, "gold": 150, "ultimate": -1 },
"rate_limit_per_minute": 10,
"max_concurrent_requests": 3
},
"billing": { "credit_cost": 1, "one_off_enabled": true, "one_off_price_cents": 99, "bill_on": "success" },
"ui": {
"theme": { "primary_color": "#FF4500", "secondary_color": "#1a1a1a" },
"layout": { "show_sidebar_ads": true, "form_style": "wizard", "result_display": "modal" }
},
"dependencies": {
"php_extensions": ["curl", "json", "mbstring"],
"system_packages": ["ffmpeg", "sox"],
"python_packages": ["xtts", "pydub", "twilio"],
"external_apis": ["twilio", "xtts", "ollama", "openai", "claude"]
},
"database": {
"tool_specific_table": "prank_call_history",
"store_results": true,
"enable_history": true,
"retention_days": 30
},
"api": {
"endpoint": "/api.php",
"auth_type": "header",
"auth_key_name": "X-API-Key",
"tier_required": "ultimate",
"documentation_url": "https://digitalprank.com/docs/api/ai-prank-caller"
},
"seo": {
"meta_title": "AI Prank Call Generator | Send Funny Custom Calls | DigitalPrank.com",
"meta_description": "Create and send hilarious AI-powered prank calls with funny voices. Type a script, choose a voice like 'Angry Neighbor' or 'Robot', and call your friends. Try it for free!",
"canonical_url": "https://digitalprank.com/tools/ai-prank-caller",
"structured_data": { "type": "WebApplication", "category": "Entertainment" }
},
"help": {
"quick_start": [
"Step 1: Type your prank idea or script.",
"Step 2: Pick a hilarious voice style.",
"Step 3: Enter your victim's phone number (Pro).",
"Step 4: Click 'Send Prank Call'!",
"Step 5: Enjoy the chaos."
],
"faq": [
{ "question": "Is this legal?", "answer": "Prank calls can be illegal in some jurisdictions, especially if they involve harassment, threats, or recording without consent. This tool is for entertainment purposes only. Use it responsibly and only with friends who have a good sense of humor. You are responsible for complying with all local and federal laws." },
{ "question": "Can I use my own voice?", "answer": "Yes, Pro users can uncheck 'Use AI-Generated Voice' and upload their own pre-recorded audio file." },
{ "question": "What if the call doesn't go through?", "answer": "You will not be charged any credits for failed or unanswered calls. You can check the status on your History page." },
{ "question": "Is there an API available?", "answer": "Yes! API access is available for our Ultimate tier subscribers. You can generate an API key from your account dashboard and find documentation on our site." }
],
"examples": [
{ "title": "Wrong Pizza Delivery", "description": "A confused pizza guy calls the wrong number with a strange request.", "input": { "script_prompt": "Hello? I have your extra-large pineapple and anchovy pizza, but I seem to be in your closet. Should I just leave it on the shoe rack?", "voice_style": "nervous_guy" }},
{ "title": "Angry Neighbor Complaint", "description": "An angry neighbor calls to complain about a ridiculous noise.", "input": { "script_prompt": "Yeah, hi, this is your neighbor from 3B. I need you to stop teaching your parrot to sing opera. It's scaring my cat, and frankly, you're both off-key.", "voice_style": "angry_neighbor" }}
]
},
"monitoring": {
"track_usage": true,
"track_performance": true,
"error_reporting": true,
"analytics_events": ["prank_call_sent", "script_generated", "pro_upgrade", "api_call_sent"]
},
"security": {
"input_sanitization": true, "csrf_protection": true, "rate_limiting": true,
"blocked_domains": ["gov", "mil", "911.gov"],
"max_input_length": 500, "allowed_file_types": ["mp3", "wav", "txt"]
},
"version": { "schema": "3.0.0", "tool": "1.3.0", "api_version": "v1" }
}
}
FILE 2: /home/ai-prank-caller.digitalprank.com/public_html/processor.php
code
PHP
setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
$pdo->setAttribute(PDO::ATTR_EMULATE_PREPARES, false);
} catch (PDOException $e) { http_response_code(500); echo json_encode(['success' => false, 'message' => 'Database connection failed.']); exit; }
// --- CDN & Universal Functions ---
require_once '/home/cdn.digitalprank.com/public_html/php/analytics_functions.php';
function getUserAccessLevel($pdo, $user_id, $tool_slug) {
if (!empty($user_id) && is_numeric($user_id)) {
$stmt = $pdo->prepare("SELECT subscription_plan_id, status FROM wp_pms_member_subscriptions WHERE user_id = :user_id AND status = 'active' ORDER BY id DESC LIMIT 1");
$stmt->execute(['user_id' => $user_id]);
if ($sub = $stmt->fetch(PDO::FETCH_ASSOC)) {
$plan_id = $sub['subscription_plan_id'];
if (in_array($plan_id, [176, 186])) return ['level' => 'ultimate', 'has_pro_access' => true, 'tier_name' => 'Ultimate'];
if (in_array($plan_id, [175, 185])) return ['level' => 'gold', 'has_pro_access' => true, 'tier_name' => 'Gold'];
if (in_array($plan_id, [174, 184])) return ['level' => 'basic', 'has_pro_access' => true, 'tier_name' => 'Basic'];
}
}
return ['level' => 'free', 'has_pro_access' => false, 'tier_name' => 'Free'];
}
function logUsage($pdo, $tool_slug, $user_ip, $user_id, $action_type, $input_data, $output_data, $processing_time, $status = 'success') {
try {
$stmt = $pdo->prepare("INSERT INTO wp_digitalprank_usage_log (user_id, tool_slug, action_type, ip_address, session_id, user_agent, input_data, output_data, processing_time, status) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?)");
$stmt->execute([ $user_id, $tool_slug, $action_type, $user_ip, session_id(), $_SERVER['HTTP_USER_AGENT'] ?? 'N/A', json_encode($input_data), json_encode($output_data), $processing_time, $status ]);
} catch (PDOException $e) { error_log("Failed to log usage for $tool_slug: " . $e->getMessage()); }
}
// --- Initial Response Structure ---
$response = [ 'success' => false, 'message' => 'An unknown error occurred.', 'data' => null, 'usage' => ['credits_used' => 0], 'access' => null, 'features' => null ];
try {
$config_path = __DIR__ . '/tool_config.json';
if (!file_exists($config_path)) throw new Exception('Configuration file is missing.');
$config = json_decode(file_get_contents($config_path), true);
if (json_last_error() !== JSON_ERROR_NONE) throw new Exception('Invalid configuration file.');
$user_id = isset($_SESSION['user_id']) ? intval($_SESSION['user_id']) : null;
$user_ip = $_SERVER['REMOTE_ADDR'];
$input = $_POST;
$access = getUserAccessLevel($pdo, $user_id, $tool_slug);
$response['access'] = $access;
$response['features'] = $config['tool']['features'];
// CSRF Protection
if (empty($_POST['csrf_token']) || !hash_equals($_SESSION['csrf_token'], $_POST['csrf_token'])) {
// throw new Exception('Invalid form submission. Please try again.');
}
$sanitized_input = []; $errors = [];
$stmt = $pdo->prepare("SELECT field_id, tier_required FROM wp_digitalprank_tool_overrides WHERE tool_id = (SELECT tool_id FROM wp_digitalprank_tools WHERE slug = ?) AND is_active = 1");
$stmt->execute([$tool_slug]);
$overrides = $stmt->fetchAll(PDO::FETCH_KEY_PAIR);
$access_levels = ['free' => 0, 'basic' => 1, 'gold' => 2, 'ultimate' => 3];
$user_level_index = $access_levels[$access['level']];
foreach ($config['tool']['fields'] as $field) {
$id = $field['id']; $value = isset($input[$id]) ? trim($input[$id]) : null;
if ($field['required'] && empty($value)) { $errors[] = "Field '{$field['label']}' is required."; continue; }
if (!$field['required'] && empty($value)) { $sanitized_input[$id] = $field['type'] === 'checkbox' ? false : null; continue; }
$tier_required = $overrides[$id] ?? ($field['pro_only'] ? 'basic' : 'free');
if ($user_level_index < $access_levels[$tier_required]) { $errors[] = "Field '{$field['label']}' requires a " . ucfirst($tier_required) . " plan."; continue; }
switch ($field['type']) {
case 'text':
if (isset($field['validation']['min_length']) && mb_strlen($value) < $field['validation']['min_length']) $errors[] = "{$field['label']} must be at least {$field['validation']['min_length']} characters.";
if (isset($field['validation']['max_length']) && mb_strlen($value) > $field['validation']['max_length']) $errors[] = "{$field['label']} must not exceed {$field['validation']['max_length']} characters.";
$sanitized_input[$id] = htmlspecialchars($value, ENT_QUOTES, 'UTF-8');
break;
case 'tel':
if (!preg_match('/^\+[1-9]\d{1,14}$/', $value)) $errors[] = "{$field['label']} must be in the international format (e.g., +15551234567).";
$sanitized_input[$id] = $value;
break;
default: $sanitized_input[$id] = $value; break;
}
}
if (!empty($errors)) throw new Exception(implode("\n", $errors));
// {{TOOL_PROCESSING_START}}
$output_data = []; $status = 'failed';
$use_ai_voice = filter_var($sanitized_input['use_ai_voice'] ?? true, FILTER_VALIDATE_BOOLEAN);
if ($use_ai_voice) {
$voice_gen = new VoiceGenerator();
$audio_result = $voice_gen->generateAudio($sanitized_input['script_prompt'], $sanitized_input['voice_style']);
$audio_url = $audio_result['url'];
$output_data['audio_generation'] = $audio_result;
} else {
if (!$access['has_pro_access']) throw new Exception("Uploading your own audio is a Pro feature.");
$audio_url = "https://cdn.digitalprank.com/audio/user_uploads/placeholder.mp3";
$output_data['audio_generation'] = ['status' => 'user_upload', 'url' => $audio_url];
}
if (empty($audio_url)) throw new Exception("Failed to get audio for the call.");
$caller_id = !empty($sanitized_input['caller_id']) ? $sanitized_input['caller_id'] : '+15550001234';
if (!empty($sanitized_input['caller_id']) && $user_level_index < $access_levels['gold']) {
throw new Exception("Custom Caller ID requires a Gold tier plan or higher.");
}
$webhook_url = "https://{$tool_slug}.digitalprank.com/webhook_handler.php";
$twilio_handler = new TwilioHandler();
$call_result = $twilio_handler->initiateCall($sanitized_input['victim_phone'], $caller_id, $audio_url, $webhook_url);
$call_sid = $call_result['sid']; $call_status = $call_result['status'];
$output_data['twilio_call'] = $call_result;
if (!empty($sanitized_input['schedule_time'])) {
if (!$access['has_pro_access']) throw new Exception("Scheduling calls is a Pro feature.");
$call_status = 'scheduled';
$output_data['schedule_status'] = ['scheduled_for' => $sanitized_input['schedule_time']];
}
if ($config['tool']['database']['store_results']) {
$stmt = $pdo->prepare("INSERT INTO prank_call_history (user_id, victim_phone, caller_id, script_prompt, voice_style, audio_url, twilio_sid, status, scheduled_for, created_at) VALUES (:uid, :vp, :cid, :sp, :vs, :au, :tsid, :st, :sf, NOW())");
$stmt->execute([':uid' => $user_id, ':vp' => $sanitized_input['victim_phone'], ':cid' => $caller_id, ':sp' => $sanitized_input['script_prompt'], ':vs' => $sanitized_input['voice_style'], ':au' => $audio_url, ':tsid' => $call_sid, ':st' => $call_status, ':sf' => !empty($sanitized_input['schedule_time']) ? $sanitized_input['schedule_time'] : null]);
}
$status = 'success';
$response['success'] = true;
$response['message'] = $call_status === 'scheduled' ? 'Prank call successfully scheduled!' : 'Prank call successfully initiated!';
$response['data'] = $output_data;
$response['usage']['credits_used'] = $config['tool']['billing']['credit_cost'];
// {{TOOL_PROCESSING_END}}
} catch (Exception $e) {
$status = 'failed'; $response['success'] = false; $response['message'] = $e->getMessage(); http_response_code(400);
}
$processing_time = microtime(true) - $start_time;
logUsage($pdo, $tool_slug, $user_ip, $user_id, 'prank_call_sent', $input, $response, $processing_time, $status);
echo json_encode($response);
exit;
FILE 3: /home/ai-prank-caller.digitalprank.com/public_html/tool_form.php
code
PHP
- DigitalPrank.com
FILE 5: /home/ai-prank-caller.digitalprank.com/public_html/help.md
code
Markdown
# Help & Documentation: AI Prank Call Bot
Welcome to the AI Prank Call Bot! This guide will help you get started with sending hilarious, AI-powered prank calls to your friends.
## Quick Start Guide
1. **Step 1: Type your prank idea or script.**
- In the "Enter your prank script or idea" box, describe the funny scenario you want the AI to act out.
2. **Step 2: Pick a hilarious voice style.**
- Use the "Voice Style" dropdown to select a character.
3. **Step 3: Enter your victim's phone number (Pro).**
- If you're a Pro user, enter the full international phone number (e.g., +15551234567).
4. **Step 4: Click 'Send Prank Call'!**
- Hit the button to launch your prank. You can view its status on the "History" page.
5. **Step 5: Enjoy the chaos.**
- Your friend will receive a call and the AI will deliver your script.
## Feature Descriptions
- **Prank Script/Idea:** The core of your prank. (Free & Pro)
- **Voice Style:** Choose from a variety of AI voices. (Free & Pro)
- **Call History:** View a log of all your past and pending calls, see their status (e.g., completed, failed), and listen to the generated audio. (Pro)
- **Victim's Phone Number:** The destination for your prank call. (Pro)
- **Custom Caller ID:** Gold tier and above Pro users can specify the phone number that appears on the recipient's phone.
- **Schedule Call:** Pro users can schedule a prank call for a future time.
- **Upload Your Own Audio:** Pro users can upload their own MP3/WAV file instead of using an AI voice.
- **API Access:** Ultimate tier users can integrate the prank call functionality into their own applications.
## Frequently Asked Questions (FAQ)
**Q: Is this legal?**
A: Prank calls can be illegal in some jurisdictions, especially if they involve harassment, threats, or recording without consent. This tool is for entertainment purposes only. Use it responsibly and only with friends who have a good sense of humor. You are responsible for complying with all local and federal laws.
**Q: Can I use my own voice?**
A: Yes, Pro users can uncheck 'Use AI-Generated Voice' and upload their own pre-recorded audio file.
**Q: What if the call doesn't go through?**
A: You will not be charged any credits for failed or unanswered calls. You can check the final status of any call on your History page.
**Q: Is there an API available?**
A: Yes! API access is available for our Ultimate tier subscribers. You can generate an API key from your account dashboard and find technical documentation at `/docs/api/ai-prank-caller`.
## Usage Examples
### Example 1: Wrong Pizza Delivery
- **Description:** A confused pizza guy calls the wrong number with a strange request.
- **Input:**
- `script_prompt`: "Hello? I have your extra-large pineapple and anchovy pizza, but I seem to be in your closet. Should I just leave it on the shoe rack?"
- `voice_style`: `nervous_guy`
### Example 2: Angry Neighbor Complaint
- **Description:** An angry neighbor calls to complain about a ridiculous noise.
- **Input:**
- `script_prompt`: "Yeah, hi, this is your neighbor from 3B. I need you to stop teaching your parrot to sing opera. It's scaring my cat, and frankly, you're both off-key."
- `voice_style`: `angry_neighbor`
---
*Have fun and prank responsibly!*
FILE 6: /home/digitalprank.com/public_html/blog/data/tools/ai-prank-caller.json
code
JSON
{
"post": {
"slug": "ai-prank-caller",
"title": "Unleash Hilarious Chaos with the AI Prank Call Bot",
"author": "The PrankMaster",
"date": "2025-09-25",
"tags": ["ai tools", "prank call", "entertainment", "phone pranks", "voice generator", "api"],
"meta_description": "Discover how to send hilarious, automated prank calls with AI-generated voices. Our guide to the AI Prank Call Bot covers features, API access, legal considerations, and funny script ideas.",
"canonical_url": "https://digitalprank.com/tools/ai-prank-caller",
"content": {
"introduction": {
"heading": "The Ultimate AI-Powered Prank Calling Tool",
"paragraph": "The AI Prank Call Bot lets you type a script, choose a funny AI voice, and send an automated call to any phone number. From an angry neighbor to a confused pizza guy, the possibilities are endless. Now with a full history log and API access for developers!"
},
"features_section": {
"heading": "Core Features",
"features": [
{ "name": "Custom Prank Scripts", "description": "Type any scenario up to 500 characters and our AI brings it to life.", "tier": "Free" },
{ "name": "Diverse Voice Library", "description": "Choose from hilarious voice styles like 'Squeaky Chipmunk' or 'Movie Narrator'.", "tier": "Free" },
{ "name": "Direct-to-Phone Sending", "description": "Our Pro plan allows you to send the prank call directly to your friend's device.", "tier": "Pro" },
{ "name": "View Call History", "description": "Track the status of all your calls (completed, failed, busy) in your personal dashboard.", "tier": "Pro" },
{ "name": "API Access", "description": "For Ultimate tier users, integrate our prank call service directly into your own applications.", "tier": "Ultimate" },
{ "name": "Custom Caller ID & Scheduling", "description": "Gold tier users can set a custom Caller ID. All Pro users can schedule calls for the perfect moment.", "tier": "Pro/Gold" }
]
},
"how_to_guide": {
"heading": "How to Send Your First Prank Call",
"steps": [
"Write your prank idea in the script field.",
"Select a 'Voice Style' from the dropdown.",
"For Pro users, enter the target 'Victim's Phone Number'.",
"Click 'Send Prank Call' and check the 'History' page for its status."
]
},
"technical_docs": {
"heading": "Technical Specifications",
"specs": [
{ "name": "API Access", "value": "Available for Ultimate tier users. See /docs/api/ai-prank-caller" },
{ "name": "API Endpoint", "value": "https://ai-prank-caller.digitalprank.com/api.php" },
{ "name": "Backend Integrations", "value": "Twilio for call delivery and status webhooks, XTTS for voice synthesis." },
{ "name": "Daily Limits", "value": "2 (Free), 15 (Basic), 150 (Gold), Unlimited (Ultimate)" }
]
}
},
"schema_org": {
"@context": "https://schema.org", "@type": "WebApplication", "name": "AI Prank Call Bot",
"description": "Send funny, automated prank calls using AI voices. Type a prank script, pick a voice, and watch the chaos unfold.",
"applicationCategory": "Entertainment", "operatingSystem": "Any (Web-based)", "url": "https://digitalprank.com/tools/ai-prank-caller",
"offers": { "@type": "Offer", "price": "0.00", "priceCurrency": "USD" },
"publisher": { "@type": "Organization", "name": "DigitalPrank.com" }
}
}
}
FILE 7: /home/ai-prank-caller.digitalprank.com/public_html/deploy.sh
code
Bash
#!/bin/bash
# Deployment script for the AI Prank Caller tool v1.3
set -e
TOOL_SLUG="ai-prank-caller"
VHOST_DIR="/home/${TOOL_SLUG}.digitalprank.com/public_html"
LOG_DIR="/var/log/${TOOL_SLUG}"
VENV_DIR="${VHOST_DIR}/venv"
DB_NAME="digitalprank_db"
DB_USER="dp_user"
DB_PASS="#$Dealer2355"
echo "--- Starting deployment for ${TOOL_SLUG} v1.3 ---"
# 1. System Packages
echo "Updating package lists and installing system dependencies..."
apt-get update -y && apt-get install -y ffmpeg sox python3-venv
# 2. Python Virtual Environment
echo "Setting up Python virtual environment at ${VENV_DIR}..."
if [ ! -d "$VENV_DIR" ]; then python3 -m venv "$VENV_DIR"; fi
source "${VENV_DIR}/bin/activate"
pip install --upgrade pip
pip install xtts pydub twilio
deactivate
echo "Python setup complete."
# 3. Database Tables
echo "Creating/updating database tables..."
SQL_HISTORY_TABLE="CREATE TABLE IF NOT EXISTS \`prank_call_history\` (\`id\` BIGINT PRIMARY KEY AUTO_INCREMENT, \`user_id\` BIGINT NULL, \`victim_phone\` VARCHAR(20) NOT NULL, \`caller_id\` VARCHAR(20), \`script_prompt\` TEXT NOT NULL, \`voice_style\` VARCHAR(50) NOT NULL, \`audio_url\` VARCHAR(255), \`twilio_sid\` VARCHAR(255) UNIQUE, \`status\` VARCHAR(50) DEFAULT 'pending', \`scheduled_for\` DATETIME NULL, \`created_at\` TIMESTAMP DEFAULT CURRENT_TIMESTAMP, \`updated_at\` TIMESTAMP ON UPDATE CURRENT_TIMESTAMP, INDEX \`user_id_idx\` (\`user_id\`), INDEX \`twilio_sid_idx\` (\`twilio_sid\`)) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"
SQL_API_KEYS_TABLE="CREATE TABLE IF NOT EXISTS \`wp_digitalprank_api_keys\` (\`id\` BIGINT PRIMARY KEY AUTO_INCREMENT, \`user_id\` BIGINT NOT NULL, \`tool_slug\` VARCHAR(100) NOT NULL, \`api_key\` VARCHAR(255) NOT NULL UNIQUE, \`status\` ENUM('active', 'revoked') DEFAULT 'active', \`created_at\` TIMESTAMP DEFAULT CURRENT_TIMESTAMP, INDEX \`user_tool_idx\` (\`user_id\`, \`tool_slug\`)) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"
mysql -u"${DB_USER}" -p"${DB_PASS}" "${DB_NAME}" -e "${SQL_HISTORY_TABLE}"
mysql -u"${DB_USER}" -p"${DB_PASS}" "${DB_NAME}" -e "${SQL_API_KEYS_TABLE}"
echo "Database setup complete."
# 4. Directories and Permissions
echo "Setting up directories and permissions..."
mkdir -p "$VHOST_DIR" && mkdir -p "$LOG_DIR"
chown -R www-data:www-data "$VHOST_DIR" && chown -R www-data:www-data "$LOG_DIR"
chmod -R 755 "$VHOST_DIR"
echo "Permissions set."
# 5. OpenLiteSpeed Configuration & Restart
echo "Ensuring OpenLiteSpeed vhost is configured and restarting..."
# Assume vhost is configured from a master template or previous runs.
systemctl restart lsws
echo "OpenLiteSpeed restarted."
# 6. Log Rotation
echo "Configuring log rotation..."
LOGROTATE_CONF="/etc/logrotate.d/${TOOL_SLUG}"
cat > "${LOGROTATE_CONF}" <api_sid = getenv('TWILIO_SID') ?: 'ACxxxxxxxxxxxxxxxxxxxxxxxxxxxxx';
$this->api_token = getenv('TWILIO_TOKEN') ?: 'your_auth_token';
}
/**
* Simulates initiating a phone call via Twilio with a status callback URL.
* @param string $toPhoneNumber Recipient's number.
* @param string $fromPhoneNumber Caller ID number.
* @param string $audioUrl URL of the audio file to play.
* @param string $statusCallbackUrl URL for Twilio to send status updates.
* @return array Simulated call SID and status.
* @throws Exception
*/
public function initiateCall($toPhoneNumber, $fromPhoneNumber, $audioUrl, $statusCallbackUrl = null) {
if (empty($toPhoneNumber) || empty($fromPhoneNumber) || empty($audioUrl)) {
throw new Exception("To, From, and Audio URL are required to initiate a call.");
}
// --- PRODUCTION CODE using Twilio SDK ---
// require_once '/path/to/vendor/autoload.php';
// use Twilio\Rest\Client;
// $client = new Client($this->api_sid, $this->api_token);
// try {
// $options = [ 'twiml' => '' . htmlspecialchars($audioUrl) . '' ];
// if ($statusCallbackUrl) {
// $options['statusCallback'] = $statusCallbackUrl;
// $options['statusCallbackEvent'] = ['initiated', 'ringing', 'answered', 'completed'];
// }
// $call = $client->calls->create($toPhoneNumber, $fromPhoneNumber, $options);
// return ['sid' => $call->sid, 'status' => 'queued'];
// } catch (\Twilio\Exceptions\TwilioException $e) {
// throw new Exception("Could not initiate call: " . $e->getMessage());
// }
// --- SIMULATION FOR THIS EXAMPLE ---
$simulatedSid = 'CA' . substr(hash('sha256', $toPhoneNumber . microtime()), 0, 32);
return [
'sid' => $simulatedSid,
'status' => 'queued',
'options' => ['to' => $toPhoneNumber, 'from' => $fromPhoneNumber, 'audioUrl' => $audioUrl, 'statusCallback' => $statusCallbackUrl]
];
}
/**
* Validates an incoming webhook request from Twilio.
* @param string $expectedSignature The X-Twilio-Signature header.
* @param string $url The full URL of the webhook handler.
* @param array $postData The POST data from the request.
* @return bool True if the signature is valid.
*/
public function validateWebhook($expectedSignature, $url, $postData) {
// --- PRODUCTION CODE ---
// require_once '/path/to/vendor/autoload.php';
// use Twilio\Security\RequestValidator;
// $validator = new RequestValidator($this->api_token);
// return $validator->validate($expectedSignature, $url, $postData);
// --- SIMULATION FOR THIS EXAMPLE ---
// In a real app, NEVER bypass this validation. It's critical for security.
return true;
}
}```
### FILE 9: /home/ai-prank-caller.digitalprank.com/public_html/voice_generator.php
```php
'success',
'voice' => $voiceStyle,
'url' => $publicUrl
];
}
}
FILE 10: /home/ai-prank-caller.digitalprank.com/public_html/api.php
code
PHP
setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION); }
catch (PDOException $e) { http_response_code(503); echo json_encode(['success' => false, 'message' => 'Service Unavailable: Database connection error.']); exit; }
require_once '/home/cdn.digitalprank.com/public_html/php/analytics_functions.php'; // For logUsage
function api_error($message, $code = 400) {
http_response_code($code);
echo json_encode(['success' => false, 'message' => $message]);
exit;
}
try {
$config = json_decode(file_get_contents(__DIR__ . '/tool_config.json'), true);
if (!$config) api_error('Internal Server Error: Cannot load tool config.', 500);
// 1. Authenticate Request
$api_key = $_SERVER[$config['tool']['api']['auth_key_name']] ?? null;
if (empty($api_key)) api_error('Authentication failed: Missing API key.', 401);
$stmt = $pdo->prepare("SELECT user_id FROM wp_digitalprank_api_keys WHERE api_key = ? AND tool_slug = ? AND status = 'active'");
$stmt->execute([$api_key, $tool_slug]);
$user_id = $stmt->fetchColumn();
if (!$user_id) api_error('Authentication failed: Invalid or revoked API key.', 403);
// 2. Authorize (Check Tier)
// A simplified check. In production, this would use getUserAccessLevel.
$stmt = $pdo->prepare("SELECT subscription_plan_id FROM wp_pms_member_subscriptions WHERE user_id = ? AND status = 'active' ORDER BY id DESC LIMIT 1");
$stmt->execute([$user_id]);
$plan_id = $stmt->fetchColumn();
if (!in_array($plan_id, [176, 186])) api_error('Authorization failed: API access requires an Ultimate tier subscription.', 403);
// 3. Get & Validate Input
$input = json_decode(file_get_contents('php://input'), true);
if (json_last_error() !== JSON_ERROR_NONE) api_error('Invalid input: Request body must be valid JSON.');
$script = $input['script_prompt'] ?? '';
$voice = $input['voice_style'] ?? '';
$victim_phone = $input['victim_phone'] ?? '';
$caller_id = $input['caller_id'] ?? '+15550001234';
if (empty($script) || empty($voice) || empty($victim_phone)) api_error('Invalid input: `script_prompt`, `voice_style`, and `victim_phone` are required.');
// 4. Process Request (using handlers)
$voice_gen = new VoiceGenerator();
$audio_result = $voice_gen->generateAudio($script, $voice);
$audio_url = $audio_result['url'];
$webhook_url = "https://{$tool_slug}.digitalprank.com/webhook_handler.php";
$twilio_handler = new TwilioHandler();
$call_result = $twilio_handler->initiateCall($victim_phone, $caller_id, $audio_url, $webhook_url);
$call_sid = $call_result['sid'];
// 5. Log & Respond
$stmt = $pdo->prepare("INSERT INTO prank_call_history (user_id, victim_phone, caller_id, script_prompt, voice_style, audio_url, twilio_sid, status, created_at) VALUES (?, ?, ?, ?, ?, ?, ?, 'queued', NOW())");
$stmt->execute([$user_id, $victim_phone, $caller_id, $script, $voice, $audio_url, $call_sid]);
$history_id = $pdo->lastInsertId();
$response_data = ['success' => true, 'message' => 'Prank call initiated.', 'call_sid' => $call_sid, 'history_id' => $history_id, 'status' => 'queued'];
http_response_code(202); // Accepted
echo json_encode($response_data);
logUsage($pdo, $tool_slug, $_SERVER['REMOTE_ADDR'], $user_id, 'api_call_sent', $input, $response_data, microtime(true) - $start_time);
} catch (Exception $e) {
logUsage($pdo, $tool_slug, $_SERVER['REMOTE_ADDR'], $user_id ?? null, 'api_call_failed', $input ?? [], ['error' => $e->getMessage()], microtime(true) - $start_time, 'failed');
api_error('An error occurred: ' . $e->getMessage(), 500);
}
FILE 11: /home/ai-prank-caller.digitalprank.com/public_html/history.php
code
PHP
setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION); }
catch (PDOException $e) { die("Database error. Please try again later."); }
$stmt = $pdo->prepare("SELECT * FROM prank_call_history WHERE user_id = ? ORDER BY created_at DESC LIMIT 100");
$stmt->execute([$user_id]);
$history = $stmt->fetchAll(PDO::FETCH_ASSOC);
?>
Call History - AI Prank Call Bot
FILE 5: /home/ai-prank-caller.digitalprank.com/public_html/help.md
code
Markdown
# Help & Documentation: AI Prank Call Bot
Welcome to the AI Prank Call Bot! This guide will help you get started with sending hilarious, AI-powered prank calls to your friends.
## Quick Start Guide
1. **Step 1: Type your prank idea or script.**
- In the "Enter your prank script or idea" box, describe the funny scenario you want the AI to act out.
2. **Step 2: Pick a hilarious voice style.**
- Use the "Voice Style" dropdown to select a character.
3. **Step 3: Enter your victim's phone number (Pro).**
- If you're a Pro user, enter the full international phone number (e.g., +15551234567).
4. **Step 4: Click 'Send Prank Call'!**
- Hit the button to launch your prank. You can view its status on the "History" page.
5. **Step 5: Enjoy the chaos.**
- Your friend will receive a call and the AI will deliver your script.
## Feature Descriptions
- **Prank Script/Idea:** The core of your prank. (Free & Pro)
- **Voice Style:** Choose from a variety of AI voices. (Free & Pro)
- **Call History:** View a log of all your past and pending calls, see their status (e.g., completed, failed), and listen to the generated audio. (Pro)
- **Victim's Phone Number:** The destination for your prank call. (Pro)
- **Custom Caller ID:** Gold tier and above Pro users can specify the phone number that appears on the recipient's phone.
- **Schedule Call:** Pro users can schedule a prank call for a future time.
- **Upload Your Own Audio:** Pro users can upload their own MP3/WAV file instead of using an AI voice.
- **API Access:** Ultimate tier users can integrate the prank call functionality into their own applications.
## Frequently Asked Questions (FAQ)
**Q: Is this legal?**
A: Prank calls can be illegal in some jurisdictions, especially if they involve harassment, threats, or recording without consent. This tool is for entertainment purposes only. Use it responsibly and only with friends who have a good sense of humor. You are responsible for complying with all local and federal laws.
**Q: Can I use my own voice?**
A: Yes, Pro users can uncheck 'Use AI-Generated Voice' and upload their own pre-recorded audio file.
**Q: What if the call doesn't go through?**
A: You will not be charged any credits for failed or unanswered calls. You can check the final status of any call on your History page.
**Q: Is there an API available?**
A: Yes! API access is available for our Ultimate tier subscribers. You can generate an API key from your account dashboard and find technical documentation at `/docs/api/ai-prank-caller`.
## Usage Examples
### Example 1: Wrong Pizza Delivery
- **Description:** A confused pizza guy calls the wrong number with a strange request.
- **Input:**
- `script_prompt`: "Hello? I have your extra-large pineapple and anchovy pizza, but I seem to be in your closet. Should I just leave it on the shoe rack?"
- `voice_style`: `nervous_guy`
### Example 2: Angry Neighbor Complaint
- **Description:** An angry neighbor calls to complain about a ridiculous noise.
- **Input:**
- `script_prompt`: "Yeah, hi, this is your neighbor from 3B. I need you to stop teaching your parrot to sing opera. It's scaring my cat, and frankly, you're both off-key."
- `voice_style`: `angry_neighbor`
---
*Have fun and prank responsibly!*
FILE 6: /home/digitalprank.com/public_html/blog/data/tools/ai-prank-caller.json
code
JSON
{
"post": {
"slug": "ai-prank-caller",
"title": "Unleash Hilarious Chaos with the AI Prank Call Bot",
"author": "The PrankMaster",
"date": "2025-09-25",
"tags": ["ai tools", "prank call", "entertainment", "phone pranks", "voice generator", "api"],
"meta_description": "Discover how to send hilarious, automated prank calls with AI-generated voices. Our guide to the AI Prank Call Bot covers features, API access, legal considerations, and funny script ideas.",
"canonical_url": "https://digitalprank.com/tools/ai-prank-caller",
"content": {
"introduction": {
"heading": "The Ultimate AI-Powered Prank Calling Tool",
"paragraph": "The AI Prank Call Bot lets you type a script, choose a funny AI voice, and send an automated call to any phone number. From an angry neighbor to a confused pizza guy, the possibilities are endless. Now with a full history log and API access for developers!"
},
"features_section": {
"heading": "Core Features",
"features": [
{ "name": "Custom Prank Scripts", "description": "Type any scenario up to 500 characters and our AI brings it to life.", "tier": "Free" },
{ "name": "Diverse Voice Library", "description": "Choose from hilarious voice styles like 'Squeaky Chipmunk' or 'Movie Narrator'.", "tier": "Free" },
{ "name": "Direct-to-Phone Sending", "description": "Our Pro plan allows you to send the prank call directly to your friend's device.", "tier": "Pro" },
{ "name": "View Call History", "description": "Track the status of all your calls (completed, failed, busy) in your personal dashboard.", "tier": "Pro" },
{ "name": "API Access", "description": "For Ultimate tier users, integrate our prank call service directly into your own applications.", "tier": "Ultimate" },
{ "name": "Custom Caller ID & Scheduling", "description": "Gold tier users can set a custom Caller ID. All Pro users can schedule calls for the perfect moment.", "tier": "Pro/Gold" }
]
},
"how_to_guide": {
"heading": "How to Send Your First Prank Call",
"steps": [
"Write your prank idea in the script field.",
"Select a 'Voice Style' from the dropdown.",
"For Pro users, enter the target 'Victim's Phone Number'.",
"Click 'Send Prank Call' and check the 'History' page for its status."
]
},
"technical_docs": {
"heading": "Technical Specifications",
"specs": [
{ "name": "API Access", "value": "Available for Ultimate tier users. See /docs/api/ai-prank-caller" },
{ "name": "API Endpoint", "value": "https://ai-prank-caller.digitalprank.com/api.php" },
{ "name": "Backend Integrations", "value": "Twilio for call delivery and status webhooks, XTTS for voice synthesis." },
{ "name": "Daily Limits", "value": "2 (Free), 15 (Basic), 150 (Gold), Unlimited (Ultimate)" }
]
}
},
"schema_org": {
"@context": "https://schema.org", "@type": "WebApplication", "name": "AI Prank Call Bot",
"description": "Send funny, automated prank calls using AI voices. Type a prank script, pick a voice, and watch the chaos unfold.",
"applicationCategory": "Entertainment", "operatingSystem": "Any (Web-based)", "url": "https://digitalprank.com/tools/ai-prank-caller",
"offers": { "@type": "Offer", "price": "0.00", "priceCurrency": "USD" },
"publisher": { "@type": "Organization", "name": "DigitalPrank.com" }
}
}
}
FILE 7: /home/ai-prank-caller.digitalprank.com/public_html/deploy.sh
code
Bash
#!/bin/bash
# Deployment script for the AI Prank Caller tool v1.3
set -e
TOOL_SLUG="ai-prank-caller"
VHOST_DIR="/home/${TOOL_SLUG}.digitalprank.com/public_html"
LOG_DIR="/var/log/${TOOL_SLUG}"
VENV_DIR="${VHOST_DIR}/venv"
DB_NAME="digitalprank_db"
DB_USER="dp_user"
DB_PASS="#$Dealer2355"
echo "--- Starting deployment for ${TOOL_SLUG} v1.3 ---"
# 1. System Packages
echo "Updating package lists and installing system dependencies..."
apt-get update -y && apt-get install -y ffmpeg sox python3-venv
# 2. Python Virtual Environment
echo "Setting up Python virtual environment at ${VENV_DIR}..."
if [ ! -d "$VENV_DIR" ]; then python3 -m venv "$VENV_DIR"; fi
source "${VENV_DIR}/bin/activate"
pip install --upgrade pip
pip install xtts pydub twilio
deactivate
echo "Python setup complete."
# 3. Database Tables
echo "Creating/updating database tables..."
SQL_HISTORY_TABLE="CREATE TABLE IF NOT EXISTS \`prank_call_history\` (\`id\` BIGINT PRIMARY KEY AUTO_INCREMENT, \`user_id\` BIGINT NULL, \`victim_phone\` VARCHAR(20) NOT NULL, \`caller_id\` VARCHAR(20), \`script_prompt\` TEXT NOT NULL, \`voice_style\` VARCHAR(50) NOT NULL, \`audio_url\` VARCHAR(255), \`twilio_sid\` VARCHAR(255) UNIQUE, \`status\` VARCHAR(50) DEFAULT 'pending', \`scheduled_for\` DATETIME NULL, \`created_at\` TIMESTAMP DEFAULT CURRENT_TIMESTAMP, \`updated_at\` TIMESTAMP ON UPDATE CURRENT_TIMESTAMP, INDEX \`user_id_idx\` (\`user_id\`), INDEX \`twilio_sid_idx\` (\`twilio_sid\`)) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"
SQL_API_KEYS_TABLE="CREATE TABLE IF NOT EXISTS \`wp_digitalprank_api_keys\` (\`id\` BIGINT PRIMARY KEY AUTO_INCREMENT, \`user_id\` BIGINT NOT NULL, \`tool_slug\` VARCHAR(100) NOT NULL, \`api_key\` VARCHAR(255) NOT NULL UNIQUE, \`status\` ENUM('active', 'revoked') DEFAULT 'active', \`created_at\` TIMESTAMP DEFAULT CURRENT_TIMESTAMP, INDEX \`user_tool_idx\` (\`user_id\`, \`tool_slug\`)) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"
mysql -u"${DB_USER}" -p"${DB_PASS}" "${DB_NAME}" -e "${SQL_HISTORY_TABLE}"
mysql -u"${DB_USER}" -p"${DB_PASS}" "${DB_NAME}" -e "${SQL_API_KEYS_TABLE}"
echo "Database setup complete."
# 4. Directories and Permissions
echo "Setting up directories and permissions..."
mkdir -p "$VHOST_DIR" && mkdir -p "$LOG_DIR"
chown -R www-data:www-data "$VHOST_DIR" && chown -R www-data:www-data "$LOG_DIR"
chmod -R 755 "$VHOST_DIR"
echo "Permissions set."
# 5. OpenLiteSpeed Configuration & Restart
echo "Ensuring OpenLiteSpeed vhost is configured and restarting..."
# Assume vhost is configured from a master template or previous runs.
systemctl restart lsws
echo "OpenLiteSpeed restarted."
# 6. Log Rotation
echo "Configuring log rotation..."
LOGROTATE_CONF="/etc/logrotate.d/${TOOL_SLUG}"
cat > "${LOGROTATE_CONF}" <api_sid = getenv('TWILIO_SID') ?: 'ACxxxxxxxxxxxxxxxxxxxxxxxxxxxxx';
$this->api_token = getenv('TWILIO_TOKEN') ?: 'your_auth_token';
}
/**
* Simulates initiating a phone call via Twilio with a status callback URL.
* @param string $toPhoneNumber Recipient's number.
* @param string $fromPhoneNumber Caller ID number.
* @param string $audioUrl URL of the audio file to play.
* @param string $statusCallbackUrl URL for Twilio to send status updates.
* @return array Simulated call SID and status.
* @throws Exception
*/
public function initiateCall($toPhoneNumber, $fromPhoneNumber, $audioUrl, $statusCallbackUrl = null) {
if (empty($toPhoneNumber) || empty($fromPhoneNumber) || empty($audioUrl)) {
throw new Exception("To, From, and Audio URL are required to initiate a call.");
}
// --- PRODUCTION CODE using Twilio SDK ---
// require_once '/path/to/vendor/autoload.php';
// use Twilio\Rest\Client;
// $client = new Client($this->api_sid, $this->api_token);
// try {
// $options = [ 'twiml' => '' . htmlspecialchars($audioUrl) . '' ];
// if ($statusCallbackUrl) {
// $options['statusCallback'] = $statusCallbackUrl;
// $options['statusCallbackEvent'] = ['initiated', 'ringing', 'answered', 'completed', 'busy', 'failed', 'no-answer', 'canceled'];
// }
// $call = $client->calls->create($toPhoneNumber, $fromPhoneNumber, $options);
// return ['sid' => $call->sid, 'status' => 'queued'];
// } catch (\Twilio\Exceptions\TwilioException $e) {
// throw new Exception("Could not initiate call: " . $e->getMessage());
// }
// --- SIMULATION FOR THIS EXAMPLE ---
$simulatedSid = 'CA' . substr(hash('sha256', $toPhoneNumber . microtime()), 0, 32);
return [
'sid' => $simulatedSid,
'status' => 'queued',
'options' => ['to' => $toPhoneNumber, 'from' => $fromPhoneNumber, 'audioUrl' => $audioUrl, 'statusCallback' => $statusCallbackUrl]
];
}
/**
* Validates an incoming webhook request from Twilio.
* @param string $expectedSignature The X-Twilio-Signature header.
* @param string $url The full URL of the webhook handler.
* @param array $postData The POST data from the request.
* @return bool True if the signature is valid.
*/
public function validateWebhook($expectedSignature, $url, $postData) {
// --- PRODUCTION CODE ---
// require_once '/path/to/vendor/autoload.php';
// use Twilio\Security\RequestValidator;
// $validator = new RequestValidator($this->api_token);
// return $validator->validate($expectedSignature, $url, $postData);
// --- SIMULATION FOR THIS EXAMPLE ---
// In a real app, NEVER bypass this validation. It's critical for security.
return true;
}
}
```
### FILE 9: /home/ai-prank-caller.digitalprank.com/public_html/voice_generator.php
```php
'success',
'voice' => $voiceStyle,
'url' => $publicUrl
];
}
}
```
### FILE 10: /home/ai-prank-caller.digitalprank.com/public_html/api.php
```php
setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION); }
catch (PDOException $e) { http_response_code(503); echo json_encode(['success' => false, 'message' => 'Service Unavailable: Database connection error.']); exit; }
require_once '/home/cdn.digitalprank.com/public_html/php/analytics_functions.php'; // For logUsage
function api_error($message, $code = 400) {
http_response_code($code);
echo json_encode(['success' => false, 'message' => $message]);
exit;
}
$user_id = null; $input = [];
try {
$config = json_decode(file_get_contents(__DIR__ . '/tool_config.json'), true);
if (!$config) api_error('Internal Server Error: Cannot load tool config.', 500);
// 1. Authenticate Request
$api_key_header = $config['tool']['api']['auth_key_name'];
$api_key = $_SERVER[$api_key_header] ?? null;
if (empty($api_key)) api_error('Authentication failed: Missing API key in ' . str_replace('HTTP_','', $api_key_header) . ' header.', 401);
$stmt = $pdo->prepare("SELECT user_id FROM wp_digitalprank_api_keys WHERE api_key = ? AND tool_slug = ? AND status = 'active'");
$stmt->execute([$api_key, $tool_slug]);
$user_id = $stmt->fetchColumn();
if (!$user_id) api_error('Authentication failed: Invalid or revoked API key.', 403);
// 2. Authorize (Check Tier)
$stmt = $pdo->prepare("SELECT subscription_plan_id FROM wp_pms_member_subscriptions WHERE user_id = ? AND status = 'active' ORDER BY id DESC LIMIT 1");
$stmt->execute([$user_id]);
$plan_id = $stmt->fetchColumn();
if (!in_array($plan_id, [176, 186])) api_error('Authorization failed: API access requires an Ultimate tier subscription.', 403);
// 3. Get & Validate Input
$input = json_decode(file_get_contents('php://input'), true);
if (json_last_error() !== JSON_ERROR_NONE) api_error('Invalid input: Request body must be valid JSON.');
$script = $input['script_prompt'] ?? '';
$voice = $input['voice_style'] ?? '';
$victim_phone = $input['victim_phone'] ?? '';
$caller_id = $input['caller_id'] ?? '+15550001234';
if (empty($script) || empty($voice) || empty($victim_phone)) api_error('Invalid input: `script_prompt`, `voice_style`, and `victim_phone` are required.');
// 4. Process Request
$voice_gen = new VoiceGenerator();
$audio_result = $voice_gen->generateAudio($script, $voice);
$audio_url = $audio_result['url'];
$webhook_url = "https://{$tool_slug}.digitalprank.com/webhook_handler.php";
$twilio_handler = new TwilioHandler();
$call_result = $twilio_handler->initiateCall($victim_phone, $caller_id, $audio_url, $webhook_url);
$call_sid = $call_result['sid'];
// 5. Log & Respond
$stmt = $pdo->prepare("INSERT INTO prank_call_history (user_id, victim_phone, caller_id, script_prompt, voice_style, audio_url, twilio_sid, status, created_at) VALUES (?, ?, ?, ?, ?, ?, ?, 'queued', NOW())");
$stmt->execute([$user_id, $victim_phone, $caller_id, $script, $voice, $audio_url, $call_sid]);
$history_id = $pdo->lastInsertId();
$response_data = ['success' => true, 'message' => 'Prank call initiated.', 'call_sid' => $call_sid, 'history_id' => $history_id, 'status' => 'queued'];
http_response_code(202); // Accepted
echo json_encode($response_data);
logUsage($pdo, $tool_slug, $_SERVER['REMOTE_ADDR'], $user_id, 'api_call_sent', $input, $response_data, microtime(true) - $start_time);
} catch (Exception $e) {
logUsage($pdo, $tool_slug, $_SERVER['REMOTE_ADDR'], $user_id, 'api_call_failed', $input, ['error' => $e->getMessage()], microtime(true) - $start_time, 'failed');
api_error('An error occurred: ' . $e->getMessage(), 500);
}
```
### FILE 11: /home/ai-prank-caller.digitalprank.com/public_html/history.php
```php
setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION); }
catch (PDOException $e) { die("Database error. Please try again later."); }
$history = [];
if ($user_id > 0) {
$stmt = $pdo->prepare("SELECT * FROM prank_call_history WHERE user_id = ? ORDER BY created_at DESC LIMIT 100");
$stmt->execute([$user_id]);
$history = $stmt->fetchAll(PDO::FETCH_ASSOC);
}
?>
Call History - AI Prank Call Bot
```
### FILE 5: /home/ai-prank-caller.digitalprank.com/public_html/help.md
```markdown
# Help & Documentation: AI Prank Call Bot
Welcome to the AI Prank Call Bot! This guide will help you get started with sending hilarious, AI-powered prank calls to your friends.
## Quick Start Guide
1. **Step 1: Type your prank idea or script.**
- In the "Enter your prank script or idea" box, describe the funny scenario you want the AI to act out.
2. **Step 2: Pick a hilarious voice style.**
- Use the "Voice Style" dropdown to select a character.
3. **Step 3: Enter your victim's phone number (Pro).**
- If you're a Pro user, enter the full international phone number (e.g., +15551234567).
4. **Step 4: Click 'Send Prank Call'!**
- Hit the button to launch your prank. You can view its status on the "History" page.
5. **Step 5: Enjoy the chaos.**
- Your friend will receive a call and the AI will deliver your script.
## Feature Descriptions
- **Prank Script/Idea:** The core of your prank. (Free & Pro)
- **Voice Style:** Choose from a variety of AI voices. (Free & Pro)
- **Call History:** View a log of all your past and pending calls, see their status (e.g., completed, failed), and listen to the generated audio. (Pro)
- **Victim's Phone Number:** The destination for your prank call. (Pro)
- **Custom Caller ID:** Gold tier and above Pro users can specify the phone number that appears on the recipient's phone.
- **Schedule Call:** Pro users can schedule a prank call for a future time. Our system will automatically dispatch it.
- **Upload Your Own Audio:** Pro users can upload their own MP3/WAV file instead of using an AI voice.
- **API Access:** Ultimate tier users can integrate the prank call functionality into their own applications.
## Frequently Asked Questions (FAQ)
**Q: Is this legal?**
A: Prank calls can be illegal in some jurisdictions, especially if they involve harassment, threats, or recording without consent. This tool is for entertainment purposes only. Use it responsibly and only with friends who have a good sense of humor. You are responsible for complying with all local and federal laws.
**Q: Can I use my own voice?**
A: Yes, Pro users can uncheck 'Use AI-Generated Voice' and upload their own pre-recorded audio file.
**Q: What if the call doesn't go through?**
A: You will not be charged any credits for failed or unanswered calls. You can check the final status of any call on your History page.
**Q: Is there an API available?**
A: Yes! API access is available for our Ultimate tier subscribers. You can generate an API key from your account dashboard and find technical documentation at `/docs/api/ai-prank-caller.md`.
## Usage Examples
### Example 1: Wrong Pizza Delivery
- **Description:** A confused pizza guy calls the wrong number with a strange request.
- **Input:**
- `script_prompt`: "Hello? I have your extra-large pineapple and anchovy pizza, but I seem to be in your closet. Should I just leave it on the shoe rack?"
- `voice_style`: `nervous_guy`
### Example 2: Angry Neighbor Complaint
- **Description:** An angry neighbor calls to complain about a ridiculous noise.
- **Input:**
- `script_prompt`: "Yeah, hi, this is your neighbor from 3B. I need you to stop teaching your parrot to sing opera. It's scaring my cat, and frankly, you're both off-key."
- `voice_style`: `angry_neighbor`
---
*Have fun and prank responsibly!*
FILE 6: /home/digitalprank.com/public_html/blog/data/tools/ai-prank-caller.json
code
JSON
{
"post": {
"slug": "ai-prank-caller",
"title": "Unleash Hilarious Chaos with the AI Prank Call Bot",
"author": "The PrankMaster",
"date": "2025-09-25",
"tags": ["ai tools", "prank call", "entertainment", "phone pranks", "voice generator", "api"],
"meta_description": "Discover how to send hilarious, automated prank calls with AI-generated voices. Our guide to the AI Prank Call Bot covers features, API access, legal considerations, and funny script ideas.",
"canonical_url": "https://digitalprank.com/tools/ai-prank-caller",
"content": {
"introduction": {
"heading": "The Ultimate AI-Powered Prank Calling Tool",
"paragraph": "The AI Prank Call Bot lets you type a script, choose a funny AI voice, and send an automated call to any phone number. From an angry neighbor to a confused pizza guy, the possibilities are endless. Now with a full history log and API access for developers!"
},
"features_section": {
"heading": "Core Features",
"features": [
{ "name": "Custom Prank Scripts", "description": "Type any scenario up to 500 characters and our AI brings it to life.", "tier": "Free" },
{ "name": "Diverse Voice Library", "description": "Choose from hilarious voice styles like 'Squeaky Chipmunk' or 'Movie Narrator'.", "tier": "Free" },
{ "name": "Direct-to-Phone Sending", "description": "Our Pro plan allows you to send the prank call directly to your friend's device.", "tier": "Pro" },
{ "name": "View Call History", "description": "Track the status of all your calls (completed, failed, busy) in your personal dashboard.", "tier": "Pro" },
{ "name": "API Access", "description": "For Ultimate tier users, integrate our prank call service directly into your own applications.", "tier": "Ultimate" },
{ "name": "Custom Caller ID & Scheduling", "description": "Gold tier users can set a custom Caller ID. All Pro users can schedule calls for the perfect moment.", "tier": "Pro/Gold" }
]
},
"how_to_guide": {
"heading": "How to Send Your First Prank Call",
"steps": [
"Write your prank idea in the script field.",
"Select a 'Voice Style' from the dropdown.",
"For Pro users, enter the target 'Victim's Phone Number'.",
"Click 'Send Prank Call' and check the 'History' page for its status."
]
},
"technical_docs": {
"heading": "Technical Specifications",
"specs": [
{ "name": "API Access", "value": "Available for Ultimate tier users. See /docs/api/ai-prank-caller.md" },
{ "name": "API Endpoint", "value": "https://ai-prank-caller.digitalprank.com/api.php" },
{ "name": "Backend Integrations", "value": "Twilio for call delivery and status webhooks, XTTS for voice synthesis." },
{ "name": "Daily Limits", "value": "2 (Free), 15 (Basic), 150 (Gold), Unlimited (Ultimate)" }
]
}
},
"schema_org": {
"@context": "https://schema.org", "@type": "WebApplication", "name": "AI Prank Call Bot",
"description": "Send funny, automated prank calls using AI voices. Type a prank script, pick a voice, and watch the chaos unfold.",
"applicationCategory": "Entertainment", "operatingSystem": "Any (Web-based)", "url": "https://digitalprank.com/tools/ai-prank-caller",
"offers": { "@type": "Offer", "price": "0.00", "priceCurrency": "USD" },
"publisher": { "@type": "Organization", "name": "DigitalPrank.com" }
}
}
}
FILE 7: /home/ai-prank-caller.digitalprank.com/public_html/deploy.sh
code
Bash
#!/bin/bash
# Deployment script for the AI Prank Caller tool v1.4
set -e
TOOL_SLUG="ai-prank-caller"
VHOST_DIR="/home/${TOOL_SLUG}.digitalprank.com/public_html"
LOG_DIR="/var/log/${TOOL_SLUG}"
VENV_DIR="${VHOST_DIR}/venv"
DB_NAME="digitalprank_db"
DB_USER="dp_user"
DB_PASS="#$Dealer2355"
echo "--- Starting deployment for ${TOOL_SLUG} v1.4 ---"
# 1. System Packages
echo "Updating package lists and installing system dependencies..."
apt-get update -y && apt-get install -y ffmpeg sox python3-venv
# 2. Python Virtual Environment
echo "Setting up Python virtual environment at ${VENV_DIR}..."
if [ ! -d "$VENV_DIR" ]; then python3 -m venv "$VENV_DIR"; fi
source "${VENV_DIR}/bin/activate"
pip install --upgrade pip
pip install xtts pydub twilio
deactivate
echo "Python setup complete."
# 3. Database Tables
echo "Creating/updating database tables..."
SQL_HISTORY_TABLE="CREATE TABLE IF NOT EXISTS \`prank_call_history\` (\`id\` BIGINT PRIMARY KEY AUTO_INCREMENT, \`user_id\` BIGINT NULL, \`victim_phone\` VARCHAR(20) NOT NULL, \`caller_id\` VARCHAR(20), \`script_prompt\` TEXT NOT NULL, \`voice_style\` VARCHAR(50) NOT NULL, \`audio_url\` VARCHAR(255), \`twilio_sid\` VARCHAR(255) UNIQUE, \`status\` VARCHAR(50) DEFAULT 'pending', \`scheduled_for\` DATETIME NULL, \`created_at\` TIMESTAMP DEFAULT CURRENT_TIMESTAMP, \`updated_at\` TIMESTAMP ON UPDATE CURRENT_TIMESTAMP, INDEX \`user_id_idx\` (\`user_id\`), INDEX \`twilio_sid_idx\` (\`twilio_sid\`)) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"
SQL_API_KEYS_TABLE="CREATE TABLE IF NOT EXISTS \`wp_digitalprank_api_keys\` (\`id\` BIGINT PRIMARY KEY AUTO_INCREMENT, \`user_id\` BIGINT NOT NULL, \`tool_slug\` VARCHAR(100) NOT NULL, \`api_key\` VARCHAR(255) NOT NULL UNIQUE, \`status\` ENUM('active', 'revoked') DEFAULT 'active', \`created_at\` TIMESTAMP DEFAULT CURRENT_TIMESTAMP, INDEX \`user_tool_idx\` (\`user_id\`, \`tool_slug\`)) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"
mysql -u"${DB_USER}" -p"${DB_PASS}" "${DB_NAME}" -e "${SQL_HISTORY_TABLE}"
mysql -u"${DB_USER}" -p"${DB_PASS}" "${DB_NAME}" -e "${SQL_API_KEYS_TABLE}"
echo "Database setup complete."
# 4. Directories and Permissions
echo "Setting up directories and permissions..."
mkdir -p "${VHOST_DIR}/assets" && mkdir -p "$LOG_DIR"
chown -R www-data:www-data "$VHOST_DIR" && chown -R www-data:www-data "$LOG_DIR"
chmod -R 755 "$VHOST_DIR"
echo "Permissions set."
# 5. Cron Job Setup
echo "Setting up cron job for scheduler..."
CRON_JOB="* * * * * /usr/bin/php ${VHOST_DIR}/cron_scheduler.php >> ${LOG_DIR}/cron.log 2>&1"
(crontab -l 2>/dev/null | grep -v -F "${VHOST_DIR}/cron_scheduler.php" ; echo "$CRON_JOB") | crontab -
echo "Cron job installed."
# 6. OpenLiteSpeed Configuration & Restart
echo "Ensuring OpenLiteSpeed vhost is configured and restarting..."
systemctl restart lsws
echo "OpenLiteSpeed restarted."
# 7. Log Rotation
echo "Configuring log rotation..."
LOGROTATE_CONF="/etc/logrotate.d/${TOOL_SLUG}"
cat > "${LOGROTATE_CONF}" <api_sid = getenv('TWILIO_SID') ?: 'ACxxxxxxxxxxxxxxxxxxxxxxxxxxxxx';
$this->api_token = getenv('TWILIO_TOKEN') ?: 'your_auth_token';
}
public function initiateCall($toPhoneNumber, $fromPhoneNumber, $audioUrl, $statusCallbackUrl = null) {
if (empty($toPhoneNumber) || empty($fromPhoneNumber) || empty($audioUrl)) {
throw new Exception("To, From, and Audio URL are required to initiate a call.");
}
// --- SIMULATION FOR THIS EXAMPLE ---
$simulatedSid = 'CA' . substr(hash('sha256', $toPhoneNumber . microtime()), 0, 32);
return [
'sid' => $simulatedSid,
'status' => 'queued',
'options' => ['to' => $toPhoneNumber, 'from' => $fromPhoneNumber, 'audioUrl' => $audioUrl, 'statusCallback' => $statusCallbackUrl]
];
}
public function validateWebhook($expectedSignature, $url, $postData) {
// In a real app, this validation is critical for security.
return true;
}
}```
### FILE 9: /home/ai-prank-caller.digitalprank.com/public_html/voice_generator.php
```php
'success',
'voice' => $voiceStyle,
'url' => $publicUrl
];
}
}
FILE 10: /home/ai-prank-caller.digitalprank.com/public_html/api.php
code
PHP
setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION); }
catch (PDOException $e) { http_response_code(503); echo json_encode(['success' => false, 'message' => 'Service Unavailable: Database error.']); exit; }
require_once '/home/cdn.digitalprank.com/public_html/php/analytics_functions.php';
function api_error($message, $code = 400) { http_response_code($code); echo json_encode(['success' => false, 'message' => $message]); exit; }
$user_id = null; $input = [];
try {
$config = json_decode(file_get_contents(__DIR__ . '/tool_config.json'), true);
if (!$config) api_error('Internal Server Error: Cannot load tool config.', 500);
$api_key_header = $config['tool']['api']['auth_key_name'];
$api_key = $_SERVER[$api_key_header] ?? null;
if (empty($api_key)) api_error('Authentication failed: Missing API key in ' . str_replace('HTTP_','', $api_key_header) . ' header.', 401);
$stmt = $pdo->prepare("SELECT user_id FROM wp_digitalprank_api_keys WHERE api_key = ? AND tool_slug = ? AND status = 'active'");
$stmt->execute([$api_key, $tool_slug]);
if (!($user_id = $stmt->fetchColumn())) api_error('Authentication failed: Invalid or revoked API key.', 403);
$stmt = $pdo->prepare("SELECT subscription_plan_id FROM wp_pms_member_subscriptions WHERE user_id = ? AND status = 'active' ORDER BY id DESC LIMIT 1");
$stmt->execute([$user_id]);
if (!in_array($stmt->fetchColumn(), [176, 186])) api_error('Authorization failed: API access requires an Ultimate tier subscription.', 403);
$input = json_decode(file_get_contents('php://input'), true);
if (json_last_error() !== JSON_ERROR_NONE) api_error('Invalid input: Request body must be valid JSON.');
$script = $input['script_prompt'] ?? ''; $voice = $input['voice_style'] ?? ''; $victim_phone = $input['victim_phone'] ?? '';
$caller_id = $input['caller_id'] ?? '+15550001234';
if (empty($script) || empty($voice) || empty($victim_phone)) api_error('Invalid input: `script_prompt`, `voice_style`, and `victim_phone` are required.');
$voice_gen = new VoiceGenerator();
$audio_result = $voice_gen->generateAudio($script, $voice);
$audio_url = $audio_result['url'];
$webhook_url = "https://{$tool_slug}.digitalprank.com/webhook_handler.php";
$twilio_handler = new TwilioHandler();
$call_result = $twilio_handler->initiateCall($victim_phone, $caller_id, $audio_url, $webhook_url);
$call_sid = $call_result['sid'];
$stmt = $pdo->prepare("INSERT INTO prank_call_history (user_id, victim_phone, caller_id, script_prompt, voice_style, audio_url, twilio_sid, status, created_at) VALUES (?, ?, ?, ?, ?, ?, ?, 'queued', NOW())");
$stmt->execute([$user_id, $victim_phone, $caller_id, $script, $voice, $audio_url, $call_sid]);
$history_id = $pdo->lastInsertId();
$response_data = ['success' => true, 'message' => 'Prank call initiated.', 'call_sid' => $call_sid, 'history_id' => $history_id, 'status' => 'queued'];
http_response_code(202); // Accepted
echo json_encode($response_data);
logUsage($pdo, $tool_slug, $_SERVER['REMOTE_ADDR'], $user_id, 'api_call_sent', $input, $response_data, microtime(true) - $start_time);
} catch (Exception $e) {
logUsage($pdo, $tool_slug, $_SERVER['REMOTE_ADDR'], $user_id, 'api_call_failed', $input, ['error' => $e->getMessage()], microtime(true) - $start_time, 'failed');
api_error('An error occurred: ' . $e->getMessage(), 500);
}
FILE 11: /home/ai-prank-caller.digitalprank.com/public_html/history.php
code
PHP
setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION); }
catch (PDOException $e) { die("Database error. Please try again later."); }
$history = [];
if ($user_id > 0) {
$stmt = $pdo->prepare("SELECT * FROM prank_call_history WHERE user_id = ? ORDER BY created_at DESC LIMIT 100");
$stmt->execute([$user_id]);
$history = $stmt->fetchAll(PDO::FETCH_ASSOC);
}
?>
Call History - AI Prank Call Bot
FILE 5: /home/ai-prank-caller.digitalprank.com/public_html/help.md
code
Markdown
# Help & Documentation: AI Prank Call Bot
Welcome to the AI Prank Call Bot! This guide will help you get started with sending hilarious, AI-powered prank calls to your friends.
## Quick Start Guide
1. **Step 1: Type your prank idea or script.**
- In the "Enter your prank script or idea" box, describe the funny scenario you want the AI to act out.
2. **Step 2: Pick a hilarious voice style.**
- Use the "Voice Style" dropdown to select a character.
3. **Step 3: Enter your victim's phone number (Pro).**
- If you're a Pro user, enter the full international phone number (e.g., +15551234567).
4. **Step 4: Click 'Send Prank Call'!**
- Hit the button to launch your prank. You can view its status on the "History" page.
5. **Step 5: Enjoy the chaos.**
- Your friend will receive a call and the AI will deliver your script.
## Feature Descriptions
- **Prank Script/Idea:** The core of your prank. (Free & Pro)
- **Voice Style:** Choose from a variety of AI voices. (Free & Pro)
- **Call History:** View a log of all your past and pending calls, see their status (e.g., completed, failed), and listen to the generated audio. (Pro)
- **Victim's Phone Number:** The destination for your prank call. (Pro)
- **Custom Caller ID:** Gold tier and above Pro users can specify the phone number that appears on the recipient's phone.
- **Schedule Call:** Pro users can schedule a prank call for a future time. Our system will automatically dispatch it.
- **Upload Your Own Audio:** Pro users can upload their own MP3/WAV file instead of using an AI voice.
- **API Access:** Ultimate tier users can integrate the prank call functionality into their own applications.
## Frequently Asked Questions (FAQ)
**Q: Is this legal?**
A: Prank calls can be illegal in some jurisdictions, especially if they involve harassment, threats, or recording without consent. This tool is for entertainment purposes only. Use it responsibly and only with friends who have a good sense of humor. You are responsible for complying with all local and federal laws.
**Q: Can I use my own voice?**
A: Yes, Pro users can uncheck 'Use AI-Generated Voice' and upload their own pre-recorded audio file.
**Q: What if the call doesn't go through?**
A: You will not be charged any credits for failed or unanswered calls. You can check the final status of any call on your History page.
**Q: Is there an API available?**
A: Yes! API access is available for our Ultimate tier subscribers. You can generate an API key from your account dashboard and find technical documentation at `/docs/api/ai-prank-caller.md`.
## Usage Examples
### Example 1: Wrong Pizza Delivery
- **Description:** A confused pizza guy calls the wrong number with a strange request.
- **Input:**
- `script_prompt`: "Hello? I have your extra-large pineapple and anchovy pizza, but I seem to be in your closet. Should I just leave it on the shoe rack?"
- `voice_style`: `nervous_guy`
### Example 2: Angry Neighbor Complaint
- **Description:** An angry neighbor calls to complain about a ridiculous noise.
- **Input:**
- `script_prompt`: "Yeah, hi, this is your neighbor from 3B. I need you to stop teaching your parrot to sing opera. It's scaring my cat, and frankly, you're both off-key."
- `voice_style`: `angry_neighbor`
---
*Have fun and prank responsibly!*
FILE 6: /home/digitalprank.com/public_html/blog/data/tools/ai-prank-caller.json
code
JSON
{
"post": {
"slug": "ai-prank-caller",
"title": "Unleash Hilarious Chaos with the AI Prank Call Bot",
"author": "The PrankMaster",
"date": "2025-09-25",
"tags": ["ai tools", "prank call", "entertainment", "phone pranks", "voice generator", "api"],
"meta_description": "Discover how to send hilarious, automated prank calls with AI-generated voices. Our guide to the AI Prank Call Bot covers features, API access, legal considerations, and funny script ideas.",
"canonical_url": "https://digitalprank.com/tools/ai-prank-caller",
"content": {
"introduction": {
"heading": "The Ultimate AI-Powered Prank Calling Tool",
"paragraph": "The AI Prank Call Bot lets you type a script, choose a funny AI voice, and send an automated call to any phone number. From an angry neighbor to a confused pizza guy, the possibilities are endless. Now with a full history log and API access for developers!"
},
"features_section": {
"heading": "Core Features",
"features": [
{ "name": "Custom Prank Scripts", "description": "Type any scenario up to 500 characters and our AI brings it to life.", "tier": "Free" },
{ "name": "Diverse Voice Library", "description": "Choose from hilarious voice styles like 'Squeaky Chipmunk' or 'Movie Narrator'.", "tier": "Free" },
{ "name": "Direct-to-Phone Sending", "description": "Our Pro plan allows you to send the prank call directly to your friend's device.", "tier": "Pro" },
{ "name": "View Call History", "description": "Track the status of all your calls (completed, failed, busy) in your personal dashboard.", "tier": "Pro" },
{ "name": "API Access", "description": "For Ultimate tier users, integrate our prank call service directly into your own applications.", "tier": "Ultimate" },
{ "name": "Custom Caller ID & Scheduling", "description": "Gold tier users can set a custom Caller ID. All Pro users can schedule calls for the perfect moment.", "tier": "Pro/Gold" }
]
},
"how_to_guide": {
"heading": "How to Send Your First Prank Call",
"steps": [
"Write your prank idea in the script field.",
"Select a 'Voice Style' from the dropdown.",
"For Pro users, enter the target 'Victim's Phone Number'.",
"Click 'Send Prank Call' and check the 'History' page for its status."
]
},
"technical_docs": {
"heading": "Technical Specifications",
"specs": [
{ "name": "API Access", "value": "Available for Ultimate tier users. See /docs/api/ai-prank-caller.md" },
{ "name": "API Endpoint", "value": "https://ai-prank-caller.digitalprank.com/api.php" },
{ "name": "Backend Integrations", "value": "Twilio for call delivery and status webhooks, XTTS for voice synthesis." },
{ "name": "Daily Limits", "value": "2 (Free), 15 (Basic), 150 (Gold), Unlimited (Ultimate)" }
]
}
},
"schema_org": {
"@context": "https://schema.org", "@type": "WebApplication", "name": "AI Prank Call Bot",
"description": "Send funny, automated prank calls using AI voices. Type a prank script, pick a voice, and watch the chaos unfold.",
"applicationCategory": "Entertainment", "operatingSystem": "Any (Web-based)", "url": "https://digitalprank.com/tools/ai-prank-caller",
"offers": { "@type": "Offer", "price": "0.00", "priceCurrency": "USD" },
"publisher": { "@type": "Organization", "name": "DigitalPrank.com" }
}
}
}
FILE 7: /home/ai-prank-caller.digitalprank.com/public_html/deploy.sh
code
Bash
#!/bin/bash
# Deployment script for the AI Prank Caller tool v1.5
set -e
TOOL_SLUG="ai-prank-caller"
VHOST_DIR="/home/${TOOL_SLUG}.digitalprank.com/public_html"
LOG_DIR="/var/log/${TOOL_SLUG}"
VENV_DIR="${VHOST_DIR}/venv"
DB_NAME="digitalprank_db"
DB_USER="dp_user"
DB_PASS="#$Dealer2355"
echo "--- Starting deployment for ${TOOL_SLUG} v1.5 ---"
# 1. System Packages
echo "Updating package lists and installing system dependencies..."
apt-get update -y && apt-get install -y ffmpeg sox python3-venv
# 2. Python Virtual Environment
echo "Setting up Python virtual environment at ${VENV_DIR}..."
if [ ! -d "$VENV_DIR" ]; then python3 -m venv "$VENV_DIR"; fi
source "${VENV_DIR}/bin/activate"
pip install --upgrade pip
pip install xtts pydub twilio
deactivate
echo "Python setup complete."
# 3. Database Tables
echo "Creating/updating database tables..."
SQL_HISTORY_TABLE="CREATE TABLE IF NOT EXISTS \`prank_call_history\` (\`id\` BIGINT PRIMARY KEY AUTO_INCREMENT, \`user_id\` BIGINT NULL, \`victim_phone\` VARCHAR(20) NOT NULL, \`caller_id\` VARCHAR(20), \`script_prompt\` TEXT NOT NULL, \`voice_style\` VARCHAR(50) NOT NULL, \`audio_url\` VARCHAR(255), \`twilio_sid\` VARCHAR(255) UNIQUE, \`status\` VARCHAR(50) DEFAULT 'pending', \`scheduled_for\` DATETIME NULL, \`created_at\` TIMESTAMP DEFAULT CURRENT_TIMESTAMP, \`updated_at\` TIMESTAMP ON UPDATE CURRENT_TIMESTAMP, INDEX \`user_id_idx\` (\`user_id\`), INDEX \`twilio_sid_idx\` (\`twilio_sid\`)) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"
SQL_API_KEYS_TABLE="CREATE TABLE IF NOT EXISTS \`wp_digitalprank_api_keys\` (\`id\` BIGINT PRIMARY KEY AUTO_INCREMENT, \`user_id\` BIGINT NOT NULL, \`tool_slug\` VARCHAR(100) NOT NULL, \`api_key\` VARCHAR(255) NOT NULL UNIQUE, \`status\` ENUM('active', 'revoked') DEFAULT 'active', \`created_at\` TIMESTAMP DEFAULT CURRENT_TIMESTAMP, INDEX \`user_tool_idx\` (\`user_id\`, \`tool_slug\`)) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"
mysql -u"${DB_USER}" -p"${DB_PASS}" "${DB_NAME}" -e "${SQL_HISTORY_TABLE}"
mysql -u"${DB_USER}" -p"${DB_PASS}" "${DB_NAME}" -e "${SQL_API_KEYS_TABLE}"
echo "Database setup complete."
# 4. Directories and Permissions
echo "Setting up directories and permissions..."
mkdir -p "${VHOST_DIR}/assets" && mkdir -p "$LOG_DIR"
chown -R www-data:www-data "$VHOST_DIR" && chown -R www-data:www-data "$LOG_DIR"
chmod -R 755 "$VHOST_DIR"
echo "Permissions set."
# 5. Cron Job Setup
echo "Setting up cron job for scheduler..."
CRON_JOB="* * * * * /usr/bin/php ${VHOST_DIR}/cron_scheduler.php >> ${LOG_DIR}/cron.log 2>&1"
(crontab -l 2>/dev/null | grep -v -F "${VHOST_DIR}/cron_scheduler.php" ; echo "$CRON_JOB") | crontab -
echo "Cron job installed."
# 6. OpenLiteSpeed Configuration & Restart
echo "Ensuring OpenLiteSpeed vhost is configured and restarting..."
systemctl restart lsws
echo "OpenLiteSpeed restarted."
# 7. Log Rotation
echo "Configuring log rotation..."
LOGROTATE_CONF="/etc/logrotate.d/${TOOL_SLUG}"
cat > "${LOGROTATE_CONF}" <api_sid = getenv('TWILIO_SID') ?: 'ACxxxxxxxxxxxxxxxxxxxxxxxxxxxxx';
$this->api_token = getenv('TWILIO_TOKEN') ?: 'your_auth_token';
}
public function initiateCall($toPhoneNumber, $fromPhoneNumber, $audioUrl, $statusCallbackUrl = null) {
if (empty($toPhoneNumber) || empty($fromPhoneNumber) || empty($audioUrl)) {
throw new Exception("To, From, and Audio URL are required to initiate a call.");
}
// Simulation for demonstration. In production, this would use the Twilio SDK.
$simulatedSid = 'CA' . substr(hash('sha256', $toPhoneNumber . microtime()), 0, 32);
return [
'sid' => $simulatedSid,
'status' => 'queued',
'options' => ['to' => $toPhoneNumber, 'from' => $fromPhoneNumber, 'audioUrl' => $audioUrl, 'statusCallback' => $statusCallbackUrl]
];
}
public function validateWebhook($expectedSignature, $url, $postData) {
// In a real app, this validation is critical for security and would use the Twilio SDK.
return true;
}
}```
### FILE 9: /home/ai-prank-caller.digitalprank.com/public_html/voice_generator.php
```php
'success',
'voice' => $voiceStyle,
'url' => $publicUrl
];
}
}
```
### FILE 10: /home/ai-prank-caller.digitalprank.com/public_html/api.php
```php
setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION); }
catch (PDOException $e) { http_response_code(503); echo json_encode(['success' => false, 'message' => 'Service Unavailable: Database error.']); exit; }
require_once '/home/cdn.digitalprank.com/public_html/php/analytics_functions.php';
function api_error($message, $code = 400) { http_response_code($code); echo json_encode(['success' => false, 'message' => $message]); exit; }
$user_id = null; $input = [];
try {
$config = json_decode(file_get_contents(__DIR__ . '/tool_config.json'), true);
if (!$config) api_error('Internal Server Error: Cannot load tool config.', 500);
$api_key_header = $config['tool']['api']['auth_key_name'];
$api_key = $_SERVER[$api_key_header] ?? null;
if (empty($api_key)) api_error('Authentication failed: Missing API key in ' . str_replace('HTTP_','', $api_key_header) . ' header.', 401);
$stmt = $pdo->prepare("SELECT user_id FROM wp_digitalprank_api_keys WHERE api_key = ? AND tool_slug = ? AND status = 'active'");
$stmt->execute([$api_key, $tool_slug]);
if (!($user_id = $stmt->fetchColumn())) api_error('Authentication failed: Invalid or revoked API key.', 403);
$stmt = $pdo->prepare("SELECT subscription_plan_id FROM wp_pms_member_subscriptions WHERE user_id = ? AND status = 'active' ORDER BY id DESC LIMIT 1");
$stmt->execute([$user_id]);
if (!in_array($stmt->fetchColumn(), [176, 186])) api_error('Authorization failed: API access requires an Ultimate tier subscription.', 403);
$input = json_decode(file_get_contents('php://input'), true);
if (json_last_error() !== JSON_ERROR_NONE) api_error('Invalid input: Request body must be valid JSON.');
$script = $input['script_prompt'] ?? ''; $voice = $input['voice_style'] ?? ''; $victim_phone = $input['victim_phone'] ?? '';
$caller_id = $input['caller_id'] ?? '+15550001234';
if (empty($script) || empty($voice) || empty($victim_phone)) api_error('Invalid input: `script_prompt`, `voice_style`, and `victim_phone` are required.');
$voice_gen = new VoiceGenerator();
$audio_result = $voice_gen->generateAudio($script, $voice);
$audio_url = $audio_result['url'];
$webhook_url = "https://{$tool_slug}.digitalprank.com/webhook_handler.php";
$twilio_handler = new TwilioHandler();
$call_result = $twilio_handler->initiateCall($victim_phone, $caller_id, $audio_url, $webhook_url);
$call_sid = $call_result['sid'];
$stmt = $pdo->prepare("INSERT INTO prank_call_history (user_id, victim_phone, caller_id, script_prompt, voice_style, audio_url, twilio_sid, status, created_at) VALUES (?, ?, ?, ?, ?, ?, ?, 'queued', NOW())");
$stmt->execute([$user_id, $victim_phone, $caller_id, $script, $voice, $audio_url, $call_sid]);
$history_id = $pdo->lastInsertId();
$response_data = ['success' => true, 'message' => 'Prank call initiated.', 'call_sid' => $call_sid, 'history_id' => $history_id, 'status' => 'queued'];
http_response_code(202); // Accepted
echo json_encode($response_data);
logUsage($pdo, $tool_slug, $_SERVER['REMOTE_ADDR'], $user_id, 'api_call_sent', $input, $response_data, microtime(true) - $start_time);
} catch (Exception $e) {
logUsage($pdo, $tool_slug, $_SERVER['REMOTE_ADDR'], $user_id, 'api_call_failed', $input, ['error' => $e->getMessage()], microtime(true) - $start_time, 'failed');
api_error('An error occurred: ' . $e->getMessage(), 500);
}
```
### FILE 11: /home/ai-prank-caller.digitalprank.com/public_html/history.php
```php
setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION); }
catch (PDOException $e) { die("Database error. Please try again later."); }
$history = [];
if ($user_id > 0) {
$stmt = $pdo->prepare("SELECT * FROM prank_call_history WHERE user_id = ? ORDER BY created_at DESC LIMIT 100");
$stmt->execute([$user_id]);
$history = $stmt->fetchAll(PDO::FETCH_ASSOC);
}
?>
Call History - AI Prank Call Bot
```
### FILE 12: /home/ai-prank-caller.digitalprank.com/public_html/webhook_handler.php
```php
setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION); }
catch (PDOException $e) { error_log("Webhook DB connection failed: " . $e->getMessage()); http_response_code(503); exit; }
$post_data = $_POST;
$twilio_signature = $_SERVER['HTTP_X_TWILIO_SIGNATURE'] ?? '';
p
r
o
t
o
c
o
l
=
i
s
s
e
t
(
protocol=isset(
_SERVER['HTTPS']) && $_SERVER['HTTPS'] === 'on' ? "https" : "http";
u
r
l
=
"
url="
protocol://
S
E
R
V
E
R
[
H
T
T
P
H
O
S
T
]
S
ERVER[HTTP
H
OST]
_SERVER[REQUEST_URI]";
v
a
l
i
d
a
t
o
r
=
n
e
w
T
w
i
l
i
o
H
a
n
d
l
e
r
(
)
;
i
f
(
!
validator=newTwilioHandler();if(!
validator->validateWebhook($twilio_signature, $url,
post_data['CallSid'] ?? 'N/A') . " from IP: " . $_SERVER['REMOTE_ADDR']);
http_response_code(403); exit;
}
$call_sid = $post_data['CallSid'] ?? null;
$call_status = $post_data['CallStatus'] ?? null;
if ($call_sid && $call_status) {
try {
$stmt = $pdo->prepare("UPDATE prank_call_history SET status = :status, updated_at = NOW() WHERE twilio_sid = :sid");
$stmt->execute([':status' => $call_status, ':sid' => $call_sid]);
} catch (PDOException
call_sid}: " . $e->getMessage());
http_response_code(500); exit;
}
}
header('Content-Type: text/xml');
echo '';
exit;
code
Code
### FILE 13: /home/ai-prank-caller.digitalprank.com/public_html/cron_scheduler.php
```php
setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
} catch (PDOException $e) { error_log("Cron DB connection failed: " . $e->getMessage()); flock($lock_handle, LOCK_UN); fclose($lock_handle); exit; }
$tool_slug = 'ai-prank-caller';
echo "Running scheduler at " . date('Y-m-d H:i:s') . "\n";
try {
$stmt = $pdo->prepare("SELECT * FROM prank_call_history WHERE status = 'scheduled' AND scheduled_for <= NOW() LIMIT 10");
$stmt->execute();
$due_calls = $stmt->fetchAll(PDO::FETCH_ASSOC);
if (!empty($due_calls)) {
$twilio_handler = new TwilioHandler();
$webhook_url = "https://{$tool_slug}.digitalprank.com/webhook_handler.php";
echo "Found " . count($due_calls) . " calls to process.\n";
foreach ($due_calls as $call) {
try {
$call_result = $twilio_handler->initiateCall($call['victim_phone'], $call['caller_id'], $call['audio_url'], $webhook_url);
$update_stmt = $pdo->prepare("UPDATE prank_call_history SET status = :status, twilio_sid = :sid, updated_at = NOW() WHERE id = :id");
$update_stmt->execute([':status' => $call_result['status'], ':sid' => $call_result['sid'], ':id' => $call['id']]);
echo "Successfully queued call ID {$call['id']} with SID {$call_result['sid']}.\n";
} catch (Exception $e) {
$fail_stmt = $pdo->prepare("UPDATE prank_call_history SET status = 'failed', updated_at = NOW() WHERE id = :id");
$fail_stmt->execute([':id' => $call['id']]);
error_log("Cron failed to process call ID {$call['id']}: " . $e->getMessage());
}
}
} else {
echo "No due calls found.\n";
}
} catch (PDOException $e) { error_log("Cron job database error: " . $e->getMessage()); }
flock($lock_handle, LOCK_UN);
fclose($lock_handle);
echo "Scheduler finished.\n";
exit;```
### FILE 14: /home/ai-prank-caller.digitalprank.com/public_html/assets/style.css
```css
/* AI Prank Caller Stylesheet v1.5 */
body { font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Helvetica, Arial, sans-serif; background-color: #f4f4f9; color: #333; margin: 0; padding: 2rem; }
.container { max-width: 900px; margin: auto; background: #fff; padding: 2rem; border-radius: 8px; box-shadow: 0 4px 12px rgba(0,0,0,0.1); }
h1 { color: #FF4500; text-align: center; }
h2 { color: #333; border-bottom: 2px solid #f0f0f0; padding-bottom: 0.5rem; margin-top: 2rem; }
p.tagline { text-align: center; color: #666; margin-top: -10px; margin-bottom: 2rem; }
.nav-links { text-align: center; margin-bottom: 2rem; border-bottom: 1px solid #eee; padding-bottom: 1.5rem; }
.nav-links a { margin: 0 15px; color: #333; text-decoration: none; font-weight: bold; padding: 8px 12px; border-radius: 6px; transition: background-color 0.2s; }
.nav-links a:hover { background-color: #f0f0f0; }
.form-group { margin-bottom: 1.5rem; }
.form-group label { display: block; font-weight: bold; margin-bottom: 0.5rem; }
.pro-badge { background-color: gold; color: #333; font-size: 0.7rem; padding: 2px 5px; border-radius: 4px; margin-left: 8px; font-weight: bold; }
input[type="text"], input[type="tel"], input[type="datetime-local"], select, textarea { width: 100%; padding: 10px; border-radius: 4px; border: 1px solid #ccc; box-sizing: border-box; }
textarea { min-height: 100px; resize: vertical; }
.submit-btn, .btn { display: inline-block; padding: 12px 20px; background-color: #FF4500; color: white; border: none; border-radius: 4px; font-size: 1rem; cursor: pointer; text-decoration: none; text-align: center; }
.submit-btn { width: 100%; font-size: 1.2rem; }
.submit-btn:disabled { background-color: #ccc; cursor: not-allowed; }
#result-modal { display: none; position: fixed; z-index: 1000; left: 0; top: 0; width: 100%; height: 100%; background-color: rgba(0,0,0,0.5); }
.modal-content { background-color: #fefefe; margin: 15% auto; padding: 20px; border-radius: 8px; width: 80%; max-width: 500px; text-align: center; }
.loader { border: 5px solid #f3f3f3; border-radius: 50%; border-top: 5px solid #FF4500; width: 40px; height: 40px; animation: spin 1s linear infinite; margin: 20px auto; }
@keyframes spin { 0% { transform: rotate(0deg); } 100% { transform: rotate(360deg); } }
table { width: 100%; border-collapse: collapse; margin-top: 1.5rem; }
th, td { padding: 12px; border-bottom: 1px solid #ddd; text-align: left; vertical-align: middle; }
th { background-color: #f8f8f8; }
.status { padding: 4px 8px; border-radius: 12px; color: white; font-size: 0.8rem; text-transform: capitalize; display: inline-block; }
.status-completed { background-color: #28a745; }
.status-queued, .status-pending, .status-ringing, .status-initiated, .status-in-progress, .status-scheduled { background-color: #ffc107; color: #333; }
.status-failed, .status-canceled { background-color: #dc3545; }
.status-busy, .status-no-answer { background-color: #17a2b8; }
.no-history { text-align: center; color: #777; padding: 2rem; }
.account-info, .api-key-section { background-color: #f9f9f9; padding: 1.5rem; border-radius: 8px; margin-top: 1rem; }
.api-key-box { background-color: #fff; border: 1px solid #ddd; padding: 1rem; border-radius: 4px; font-family: monospace; word-wrap: break-word; margin: 1rem 0; }
.api-key-section p { font-size: 0.9rem; color: #555; }
FILE 15: /home/digitalprank.com/public_html/docs/api/ai-prank-caller.md
code
Markdown
# API Documentation: AI Prank Call Bot
Welcome to the AI Prank Call Bot API! This document provides all the information you need to integrate our hilarious prank call service into your own applications.
**API Version:** `v1`
**Base Endpoint:** `https://ai-prank-caller.digitalprank.com/api.php`
## Authentication
Authentication is handled via an API key passed in an HTTP header. Access is restricted to **Ultimate Tier** subscribers.
- **Header Name:** `X-API-Key`
- **Value:** Your unique API key.
You can generate and manage your API keys from your DigitalPrank.com account dashboard.
```bash
# Example Header
-H "X-API-Key: YOUR_ULTIMATE_TIER_API_KEY"
Rate Limiting
API access is subject to rate limits to ensure service stability. The current limits are:
10 requests per minute.
3 concurrent requests from the same API key.
If you exceed the rate limit, you will receive an HTTP 429 Too Many Requests response.
Endpoints
Initiate a Prank Call
This is the primary endpoint for creating and sending a new prank call.
Method: POST
Endpoint: /api.php
Request Body
The request body must be a raw JSON object with the following properties:
Parameter Type Required Description
script_prompt string Yes The text script for the AI to speak. Must be between 10 and 500 characters.
voice_style string Yes The voice to use. See available voice styles below.
victim_phone string Yes The recipient's phone number in E.164 format (e.g., +15551234567).
caller_id string No An E.164 formatted number to display as the caller ID. If omitted, a default number is used.
Available Voice Styles
annoying_robot, squeaky_chipmunk, scary_deep, sassy_female, movie_narrator, angry_neighbor, confused_old_lady, slick_salesman, nervous_guy
Example Request (cURL)
code
Bash
curl -X POST \
https://ai-prank-caller.digitalprank.com/api.php \
-H 'Content-Type: application/json' \
-H 'X-API-Key: YOUR_ULTIMATE_TIER_API_KEY' \
-d '{
"script_prompt": "Hello, this is the Department of Motor Vehicles. We are calling to inform you that your license has been suspended due to excessive coolness. Please report to our office immediately.",
"voice_style": "movie_narrator",
"victim_phone": "+15551234567",
"caller_id": "+15558675309"
}'
Success Response (HTTP 202 Accepted)
If the request is valid, the call will be queued for delivery and you will receive a 202 Accepted response.
code
JSON
{
"success": true,
"message": "Prank call initiated.",
"call_sid": "CAa1b2c3d4e5f6a7b8c9d0e1f2a3b4c5d6",
"history_id": "12345",
"status": "queued"
}
call_sid: The unique identifier for the call from our telephony provider (Twilio). You can use this for tracking.
history_id: The unique identifier for this call in the DigitalPrank database.
status: The initial status of the call. It will be updated via webhook as it progresses.
Error Responses
HTTP 400 Bad Request: Sent if the JSON body is malformed or required parameters are missing.
HTTP 401 Unauthorized: Sent if the X-API-Key header is missing.
HTTP 403 Forbidden: Sent if the API key is invalid, revoked, or does not belong to an Ultimate tier subscriber.
HTTP 500 Internal Server Error: Sent if an unexpected error occurs on our end.
Webhooks for Call Status
Our system uses webhooks to provide real-time status updates for your calls. When a call's status changes (e.g., from queued to ringing, completed, or failed), our provider (Twilio) will send a POST request to our webhook handler, which updates our database. You can view the final status of any call by checking your History page on the main website.
Last Updated: 2025-09-25
code
Code
### FILE 16: /home/ai-prank-caller.digitalprank.com/public_html/account.php
```php
setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION); }
catch (PDOException $e) { die("Database error."); }
require_once '/home/cdn/digitalprank.com/public_html/php/analytics_functions.php';
$access = getUserAccessLevel($pdo, $user_id, $tool_slug);
$config = json_decode(file_get_contents('tool_config.json'), true);
$daily_limit = $config['tool']['limits']['tier_daily'][$access['level']] ?? 0;
// Handle API Key Generation
$api_key = null;
if ($_SERVER['REQUEST_METHOD'] === 'POST' && isset($_POST['generate_api_key']) && $access['level'] === 'ultimate') {
// Invalidate old key
$stmt = $pdo->prepare("UPDATE wp_digitalprank_api_keys SET status = 'revoked' WHERE user_id = ? AND tool_slug = ?");
$stmt->execute([$user_id, $tool_slug]);
// Generate new key
$new_key = 'dpk_' . bin2hex(random_bytes(24));
$stmt = $pdo->prepare("INSERT INTO wp_digitalprank_api_keys (user_id, tool_slug, api_key, status) VALUES (?, ?, ?, 'active')");
$stmt->execute([$user_id, $tool_slug, $new_key]);
logUsage($pdo, $tool_slug, $_SERVER['REMOTE_ADDR'], $user_id, 'api_key_generated', [], [], 0);
// Refresh the page to show the new key
header('Location: account.php'); exit;
}
// Fetch existing API key for Ultimate users
if ($access['level'] === 'ultimate') {
$stmt = $pdo->prepare("SELECT api_key FROM wp_digitalprank_api_keys WHERE user_id = ? AND tool_slug = ? AND status = 'active'");
$stmt->execute([$user_id, $tool_slug]);
$api_key = $stmt->fetchColumn();
}
?>
My Account - AI Prank Call Bot
FILE 5: /home/ai-prank-caller.digitalprank.com/public_html/help.md
code
Markdown
# Help & Documentation: AI Prank Call Bot
Welcome to the AI Prank Call Bot! This guide will help you get started with sending hilarious, AI-powered prank calls to your friends.
## Quick Start Guide
1. **Step 1: Type your prank idea or script.**
- In the "Enter your prank script or idea" box, describe the funny scenario you want the AI to act out.
2. **Step 2: Pick a hilarious voice style.**
- Use the "Voice Style" dropdown to select a character.
3. **Step 3: Enter your victim's phone number (Pro).**
- If you're a Pro user, enter the full international phone number (e.g., +15551234567).
4. **Step 4: Click 'Send Prank Call'!**
- Hit the button to launch your prank. You can view its status on the "History" page.
5. **Step 5: Enjoy the chaos.**
- Your friend will receive a call and the AI will deliver your script.
## Feature Descriptions
- **Prank Script/Idea:** The core of your prank. (Free & Pro)
- **Voice Style:** Choose from a variety of AI voices. (Free & Pro)
- **Call History:** View a log of all your past and pending calls, see their status (e.g., completed, failed), and listen to the generated audio. (Pro)
- **Victim's Phone Number:** The destination for your prank call. (Pro)
- **Custom Caller ID:** Gold tier and above Pro users can specify the phone number that appears on the recipient's phone.
- **Schedule Call:** Pro users can schedule a prank call for a future time. Our system will automatically dispatch it.
- **Upload Your Own Audio:** Pro users can upload their own MP3/WAV file instead of using an AI voice.
- **API Access:** Ultimate tier users can integrate the prank call functionality into their own applications.
## Frequently Asked Questions (FAQ)
**Q: Is this legal?**
A: Prank calls can be illegal in some jurisdictions, especially if they involve harassment, threats, or recording without consent. This tool is for entertainment purposes only. Use it responsibly and only with friends who have a good sense of humor. You are responsible for complying with all local and federal laws.
**Q: Can I use my own voice?**
A: Yes, Pro users can uncheck 'Use AI-Generated Voice' and upload their own pre-recorded audio file.
**Q: What if the call doesn't go through?**
A: You will not be charged any credits for failed or unanswered calls. You can check the final status of any call on your History page.
**Q: Is there an API available?**
A: Yes! API access is available for our Ultimate tier subscribers. You can generate an API key from your account dashboard and find technical documentation at `/docs/api/ai-prank-caller.md`.
## Usage Examples
### Example 1: Wrong Pizza Delivery
- **Description:** A confused pizza guy calls the wrong number with a strange request.
- **Input:**
- `script_prompt`: "Hello? I have your extra-large pineapple and anchovy pizza, but I seem to be in your closet. Should I just leave it on the shoe rack?"
- `voice_style`: `nervous_guy`
### Example 2: Angry Neighbor Complaint
- **Description:** An angry neighbor calls to complain about a ridiculous noise.
- **Input:**
- `script_prompt`: "Yeah, hi, this is your neighbor from 3B. I need you to stop teaching your parrot to sing opera. It's scaring my cat, and frankly, you're both off-key."
- `voice_style`: `angry_neighbor`
---
*Have fun and prank responsibly!*```
### FILE 6: /home/digitalprank.com/public_html/blog/data/tools/ai-prank-caller.json
```json
{
"post": {
"slug": "ai-prank-caller",
"title": "Unleash Hilarious Chaos with the AI Prank Call Bot",
"author": "The PrankMaster",
"date": "2025-09-25",
"tags": ["ai tools", "prank call", "entertainment", "phone pranks", "voice generator", "api"],
"meta_description": "Discover how to send hilarious, automated prank calls with AI-generated voices. Our guide to the AI Prank Call Bot covers features, API access, legal considerations, and funny script ideas.",
"canonical_url": "https://digitalprank.com/tools/ai-prank-caller",
"content": {
"introduction": {
"heading": "The Ultimate AI-Powered Prank Calling Tool",
"paragraph": "The AI Prank Call Bot lets you type a script, choose a funny AI voice, and send an automated call to any phone number. From an angry neighbor to a confused pizza guy, the possibilities are endless. Now with a full history log and API access for developers!"
},
"features_section": {
"heading": "Core Features",
"features": [
{ "name": "Custom Prank Scripts", "description": "Type any scenario up to 500 characters and our AI brings it to life.", "tier": "Free" },
{ "name": "Diverse Voice Library", "description": "Choose from hilarious voice styles like 'Squeaky Chipmunk' or 'Movie Narrator'.", "tier": "Free" },
{ "name": "Direct-to-Phone Sending", "description": "Our Pro plan allows you to send the prank call directly to your friend's device.", "tier": "Pro" },
{ "name": "View Call History", "description": "Track the status of all your calls (completed, failed, busy) in your personal dashboard.", "tier": "Pro" },
{ "name": "API Access", "description": "For Ultimate tier users, integrate our prank call service directly into your own applications.", "tier": "Ultimate" },
{ "name": "Custom Caller ID & Scheduling", "description": "Gold tier users can set a custom Caller ID. All Pro users can schedule calls for the perfect moment.", "tier": "Pro/Gold" }
]
},
"how_to_guide": {
"heading": "How to Send Your First Prank Call",
"steps": [
"Write your prank idea in the script field.",
"Select a 'Voice Style' from the dropdown.",
"For Pro users, enter the target 'Victim's Phone Number'.",
"Click 'Send Prank Call' and check the 'History' page for its status."
]
},
"technical_docs": {
"heading": "Technical Specifications",
"specs": [
{ "name": "API Access", "value": "Available for Ultimate tier users. See /docs/api/ai-prank-caller.md" },
{ "name": "API Endpoint", "value": "https://ai-prank-caller.digitalprank.com/api.php" },
{ "name": "Backend Integrations", "value": "Twilio for call delivery and status webhooks, XTTS for voice synthesis." },
{ "name": "Daily Limits", "value": "2 (Free), 15 (Basic), 150 (Gold), Unlimited (Ultimate)" }
]
}
},
"schema_org": {
"@context": "https://schema.org", "@type": "WebApplication", "name": "AI Prank Call Bot",
"description": "Send funny, automated prank calls using AI voices. Type a prank script, pick a voice, and watch the chaos unfold.",
"applicationCategory": "Entertainment", "operatingSystem": "Any (Web-based)", "url": "https://digitalprank.com/tools/ai-prank-caller",
"offers": { "@type": "Offer", "price": "0.00", "priceCurrency": "USD" },
"publisher": { "@type": "Organization", "name": "DigitalPrank.com" }
}
}
}
FILE 7: /home/ai-prank-caller.digitalprank.com/public_html/deploy.sh
code
Bash
#!/bin/bash
# Deployment script for the AI Prank Caller tool v1.5
set -e
TOOL_SLUG="ai-prank-caller"
VHOST_DIR="/home/${TOOL_SLUG}.digitalprank.com/public_html"
LOG_DIR="/var/log/${TOOL_SLUG}"
VENV_DIR="${VHOST_DIR}/venv"
DB_NAME="digitalprank_db"
DB_USER="dp_user"
DB_PASS="#$Dealer2355"
echo "--- Starting deployment for ${TOOL_SLUG} v1.5 ---"
# 1. System Packages
echo "Updating package lists and installing system dependencies..."
apt-get update -y && apt-get install -y ffmpeg sox python3-venv
# 2. Python Virtual Environment
echo "Setting up Python virtual environment at ${VENV_DIR}..."
if [ ! -d "$VENV_DIR" ]; then python3 -m venv "$VENV_DIR"; fi
source "${VENV_DIR}/bin/activate"
pip install --upgrade pip
pip install xtts pydub twilio
deactivate
echo "Python setup complete."
# 3. Database Tables
echo "Creating/updating database tables..."
SQL_HISTORY_TABLE="CREATE TABLE IF NOT EXISTS \`prank_call_history\` (\`id\` BIGINT PRIMARY KEY AUTO_INCREMENT, \`user_id\` BIGINT NULL, \`victim_phone\` VARCHAR(20) NOT NULL, \`caller_id\` VARCHAR(20), \`script_prompt\` TEXT NOT NULL, \`voice_style\` VARCHAR(50) NOT NULL, \`audio_url\` VARCHAR(255), \`twilio_sid\` VARCHAR(255) UNIQUE, \`status\` VARCHAR(50) DEFAULT 'pending', \`scheduled_for\` DATETIME NULL, \`created_at\` TIMESTAMP DEFAULT CURRENT_TIMESTAMP, \`updated_at\` TIMESTAMP ON UPDATE CURRENT_TIMESTAMP, INDEX \`user_id_idx\` (\`user_id\`), INDEX \`twilio_sid_idx\` (\`twilio_sid\`)) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"
SQL_API_KEYS_TABLE="CREATE TABLE IF NOT EXISTS \`wp_digitalprank_api_keys\` (\`id\` BIGINT PRIMARY KEY AUTO_INCREMENT, \`user_id\` BIGINT NOT NULL, \`tool_slug\` VARCHAR(100) NOT NULL, \`api_key\` VARCHAR(255) NOT NULL UNIQUE, \`status\` ENUM('active', 'revoked') DEFAULT 'active', \`created_at\` TIMESTAMP DEFAULT CURRENT_TIMESTAMP, INDEX \`user_tool_idx\` (\`user_id\`, \`tool_slug\`)) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;"
mysql -u"${DB_USER}" -p"${DB_PASS}" "${DB_NAME}" -e "${SQL_HISTORY_TABLE}"
mysql -u"${DB_USER}" -p"${DB_PASS}" "${DB_NAME}" -e "${SQL_API_KEYS_TABLE}"
echo "Database setup complete."
# 4. Directories and Permissions
echo "Setting up directories and permissions..."
mkdir -p "${VHOST_DIR}/assets" && mkdir -p "$LOG_DIR"
chown -R www-data:www-data "$VHOST_DIR" && chown -R www-data:www-data "$LOG_DIR"
chmod -R 755 "$VHOST_DIR"
echo "Permissions set."
# 5. Cron Job Setup
echo "Setting up cron job for scheduler..."
CRON_JOB="* * * * * /usr/bin/php ${VHOST_DIR}/cron_scheduler.php >> ${LOG_DIR}/cron.log 2>&1"
(crontab -l 2>/dev/null | grep -v -F "${VHOST_DIR}/cron_scheduler.php" ; echo "$CRON_JOB") | crontab -
echo "Cron job installed."
# 6. OpenLiteSpeed Configuration & Restart
echo "Ensuring OpenLiteSpeed vhost is configured and restarting..."
systemctl restart lsws
echo "OpenLiteSpeed restarted."
# 7. Log Rotation
echo "Configuring log rotation..."
LOGROTATE_CONF="/etc/logrotate.d/${TOOL_SLUG}"
cat > "${LOGROTATE_CONF}" <api_sid = getenv('TWILIO_SID') ?: 'ACxxxxxxxxxxxxxxxxxxxxxxxxxxxxx';
$this->api_token = getenv('TWILIO_TOKEN') ?: 'your_auth_token';
}
public function initiateCall($toPhoneNumber, $fromPhoneNumber, $audioUrl, $statusCallbackUrl = null) {
if (empty($toPhoneNumber) || empty($fromPhoneNumber) || empty($audioUrl)) {
throw new Exception("To, From, and Audio URL are required to initiate a call.");
}
// Simulation for demonstration. In production, this would use the Twilio SDK.
$simulatedSid = 'CA' . substr(hash('sha256', $toPhoneNumber . microtime()), 0, 32);
return [
'sid' => $simulatedSid,
'status' => 'queued',
'options' => ['to' => $toPhoneNumber, 'from' => $fromPhoneNumber, 'audioUrl' => $audioUrl, 'statusCallback' => $statusCallbackUrl]
];
}
public function validateWebhook($expectedSignature, $url, $postData) {
// In a real app, this validation is critical for security and would use the Twilio SDK.
return true;
}
}```### FILE 9: /home/ai-prank-caller.digitalprank.com/public_html/voice_generator.php
```php
'success',
'voice' => $voiceStyle,
'url' => $publicUrl
];
}
}
```
### FILE 10: /home/ai-prank-caller.digitalprank.com/public_html/api.php
```php
setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION); }
catch (PDOException $e) { http_response_code(503); echo json_encode(['success' => false, 'message' => 'Service Unavailable: Database error.']); exit; }
require_once '/home/cdn.digitalprank.com/public_html/php/analytics_functions.php';
function api_error($message, $code = 400) { http_response_code($code); echo json_encode(['success' => false, 'message' => $message]); exit; }
$user_id = null; $input = [];
try {
$config = json_decode(file_get_contents(__DIR__ . '/tool_config.json'), true);
if (!$config) api_error('Internal Server Error: Cannot load tool config.', 500);
$api_key_header = $config['tool']['api']['auth_key_name'];
$api_key = $_SERVER[$api_key_header] ?? null;
if (empty($api_key)) api_error('Authentication failed: Missing API key in ' . str_replace('HTTP_','', $api_key_header) . ' header.', 401);
$stmt = $pdo->prepare("SELECT user_id FROM wp_digitalprank_api_keys WHERE api_key = ? AND tool_slug = ? AND status = 'active'");
$stmt->execute([$api_key, $tool_slug]);
if (!($user_id = $stmt->fetchColumn())) api_error('Authentication failed: Invalid or revoked API key.', 403);
$stmt = $pdo->prepare("SELECT subscription_plan_id FROM wp_pms_member_subscriptions WHERE user_id = ? AND status = 'active' ORDER BY id DESC LIMIT 1");
$stmt->execute([$user_id]);
if (!in_array($stmt->fetchColumn(), [176, 186])) api_error('Authorization failed: API access requires an Ultimate tier subscription.', 403);
$input = json_decode(file_get_contents('php://input'), true);
if (json_last_error() !== JSON_ERROR_NONE) api_error('Invalid input: Request body must be valid JSON.');
$script = $input['script_prompt'] ?? ''; $voice = $input['voice_style'] ?? ''; $victim_phone = $input['victim_phone'] ?? '';
$caller_id = $input['caller_id'] ?? '+15550001234';
if (empty($script) || empty($voice) || empty($victim_phone)) api_error('Invalid input: `script_prompt`, `voice_style`, and `victim_phone` are required.');
$voice_gen = new VoiceGenerator();
$audio_result = $voice_gen->generateAudio($script, $voice);
$audio_url = $audio_result['url'];
$webhook_url = "https://{$tool_slug}.digitalprank.com/webhook_handler.php";
$twilio_handler = new TwilioHandler();
$call_result = $twilio_handler->initiateCall($victim_phone, $caller_id, $audio_url, $webhook_url);
$call_sid = $call_result['sid'];
$stmt = $pdo->prepare("INSERT INTO prank_call_history (user_id, victim_phone, caller_id, script_prompt, voice_style, audio_url, twilio_sid, status, created_at) VALUES (?, ?, ?, ?, ?, ?, ?, 'queued', NOW())");
$stmt->execute([$user_id, $victim_phone, $caller_id, $script, $voice, $audio_url, $call_sid]);
$history_id = $pdo->lastInsertId();
$response_data = ['success' => true, 'message' => 'Prank call initiated.', 'call_sid' => $call_sid, 'history_id' => $history_id, 'status' => 'queued'];
http_response_code(202); // Accepted
echo json_encode($response_data);
logUsage($pdo, $tool_slug, $_SERVER['REMOTE_ADDR'], $user_id, 'api_call_sent', $input, $response_data, microtime(true) - $start_time);
} catch (Exception $e) {
logUsage($pdo, $tool_slug, $_SERVER['REMOTE_ADDR'], $user_id, 'api_call_failed', $input, ['error' => $e->getMessage()], microtime(true) - $start_time, 'failed');
api_error('An error occurred: ' . $e->getMessage(), 500);
}
```
### FILE 11: /home/ai-prank-caller.digitalprank.com/public_html/history.php
```php
setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION); }
catch (PDOException $e) { die("Database error. Please try again later."); }
$history = [];
if ($user_id > 0) {
$stmt = $pdo->prepare("SELECT * FROM prank_call_history WHERE user_id = ? ORDER BY created_at DESC LIMIT 100");
$stmt->execute([$user_id]);
$history = $stmt->fetchAll(PDO::FETCH_ASSOC);
}
?>
Call History - AI Prank Call Bot
```
### FILE 12: /home/ai-prank-caller.digitalprank.com/public_html/webhook_handler.php
```php
setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION); }
catch (PDOException $e) { error_log("Webhook DB connection failed: " . $e->getMessage()); http_response_code(503); exit; }
$post_data = $_POST;
$twilio_signature = $_SERVER['HTTP_X_TWILIO_SIGNATURE'] ?? '';
p
r
o
t
o
c
o
l
=
i
s
s
e
t
(
protocol=isset(
_SERVER['HTTPS']) && $_SERVER['HTTPS'] === 'on' ? "https" : "http";
u
r
l
=
"
url="
protocol://
S
E
R
V
E
R
[
H
T
T
P
H
O
S
T
]
S
ERVER[HTTP
H
OST]
_SERVER[REQUEST_URI]";
v
a
l
i
d
a
t
o
r
=
n
e
w
T
w
i
l
i
o
H
a
n
d
l
e
r
(
)
;
i
f
(
!
validator=newTwilioHandler();if(!
validator->validateWebhook($twilio_signature, $url,
post_data['CallSid'] ?? 'N/A') . " from IP: " . $_SERVER['REMOTE_ADDR']);
http_response_code(403); exit;
}
$call_sid = $post_data['CallSid'] ?? null;
$call_status = $post_data['CallStatus'] ?? null;
if ($call_sid && $call_status) {
try {
$stmt = $pdo->prepare("UPDATE prank_call_history SET status = :status, updated_at = NOW() WHERE twilio_sid = :sid");
$stmt->execute([':status' => $call_status, ':sid' => $call_sid]);
} catch (PDOException
call_sid}: " . $e->getMessage());
http_response_code(500); exit;
}
}
header('Content-Type: text/xml');
echo '';
exit;
code
Code
### FILE 13: /home/ai-prank-caller.digitalprank.com/public_html/cron_scheduler.php
```php
setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
} catch (PDOException $e) { error_log("Cron DB connection failed: " . $e->getMessage()); flock($lock_handle, LOCK_UN); fclose($lock_handle); exit; }
$tool_slug = 'ai-prank-caller';
echo "Running scheduler at " . date('Y-m-d H:i:s') . "\n";
try {
$stmt = $pdo->prepare("SELECT * FROM prank_call_history WHERE status = 'scheduled' AND scheduled_for <= NOW() LIMIT 10");
$stmt->execute();
$due_calls = $stmt->fetchAll(PDO::FETCH_ASSOC);
if (!empty($due_calls)) {
$twilio_handler = new TwilioHandler();
$webhook_url = "https://{$tool_slug}.digitalprank.com/webhook_handler.php";
echo "Found " . count($due_calls) . " calls to process.\n";
foreach ($due_calls as $call) {
try {
$call_result = $twilio_handler->initiateCall($call['victim_phone'], $call['caller_id'], $call['audio_url'], $webhook_url);
$update_stmt = $pdo->prepare("UPDATE prank_call_history SET status = :status, twilio_sid = :sid, updated_at = NOW() WHERE id = :id");
$update_stmt->execute([':status' => $call_result['status'], ':sid' => $call_result['sid'], ':id' => $call['id']]);
echo "Successfully queued call ID {$call['id']} with SID {$call_result['sid']}.\n";
} catch (Exception $e) {
$fail_stmt = $pdo->prepare("UPDATE prank_call_history SET status = 'failed', updated_at = NOW() WHERE id = :id");
$fail_stmt->execute([':id' => $call['id']]);
error_log("Cron failed to process call ID {$call['id']}: " . $e->getMessage());
}
}
} else {
echo "No due calls found.\n";
}
} catch (PDOException $e) { error_log("Cron job database error: " . $e->getMessage()); }
flock($lock_handle, LOCK_UN);
fclose($lock_handle);
echo "Scheduler finished.\n";
exit;```
### FILE 14: /home/ai-prank-caller.digitalprank.com/public_html/assets/style.css
```css
/* AI Prank Caller Stylesheet v1.5 */
body { font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Helvetica, Arial, sans-serif; background-color: #f4f4f9; color: #333; margin: 0; padding: 2rem; }
.container { max-width: 900px; margin: auto; background: #fff; padding: 2rem; border-radius: 8px; box-shadow: 0 4px 12px rgba(0,0,0,0.1); }
h1 { color: #FF4500; text-align: center; }
h2 { color: #333; border-bottom: 2px solid #f0f0f0; padding-bottom: 0.5rem; margin-top: 2rem; }
p.tagline { text-align: center; color: #666; margin-top: -10px; margin-bottom: 2rem; }
.nav-links { text-align: center; margin-bottom: 2rem; border-bottom: 1px solid #eee; padding-bottom: 1.5rem; }
.nav-links a { margin: 0 15px; color: #333; text-decoration: none; font-weight: bold; padding: 8px 12px; border-radius: 6px; transition: background-color 0.2s; }
.nav-links a:hover { background-color: #f0f0f0; }
.form-group { margin-bottom: 1.5rem; }
.form-group label { display: block; font-weight: bold; margin-bottom: 0.5rem; }
.pro-badge { background-color: gold; color: #333; font-size: 0.7rem; padding: 2px 5px; border-radius: 4px; margin-left: 8px; font-weight: bold; }
input[type="text"], input[type="tel"], input[type="datetime-local"], select, textarea { width: 100%; padding: 10px; border-radius: 4px; border: 1px solid #ccc; box-sizing: border-box; }
textarea { min-height: 100px; resize: vertical; }
.submit-btn, .btn { display: inline-block; padding: 12px 20px; background-color: #FF4500; color: white; border: none; border-radius: 4px; font-size: 1rem; cursor: pointer; text-decoration: none; text-align: center; }
.submit-btn { width: 100%; font-size: 1.2rem; }
.submit-btn:disabled { background-color: #ccc; cursor: not-allowed; }
#result-modal { display: none; position: fixed; z-index: 1000; left: 0; top: 0; width: 100%; height: 100%; background-color: rgba(0,0,0,0.5); }
.modal-content { background-color: #fefefe; margin: 15% auto; padding: 20px; border-radius: 8px; width: 80%; max-width: 500px; text-align: center; }
.loader { border: 5px solid #f3f3f3; border-radius: 50%; border-top: 5px solid #FF4500; width: 40px; height: 40px; animation: spin 1s linear infinite; margin: 20px auto; }
@keyframes spin { 0% { transform: rotate(0deg); } 100% { transform: rotate(360deg); } }
table { width: 100%; border-collapse: collapse; margin-top: 1.5rem; }
th, td { padding: 12px; border-bottom: 1px solid #ddd; text-align: left; vertical-align: middle; }
th { background-color: #f8f8f8; }
.status { padding: 4px 8px; border-radius: 12px; color: white; font-size: 0.8rem; text-transform: capitalize; display: inline-block; }
.status-completed { background-color: #28a745; }
.status-queued, .status-pending, .status-ringing, .status-initiated, .status-in-progress, .status-scheduled { background-color: #ffc107; color: #333; }
.status-failed, .status-canceled { background-color: #dc3545; }
.status-busy, .status-no-answer { background-color: #17a2b8; }
.no-history { text-align: center; color: #777; padding: 2rem; }
.account-info, .api-key-section { background-color: #f9f9f9; padding: 1.5rem; border-radius: 8px; margin-top: 1rem; }
.api-key-box { background-color: #fff; border: 1px solid #ddd; padding: 1rem; border-radius: 4px; font-family: monospace; word-wrap: break-word; margin: 1rem 0; }
.api-key-section p { font-size: 0.9rem; color: #555; }
FILE 15: /home/digitalprank.com/public_html/docs/api/ai-prank-caller.md
code
Markdown
# API Documentation: AI Prank Call Bot
Welcome to the AI Prank Call Bot API! This document provides all the information you need to integrate our hilarious prank call service into your own applications.
**API Version:** `v1`
**Base Endpoint:** `https://ai-prank-caller.digitalprank.com/api.php`
## Authentication
Authentication is handled via an API key passed in an HTTP header. Access is restricted to **Ultimate Tier** subscribers.
- **Header Name:** `X-API-Key`
- **Value:** Your unique API key.
You can generate and manage your API keys from your DigitalPrank.com account dashboard.
```bash
# Example Header
-H "X-API-Key: YOUR_ULTIMATE_TIER_API_KEY"
Rate Limiting
API access is subject to rate limits to ensure service stability. The current limits are:
10 requests per minute.
3 concurrent requests from the same API key.
If you exceed the rate limit, you will receive an HTTP 429 Too Many Requests response.
Endpoints
Initiate a Prank Call
This is the primary endpoint for creating and sending a new prank call.
Method: POST
Endpoint: /api.php
Request Body
The request body must be a raw JSON object with the following properties:
Parameter Type Required Description
script_prompt string Yes The text script for the AI to speak. Must be between 10 and 500 characters.
voice_style string Yes The voice to use. See available voice styles below.
victim_phone string Yes The recipient's phone number in E.164 format (e.g., +15551234567).
caller_id string No An E.164 formatted number to display as the caller ID. If omitted, a default number is used.
Available Voice Styles
annoying_robot, squeaky_chipmunk, scary_deep, sassy_female, movie_narrator, angry_neighbor, confused_old_lady, slick_salesman, nervous_guy
Example Request (cURL)
code
Bash
curl -X POST \
https://ai-prank-caller.digitalprank.com/api.php \
-H 'Content-Type: application/json' \
-H 'X-API-Key: YOUR_ULTIMATE_TIER_API_KEY' \
-d '{
"script_prompt": "Hello, this is the Department of Motor Vehicles. We are calling to inform you that your license has been suspended due to excessive coolness. Please report to our office immediately.",
"voice_style": "movie_narrator",
"victim_phone": "+15551234567",
"caller_id": "+15558675309"
}'
Success Response (HTTP 202 Accepted)
If the request is valid, the call will be queued for delivery and you will receive a 202 Accepted response.
code
JSON
{
"success": true,
"message": "Prank call initiated.",
"call_sid": "CAa1b2c3d4e5f6a7b8c9d0e1f2a3b4c5d6",
"history_id": "12345",
"status": "queued"
}
call_sid: The unique identifier for the call from our telephony provider (Twilio). You can use this for tracking.
history_id: The unique identifier for this call in the DigitalPrank database.
status: The initial status of the call. It will be updated via webhook as it progresses.
Error Responses
HTTP 400 Bad Request: Sent if the JSON body is malformed or required parameters are missing.
HTTP 401 Unauthorized: Sent if the X-API-Key header is missing.
HTTP 403 Forbidden: Sent if the API key is invalid, revoked, or does not belong to an Ultimate tier subscriber.
HTTP 500 Internal Server Error: Sent if an unexpected error occurs on our end.
Webhooks for Call Status
Our system uses webhooks to provide real-time status updates for your calls. When a call's status changes (e.g., from queued to ringing, completed, or failed), our provider (Twilio) will send a POST request to our webhook handler, which updates our database. You can view the final status of any call by checking your History page on the main website.
Last Updated: 2025-09-25
code
Code
### FILE 16: /home/ai-prank-caller.digitalprank.com/public_html/account.php
```php
setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION); }
catch (PDOException $e) { die("Database error."); }
require_once '/home/cdn.digitalprank.com/public_html/php/analytics_functions.php';
$access = getUserAccessLevel($pdo, $user_id, $tool_slug);
$config = json_decode(file_get_contents('tool_config.json'), true);
$daily_limit = $config['tool']['limits']['tier_daily'][$access['level']] ?? 0;
// Handle API Key Generation
$api_key = null;
if ($_SERVER['REQUEST_METHOD'] === 'POST' && isset($_POST['generate_api_key']) && $access['level'] === 'ultimate') {
// Invalidate old key
$stmt = $pdo->prepare("UPDATE wp_digitalprank_api_keys SET status = 'revoked' WHERE user_id = ? AND tool_slug = ?");
$stmt->execute([$user_id, $tool_slug]);
// Generate new key
$new_key = 'dpk_' . bin2hex(random_bytes(24));
$stmt = $pdo->prepare("INSERT INTO wp_digitalprank_api_keys (user_id, tool_slug, api_key, status) VALUES (?, ?, ?, 'active')");
$stmt->execute([$user_id, $tool_slug, $new_key]);
logUsage($pdo, $tool_slug, $_SERVER['REMOTE_ADDR'], $user_id, 'api_key_generated', [], [], 0);
// Refresh the page to show the new key
header('Location: account.php'); exit;
}
// Fetch existing API key for Ultimate users
if ($access['level'] === 'ultimate') {
$stmt = $pdo->prepare("SELECT api_key FROM wp_digitalprank_api_keys WHERE user_id = ? AND tool_slug = ? AND status = 'active'");
$stmt->execute([$user_id, $tool_slug]);
$api_key = $stmt->fetchColumn();
}
?>
My Account - AI Prank Call Bot