202 lines
9.5 KiB
PHP
202 lines
9.5 KiB
PHP
<?php
|
|
require_once 'db/config.php';
|
|
|
|
try {
|
|
$pdo = db();
|
|
|
|
// Timeframe filters
|
|
$today = date('Y-m-d');
|
|
$this_week_start = date('Y-m-d', strtotime('monday this week'));
|
|
$this_month_start = date('Y-m-01');
|
|
|
|
// Total calls
|
|
$stmt_calls_today = $pdo->prepare("SELECT COUNT(*) as total FROM call_tracking WHERE DATE(call_start_time) = ?");
|
|
$stmt_calls_today->execute([$today]);
|
|
$total_calls_today = $stmt_calls_today->fetch()['total'];
|
|
|
|
$stmt_calls_week = $pdo->prepare("SELECT COUNT(*) as total FROM call_tracking WHERE call_start_time >= ?");
|
|
$stmt_calls_week->execute([$this_week_start]);
|
|
$total_calls_week = $stmt_calls_week->fetch()['total'];
|
|
|
|
$stmt_calls_month = $pdo->prepare("SELECT COUNT(*) as total FROM call_tracking WHERE call_start_time >= ?");
|
|
$stmt_calls_month->execute([$this_month_start]);
|
|
$total_calls_month = $stmt_calls_month->fetch()['total'];
|
|
|
|
// Calls by source (for pie chart)
|
|
$stmt_calls_by_source = $pdo->query("
|
|
SELECT traffic_source, COUNT(*) as count
|
|
FROM call_tracking
|
|
GROUP BY traffic_source
|
|
ORDER BY count DESC
|
|
");
|
|
$calls_by_source = $stmt_calls_by_source->fetchAll();
|
|
$chart_labels_source = json_encode(array_column($calls_by_source, 'traffic_source'));
|
|
$chart_data_source = json_encode(array_column($calls_by_source, 'count'));
|
|
|
|
// AI Rescue Rate
|
|
$stmt_ai_rescue = $pdo->query("
|
|
SELECT
|
|
(SUM(CASE WHEN was_ai_rescue = 1 THEN 1 ELSE 0 END) / COUNT(*)) * 100 as rescue_rate
|
|
FROM call_tracking
|
|
WHERE call_status = 'missed' OR answered_by != 'human'
|
|
");
|
|
$ai_rescue_rate = $stmt_ai_rescue->fetchColumn() ?? 0;
|
|
|
|
// Recent calls
|
|
$stmt_recent_calls = $pdo->query('SELECT * FROM call_tracking ORDER BY call_start_time DESC LIMIT 10');
|
|
$recent_calls = $stmt_recent_calls->fetchAll();
|
|
|
|
} catch (PDOException $e) {
|
|
$error = "Database error: " . $e->getMessage();
|
|
}
|
|
|
|
$project_name = "HVAC Command Center";
|
|
$page_title = "Call Tracking";
|
|
|
|
?>
|
|
<!DOCTYPE html>
|
|
<html lang="en">
|
|
<head>
|
|
<meta charset="UTF-8">
|
|
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
|
<title><?= htmlspecialchars($page_title) ?> | <?= htmlspecialchars($project_name) ?></title>
|
|
<link href="https://cdn.jsdelivr.net/npm/bootstrap@5.3.3/dist/css/bootstrap.min.css" rel="stylesheet">
|
|
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/6.5.1/css/all.min.css">
|
|
<link rel="stylesheet" href="assets/css/custom.css?v=<?php echo time(); ?>">
|
|
</head>
|
|
<body>
|
|
|
|
<div class="sidebar">
|
|
<div class="sidebar-header">
|
|
<h2 class="h5"><i class="fas fa-tachometer-alt me-2"></i><?= htmlspecialchars($project_name) ?></h2>
|
|
</div>
|
|
<ul class="nav flex-column">
|
|
<li class="nav-item"><a class="nav-link" href="index.php"><i class="fas fa-home"></i>Dashboard</a></li>
|
|
<li class="nav-item"><a class="nav-link" href="customers.php"><i class="fas fa-users"></i>Customers</a></li>
|
|
<li class="nav-item"><a class="nav-link" href="bookings.php"><i class="fas fa-calendar-check"></i>Bookings</a></li>
|
|
<li class="nav-item"><a class="nav-link" href="ai-call-logs.php"><i class="fas fa-robot"></i>AI Call Logs</a></li>
|
|
<li class="nav-item"><a class="nav-link" href="chat-logs.php"><i class="fas fa-comments"></i>Chat Logs</a></li>
|
|
<li class="nav-item"><a class="nav-link active" href="call-tracking.php"><i class="fas fa-phone-alt"></i>Call Tracking</a></li>
|
|
<li class="nav-item"><a class="nav-link" href="reviews.php"><i class="fas fa-star"></i>Reviews</a></li>
|
|
<li class="nav-item"><a class="nav-link" href="calendar.php"><i class="fas fa-calendar-alt"></i>Calendar</a></li>
|
|
</ul>
|
|
</div>
|
|
|
|
<div class="main-content">
|
|
<header class="d-flex justify-content-between align-items-center mb-4">
|
|
<h1><?= htmlspecialchars($page_title) ?></h1>
|
|
</header>
|
|
|
|
<?php if (isset($error)): ?>
|
|
<div class="alert alert-danger"><i class="fas fa-exclamation-triangle me-2"></i> <?= htmlspecialchars($error) ?></div>
|
|
<?php else: ?>
|
|
<!-- Stat Cards -->
|
|
<div class="row g-4 mb-4">
|
|
<div class="col-lg-3 col-md-6">
|
|
<div class="card stat-card h-100">
|
|
<div class="card-body text-center">
|
|
<h6 class="text-muted">Calls Today</h6>
|
|
<h4 class="fw-bold mb-0"><?= $total_calls_today ?></h4>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
<div class="col-lg-3 col-md-6">
|
|
<div class="card stat-card h-100">
|
|
<div class="card-body text-center">
|
|
<h6 class="text-muted">This Week</h6>
|
|
<h4 class="fw-bold mb-0"><?= $total_calls_week ?></h4>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
<div class="col-lg-3 col-md-6">
|
|
<div class="card stat-card h-100">
|
|
<div class="card-body text-center">
|
|
<h6 class="text-muted">This Month</h6>
|
|
<h4 class="fw-bold mb-0"><?= $total_calls_month ?></h4>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
<div class="col-lg-3 col-md-6">
|
|
<div class="card stat-card h-100 bg-success text-white">
|
|
<div class="card-body text-center">
|
|
<h6 class="text-white">AI Rescue Rate</h6>
|
|
<h4 class="fw-bold mb-0"><?= number_format($ai_rescue_rate, 1) ?>%</h4>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- Charts -->
|
|
<div class="row g-4 mb-4">
|
|
<div class="col-md-6">
|
|
<div class="card">
|
|
<div class="card-header"><h5 class="m-0">Calls by Source</h5></div>
|
|
<div class="card-body"><canvas id="callsBySourceChart"></canvas></div>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- Recent Calls Table -->
|
|
<div class="card">
|
|
<div class="card-header"><h5 class="m-0">Recent Calls</h5></div>
|
|
<div class="card-body">
|
|
<div class="table-responsive">
|
|
<table class="table table-hover">
|
|
<thead>
|
|
<tr><th>Caller</th><th>Source</th><th>Status</th><th>Answered By</th><th>Duration</th><th>Date</th></tr>
|
|
</thead>
|
|
<tbody>
|
|
<?php foreach ($recent_calls as $call): ?>
|
|
<tr>
|
|
<td><?= htmlspecialchars($call['caller_name'] ?? $call['caller_number']) ?></td>
|
|
<td><span class="badge bg-info"><?= htmlspecialchars(ucwords(str_replace('_', ' ', $call['traffic_source']))) ?></span></td>
|
|
<td><?= htmlspecialchars(ucfirst($call['call_status'])) ?></td>
|
|
<td><?= htmlspecialchars(ucwords(str_replace('_', ' ', $call['answered_by']))) ?></td>
|
|
<td><?= $call['call_duration_seconds'] ? gmdate("i:s", $call['call_duration_seconds']) : 'N/A' ?></td>
|
|
<td><?= date("M d, Y h:i A", strtotime($call['call_start_time'])) ?></td>
|
|
</tr>
|
|
<?php endforeach; ?>
|
|
<?php if (empty($recent_calls)): ?>
|
|
<tr><td colspan="6" class="text-center text-muted">No calls recorded yet.</td></tr>
|
|
<?php endif; ?>
|
|
</tbody>
|
|
</table>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
<?php endif; ?>
|
|
</div>
|
|
|
|
<script src="https://cdn.jsdelivr.net/npm/bootstrap@5.3.3/dist/js/bootstrap.bundle.min.js"></script>
|
|
<script src="https://cdn.jsdelivr.net/npm/chart.js@4.4.2/dist/chart.umd.min.js"></script>
|
|
<script>
|
|
document.addEventListener('DOMContentLoaded', function() {
|
|
Chart.defaults.color = '#aab0bb';
|
|
Chart.defaults.borderColor = 'rgba(255, 255, 255, 0.1)';
|
|
const chartBackgroundColor = ['#4dc9ff', '#ff6384', '#ffce56', '#36a2eb', '#9966ff', '#ff9f40'];
|
|
|
|
// Chart for Calls by Source
|
|
const ctxSource = document.getElementById('callsBySourceChart');
|
|
if (ctxSource) {
|
|
new Chart(ctxSource, {
|
|
type: 'pie',
|
|
data: {
|
|
labels: <?= $chart_labels_source ?>,
|
|
datasets: [{
|
|
label: 'Calls',
|
|
data: <?= $chart_data_source ?>,
|
|
backgroundColor: chartBackgroundColor,
|
|
borderColor: '#2d3446',
|
|
borderWidth: 3
|
|
}]
|
|
},
|
|
options: {
|
|
responsive: true,
|
|
plugins: { legend: { position: 'bottom', labels: { color: '#aab0bb' } } }
|
|
}
|
|
});
|
|
}
|
|
});
|
|
</script>
|
|
</body>
|
|
</html>
|