Files
webgis-poverty-pontianak/api/dashboard/stats.php
T

197 lines
7.4 KiB
PHP

<?php
header('Content-Type: application/json; charset=UTF-8');
require_once '../auth_helper.php';
requireLogin();
include_once '../db_connect.php';
$user = getCurrentUser();
$isPengelola = $user['role'] === 'pengelola';
$ibadahId = $isPengelola ? intval($user['ibadah_id']) : null;
// ── Helper: Haversine distance in meters ──────────────────────────────────
function haversine($lat1, $lng1, $lat2, $lng2) {
$R = 6371000;
$dLat = deg2rad($lat2 - $lat1);
$dLng = deg2rad($lng2 - $lng1);
$a = sin($dLat/2)*sin($dLat/2)
+ cos(deg2rad($lat1))*cos(deg2rad($lat2))*sin($dLng/2)*sin($dLng/2);
return $R * 2 * atan2(sqrt($a), sqrt(1-$a));
}
// ── 1. Rumah Ibadah ───────────────────────────────────────────────────────
if ($isPengelola && $ibadahId) {
$riRes = $conn->query("SELECT * FROM rumah_ibadah WHERE id=$ibadahId");
} else {
$riRes = $conn->query("SELECT * FROM rumah_ibadah");
}
$ibadahList = [];
while ($row = $riRes->fetch_assoc()) $ibadahList[] = $row;
$totalIbadah = count($ibadahList);
// Distribusi per jenis
$jenisDist = [];
foreach ($ibadahList as $ib) {
$j = $ib['jenis'] ?? 'Lainnya';
$jenisDist[$j] = ($jenisDist[$j] ?? 0) + 1;
}
// ── 2. Penduduk Miskin ────────────────────────────────────────────────────
$pmRes = $conn->query("SELECT * FROM penduduk_miskin");
$allMiskin = [];
while ($row = $pmRes->fetch_assoc()) $allMiskin[] = $row;
// Filter: pengelola hanya lihat yang dalam radius ibadahnya
if ($isPengelola && $ibadahId && !empty($ibadahList)) {
$ib = $ibadahList[0];
$filteredMiskin = array_filter($allMiskin, function($m) use ($ib) {
return haversine((float)$ib['lat'], (float)$ib['lng'], (float)$m['lat'], (float)$m['lng']) <= (float)$ib['radius'];
});
$filteredMiskin = array_values($filteredMiskin);
} else {
$filteredMiskin = $allMiskin;
}
$totalMiskin = count($filteredMiskin);
$totalJiwa = array_sum(array_column($filteredMiskin, 'jumlah_jiwa'));
// Kategori bantuan
$kategoriDist = [];
foreach ($filteredMiskin as $m) {
$k = $m['kategori_bantuan'] ?? 'Lainnya';
$kategoriDist[$k] = ($kategoriDist[$k] ?? 0) + 1;
}
// Terurus vs Tidak (dalam radius salah satu ibadah)
$terurusCount = 0;
$tidakTerurusCount = 0;
foreach ($filteredMiskin as $m) {
$inAnyRadius = false;
foreach ($ibadahList as $ib) {
if (haversine((float)$ib['lat'], (float)$ib['lng'], (float)$m['lat'], (float)$m['lng']) <= (float)$ib['radius']) {
$inAnyRadius = true;
break;
}
}
if ($inAnyRadius) $terurusCount++;
else $tidakTerurusCount++;
}
// Jika admin: hitung seluruh miskin dalam radius seluruh ibadah
if (!$isPengelola) {
$allIbadahRes = $conn->query("SELECT * FROM rumah_ibadah");
$allIbadahList = [];
while ($row = $allIbadahRes->fetch_assoc()) $allIbadahList[] = $row;
$terurusCount = 0;
$tidakTerurusCount = 0;
foreach ($allMiskin as $m) {
$inAnyRadius = false;
foreach ($allIbadahList as $ib) {
if (haversine((float)$ib['lat'], (float)$ib['lng'], (float)$m['lat'], (float)$m['lng']) <= (float)$ib['radius']) {
$inAnyRadius = true;
break;
}
}
if ($inAnyRadius) $terurusCount++;
else $tidakTerurusCount++;
}
}
// ── 3. Log Bantuan ────────────────────────────────────────────────────────
if ($isPengelola && $ibadahId) {
$logRes = $conn->query("
SELECT lb.*, ri.nama as nama_ibadah, ri.jenis as jenis_ibadah, pm.nama as nama_kk
FROM log_bantuan lb
JOIN rumah_ibadah ri ON ri.id = lb.ibadah_id
JOIN penduduk_miskin pm ON pm.id = lb.miskin_id
WHERE lb.ibadah_id = $ibadahId
ORDER BY lb.tanggal DESC, lb.id DESC
LIMIT 10
");
$totalLogRes = $conn->query("SELECT COUNT(*) as cnt FROM log_bantuan WHERE ibadah_id=$ibadahId");
} else {
$logRes = $conn->query("
SELECT lb.*, ri.nama as nama_ibadah, ri.jenis as jenis_ibadah, pm.nama as nama_kk
FROM log_bantuan lb
JOIN rumah_ibadah ri ON ri.id = lb.ibadah_id
JOIN penduduk_miskin pm ON pm.id = lb.miskin_id
ORDER BY lb.tanggal DESC, lb.id DESC
LIMIT 10
");
$totalLogRes = $conn->query("SELECT COUNT(*) as cnt FROM log_bantuan");
}
$recentLogs = [];
while ($row = $logRes->fetch_assoc()) $recentLogs[] = $row;
$totalLog = 0;
if ($totalLogRes && $trow = $totalLogRes->fetch_assoc()) $totalLog = (int)$trow['cnt'];
// Distribusi tipe bantuan dari log
$tipeDist = [];
if ($isPengelola && $ibadahId) {
$tipeRes = $conn->query("SELECT tipe_bantuan, COUNT(*) as cnt FROM log_bantuan WHERE ibadah_id=$ibadahId GROUP BY tipe_bantuan");
} else {
$tipeRes = $conn->query("SELECT tipe_bantuan, COUNT(*) as cnt FROM log_bantuan GROUP BY tipe_bantuan");
}
while ($row = $tipeRes->fetch_assoc()) $tipeDist[$row['tipe_bantuan']] = (int)$row['cnt'];
// Bantuan per bulan (6 bulan terakhir)
if ($isPengelola && $ibadahId) {
$bulanRes = $conn->query("
SELECT DATE_FORMAT(tanggal, '%Y-%m') as bulan, COUNT(*) as cnt
FROM log_bantuan
WHERE ibadah_id=$ibadahId AND tanggal >= DATE_SUB(CURDATE(), INTERVAL 6 MONTH)
GROUP BY bulan ORDER BY bulan ASC
");
} else {
$bulanRes = $conn->query("
SELECT DATE_FORMAT(tanggal, '%Y-%m') as bulan, COUNT(*) as cnt
FROM log_bantuan
WHERE tanggal >= DATE_SUB(CURDATE(), INTERVAL 6 MONTH)
GROUP BY bulan ORDER BY bulan ASC
");
}
$bantuanPerBulan = [];
while ($row = $bulanRes->fetch_assoc()) $bantuanPerBulan[] = $row;
// ── 4. Ibadah Tipe (admin only: performa per ibadah) ─────────────────────
$ibadahPerforma = [];
if (!$isPengelola) {
$perfRes = $conn->query("
SELECT ri.id, ri.nama, ri.jenis, ri.radius,
COUNT(DISTINCT lb.id) as total_log,
COUNT(DISTINCT lb.miskin_id) as total_penerima
FROM rumah_ibadah ri
LEFT JOIN log_bantuan lb ON lb.ibadah_id = ri.id
GROUP BY ri.id
ORDER BY total_log DESC
");
while ($row = $perfRes->fetch_assoc()) $ibadahPerforma[] = $row;
}
// ── Output ────────────────────────────────────────────────────────────────
echo json_encode([
'status' => 'success',
'role' => $user['role'],
'ibadah_id' => $ibadahId,
'stats' => [
'total_ibadah' => $totalIbadah,
'total_miskin' => $totalMiskin,
'total_jiwa' => $totalJiwa,
'total_log' => $totalLog,
'terurus' => $terurusCount,
'tidak_terurus' => $tidakTerurusCount,
'pct_terurus' => $totalMiskin > 0 ? round($terurusCount / $totalMiskin * 100, 1) : 0,
],
'distribusi' => [
'jenis_ibadah' => $jenisDist,
'kategori' => $kategoriDist,
'tipe_bantuan' => $tipeDist,
'per_bulan' => $bantuanPerBulan,
],
'ibadah_list' => $ibadahList,
'ibadah_performa' => $ibadahPerforma,
'recent_logs' => $recentLogs,
]);