<?php
// cron_engine.php
// Script ini didesain khusus untuk dijalankan via Cronjob secara berkala (misal tiap 5-10 menit).
// Script tidak membutuhkan login (session) dan akan mengeksekusi sebagian kecil media 
// secara bergantian agar aman dari Timeout Server dan Rate Limit AI.

require_once 'db.php';

// Atur header dan timeout untuk cronjob
header('Content-Type: text/plain; charset=utf-8');
header('Cache-Control: no-cache');
set_time_limit(300); // Max eksekusi 5 menit per run

function cron_log($msg) {
    $time = date('Y-m-d H:i:s');
    echo "[$time] $msg\n";
    flush();
}

try {
    cron_log("=== MULAI CRONJOB ENGINE ===");

    // Implementasi Pembagian Waktu (Batching per Menit)
    // Menit dibagi menjadi blok 5 menit (0-4, 5-9, dst). Masing-masing batch memproses media secara proporsional.
    $minute = (int)date('i');
    $batch_index = floor($minute / 5);
    
    // Hitung total media aktif
    $stmt_total = $pdo->query("SELECT COUNT(id) FROM media WHERE url IS NOT NULL AND url != ''");
    $total_media = $stmt_total->fetchColumn();
    
    if ($total_media == 0) {
        cron_log("Tidak ada media aktif yang bisa diproses.");
        exit;
    }

    // 1 jam = 60 menit. Blok 5 menit = 12 batch per jam.
    $total_batches = 12;
    $limit = ceil($total_media / $total_batches);
    if ($limit < 1) $limit = 1;

    $offset = $batch_index * $limit;
    
    cron_log("Menit saat ini: $minute. Memproses Batch Index: $batch_index (Media ke-" . ($offset + 1) . " s/d " . ($offset + $limit) . " dari total $total_media media)");
    
    // Kita ambil berdasarkan ID agar konsisten pembagian offset-nya
    $stmt_media = $pdo->query("SELECT * FROM media WHERE url IS NOT NULL AND url != '' ORDER BY id ASC LIMIT $limit OFFSET $offset");
    $medias = $stmt_media->fetchAll(PDO::FETCH_ASSOC);

    cron_log("Ditemukan " . count($medias) . " media dalam antrean untuk di-scrape saat ini.");

    foreach ($medias as $media) {
        cron_log("-----------------------------------------");
        cron_log("Memproses Media: " . $media['nama'] . " (ID: " . $media['id'] . ")");

        // Update waktu terakhir disrape DULUAN supaya kalau error tidak nyangkut terus di atas
        $now = date('Y-m-d H:i:s');
        $update_time = $pdo->prepare("UPDATE media SET last_scraped_at = ? WHERE id = ?");
        $update_time->execute([$now, $media['id']]);

        // Ambil data Instansi yang menaungi media ini
        $instansi_id = $media['instansi_id'];
        $stmt_instansi = $pdo->prepare("SELECT * FROM instansi WHERE id = ? AND status = 'aktif'");
        $stmt_instansi->execute([$instansi_id]);
        $instansi = $stmt_instansi->fetch(PDO::FETCH_ASSOC);

        // Ambil Aturan Entitas (Weighted Scoring)
        $stmt_entities = $pdo->prepare("SELECT entity, type, score FROM instansi_entities WHERE instansi_id = ?");
        $stmt_entities->execute([$instansi_id]);
        $db_entities = $stmt_entities->fetchAll(PDO::FETCH_ASSOC);

        if (!$instansi) {
            cron_log("-> Skip: Instansi ID $instansi_id tidak ditemukan atau suspend.");
            continue;
        }

        $api_key = trim($instansi['api_key_ai']);
        $ai_agent = trim($instansi['ai_agent'] ?? 'Groq');
        $ai_model = trim($instansi['ai_model'] ?? 'llama3-70b-8192');
        $keywords_raw = trim($instansi['keyword_global']);
        $blacklist_raw = trim($instansi['blacklist'] ?? 'judi, slot, kasino, togel, porn, pinjol, bokep, judol');
        $demoted_raw = trim($instansi['demoted_keywords'] ?? '');

        // 1. Ambil conflict dari DB
        $instansi_entities = [];
        foreach ($db_entities as $e) {
            if ($e['type'] === 'conflict') {
                $instansi_entities[] = $e;
            }
        }
        
        // 2. Selalu gunakan keyword_global sebagai target (dynamic, up-to-date)
        $keyword_list = array_filter(array_map('trim', explode(',', $keywords_raw)));
        if (!empty($keyword_list)) {
            foreach ($keyword_list as $kw) {
                $instansi_entities[] = ['entity' => $kw, 'type' => 'target', 'score' => 50];
            }
        }

        if (empty($api_key)) {
            cron_log("-> Skip: API Key Groq untuk instansi ini belum disetting.");
            continue;
        }

        $keyword_list = array_map('trim', explode(',', $keywords_raw));
        $keyword_list = array_filter($keyword_list);

        $rss_url = $media['url'];
        $tier_media = $media['tier'] ?? 'Tier 3';

        // 1. Fetch XML
        $ch = curl_init($rss_url);
        curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
        curl_setopt($ch, CURLOPT_TIMEOUT, 15);
        curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true);
        curl_setopt($ch, CURLOPT_USERAGENT, 'Mozilla/5.0 (Windows NT 10.0; Win64; x64)');
        curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false);
        $rss_content = curl_exec($ch);
        $http_code = curl_getinfo($ch, CURLINFO_HTTP_CODE);
        curl_close($ch);

        if (!$rss_content || $http_code != 200) {
            cron_log("-> Gagal load RSS (HTTP $http_code). Skip.");
            continue;
        }

        // Clean XML
        $rss_content = preg_replace('/xmlns[^=]*="[^"]*"/i', '', $rss_content);
        $rss = @simplexml_load_string($rss_content, 'SimpleXMLElement', LIBXML_NOCDATA);

        $items = [];
        if ($rss && isset($rss->channel->item)) $items = $rss->channel->item; 
        elseif ($rss && isset($rss->entry)) $items = $rss->entry; 

        if (empty($items)) {
            cron_log("-> Format XML tidak dikenali / Kosong. Skip.");
            continue;
        }

        $berita_baru = 0;
        $count_item = 0;

        foreach ($items as $item) {
            if ($count_item >= 5) break; // Limit 5 berita per media per run

            $judul = isset($item->title) ? strip_tags((string)$item->title) : '';
            $link = isset($item->link['href']) ? (string)$item->link['href'] : (string)$item->link;
            $raw_desc = isset($item->description) ? (string)$item->description : ((string)$item->content ?: (string)$item->summary);
            $tanggal = isset($item->pubDate) ? (string)$item->pubDate : ((string)$item->published ?: (string)$item->updated);
            $deskripsi = strip_tags($raw_desc);

            // Thumbnail
            $thumbnail_url = '';
            if (isset($item->enclosure) && strpos((string)$item->enclosure['type'], 'image') !== false) {
                $thumbnail_url = (string) $item->enclosure['url'];
            }
            if (empty($thumbnail_url) && preg_match('/<img[^>]+src=[\'"]([^\'"]+)[\'"]/i', $raw_desc, $matches)) {
                $thumbnail_url = $matches[1];
            }

            // Cek DB
            $stmt_cek = $pdo->prepare("SELECT id FROM berita WHERE guid = ? AND instansi_id = ?");
            $stmt_cek->execute([$link, $instansi_id]);
            if ($stmt_cek->rowCount() > 0) {
                continue; // Sudah ada
            }

            // 2. Rule Score PHP (Weighted Dominance)
            $target_score = 0;
            $conflict_score = 0;
            $matched_target_kws = [];
            $matched_conflict_kws = [];
            
            $judul_lower = strtolower($judul);
            $desc_lower = strtolower($deskripsi);

            // Cek entitas (Exact Word Matching)
            foreach ($instansi_entities as $rule) {
                $entity = strtolower($rule['entity']);
                $entity_escaped = preg_quote($entity, '/');
                $pattern = '/\b' . $entity_escaped . '\b/i';
                
                $matched = false;
                if (preg_match($pattern, $judul_lower) || preg_match($pattern, $desc_lower)) {
                    $matched = true;
                }

                if ($matched) {
                    if ($rule['type'] === 'target') {
                        $target_score += (int)$rule['score'];
                        if (!in_array($entity, $matched_target_kws)) $matched_target_kws[] = $entity;
                    } elseif ($rule['type'] === 'conflict') {
                        $conflict_score += (int)$rule['score'];
                        if (!in_array($entity, $matched_conflict_kws)) $matched_conflict_kws[] = $entity;
                    }
                }
            }

            // Base Score dari Weighted Dominance
            $score = $target_score - $conflict_score;

            // Source trusted
            $trusted_tiers = ['Tier 1', 'Tier 2'];
            if (in_array($tier_media, $trusted_tiers)) {
                $score += 20;
            }

            // Demoted Keywords
            $demoted = array_filter(array_map('trim', explode(',', $demoted_raw)));
            foreach ($demoted as $demotedKw) {
                $pattern = '/\b' . preg_quote($demotedKw, '/') . '\b/i';
                if (preg_match($pattern, $judul) || preg_match($pattern, $deskripsi)) {
                    $score -= 10;
                }
            }

            // Blacklist
            $blacklist = array_filter(array_map('trim', explode(',', $blacklist_raw)));
            if (empty($blacklist)) {
                $blacklist = ['judi', 'slot', 'kasino', 'togel', 'porn', 'pinjol', 'bokep', 'judol'];
            }
            $is_blacklisted = false;
            foreach ($blacklist as $bad) {
                $pattern = '/\b' . preg_quote($bad, '/') . '\b/i';
                if (preg_match($pattern, $judul) || preg_match($pattern, $deskripsi)) {
                    $score -= 80;
                    $is_blacklisted = true;
                    break;
                }
            }

            if ($is_blacklisted) {
                continue; // Skip silently on cron
            }

            // 3. Ambigu handling
            $content_to_analyze = $deskripsi;
            if (empty($matched_target_kws)) {
                $ch_html = curl_init($link);
                curl_setopt($ch_html, CURLOPT_RETURNTRANSFER, true);
                curl_setopt($ch_html, CURLOPT_FOLLOWLOCATION, true);
                curl_setopt($ch_html, CURLOPT_TIMEOUT, 10);
                curl_setopt($ch_html, CURLOPT_USERAGENT, 'Mozilla/5.0');
                $html_content = curl_exec($ch_html);
                curl_close($ch_html);

                if ($html_content) {
                    $html_text = strip_tags($html_content);
                    foreach ($instansi_entities as $rule) {
                        if ($rule['type'] !== 'target') continue;
                        $pattern = '/\b' . preg_quote($rule['entity'], '/i') . '\b/i';
                        if (preg_match($pattern, $html_text)) {
                            $matched_target_kws[] = $rule['entity'];
                            $target_score += 10;
                            $score += 10;
                            break;
                        }
                    }
                    $content_to_analyze = mb_strimwidth($html_text, 0, 1000, '...');
                }
            }

            if (empty($matched_target_kws) || $score < 30) {
                continue; // Tidak relevan, skip silently
            }

            // 4. Proses AI
            $sentimen_ai = 'netral';
            $urgensi_ai = 'rendah';
            $kategori_ai = 'Lainnya';
            $is_relevan = false;

            $keywords_str = implode(', ', $matched_target_kws);
            $conflict_str = implode(', ', $matched_conflict_kws);
            
           $system_prompt = "
AI monitoring berita instansi.
Target: {$keywords_str}
Aturan relevansi:
- Berita bernilai relevan (YA) jika menyebutkan, berlokasi di, atau berkaitan dengan Target.
- SANGAT PENTING: Pastikan berita BENAR-BENAR terkait konteks institusi/daerah Target. Jika Target adalah tokoh pemerintahan/daerah, TOLAK berita tentang artis/selebriti/pihak lain yang kebetulan memiliki nama sama (misal Lisa Blackpink, dll). Jika ragu atau konteksnya melenceng, jawab TIDAK relevan.
- Jangan menolak berita seputar kegiatan dinas, acara, atau pemerintahan di wilayah Target.
";
if (!empty($matched_conflict_kws)) {
    $system_prompt .= "
- Jika fokus berita pada entitas konflik [{$conflict_str}] maka relevansi=TIDAK.
";
}
if (!empty($demoted_raw)) {
    $system_prompt .= "
- Jika fokus utama pada [{$demoted_raw}] maka relevansi=TIDAK.
";
}
$system_prompt .= "
Kategori:
Infrastruktur
Pelayanan
Pendidikan
Kesehatan
Sosial
Keamanan
Politik
Lingkungan
Ekonomi
Lainnya
Rule:
- polisi/kriminal/narkoba/pencurian/pembunuhan=Keamanan
- jalan/jembatan/banjir=Infrastruktur
- rumah sakit/BPJS/puskesmas=Kesehatan
- sekolah/guru/siswa=Pendidikan
Tentukan:
- relevansi
- sentimen
- urgensi
- kategori
Balas JSON saja:
{
\"r\":\"YA/TIDAK\",
\"s\":\"POSITIF/NEGATIF/NETRAL\",
\"u\":\"TINGGI/SEDANG/RENDAH\",
\"k\":Sesuai list Kategori 
}
";
$user_prompt =
$judul . "\n" .
mb_substr(strip_tags($content_to_analyze), 0, 300);

            $headers = [
                'Content-Type: application/json',
                'Authorization: Bearer ' . $api_key
            ];

            $model_to_use = !empty($ai_model) ? $ai_model : 'llama3-70b-8192';
            $data = [
                "model" => $model_to_use,
                "messages" => [
                    ["role" => "system", "content" => $system_prompt], 
                    ["role" => "user", "content" => $user_prompt]
                ],
                "temperature" => 0.2
            ];

            $json_payload = json_encode($data, JSON_INVALID_UTF8_SUBSTITUTE | JSON_UNESCAPED_UNICODE);
            if ($json_payload === false) {
                cron_log("   [ERROR] Gagal menyusun request JSON (Invalid UTF-8).");
                continue;
            }

            $api_url = "https://api.groq.com/openai/v1/chat/completions";
            if ($ai_agent === 'KoboiLLM') {
                $api_url = "https://api.koboillm.com/v1/chat/completions";
            }

            $ch_ai = curl_init($api_url);
            curl_setopt($ch_ai, CURLOPT_RETURNTRANSFER, true);
            curl_setopt($ch_ai, CURLOPT_POST, true);
            curl_setopt($ch_ai, CURLOPT_HTTPHEADER, $headers);
            curl_setopt($ch_ai, CURLOPT_POSTFIELDS, $json_payload);
            curl_setopt($ch_ai, CURLOPT_TIMEOUT, 20);
            curl_setopt($ch_ai, CURLOPT_SSL_VERIFYPEER, false);
            
            $ai_response = curl_exec($ch_ai);
            curl_close($ch_ai);

            if ($ai_response) {
                $res_json = json_decode($ai_response, true);
                $raw_ai = $res_json['choices'][0]['message']['content'] ?? '';
                
                if (preg_match('/\{[\s\S]*\}/', str_replace(['```json', '```'], '', $raw_ai), $matches)) {
                    $hasil_ai = json_decode($matches[0], true);
                    if ($hasil_ai && isset($hasil_ai['r']) && trim(strtoupper($hasil_ai['r'])) === 'YA') {
                        $is_relevan = true;
                        $score += 50; 
                        $sentimen_ai = strtolower(trim($hasil_ai['s'] ?? 'netral'));
                        $urgensi_ai = strtolower(trim($hasil_ai['u'] ?? 'rendah'));
                        $kategori_ai = trim($hasil_ai['k'] ?? 'Lainnya');
                    }
                }
            }

            if (!$is_relevan) {
                sleep(2); // Jeda rate limit Groq untuk skip
                continue;
            }

            $sentimen_db = $sentimen_ai;
            if ($sentimen_ai === 'positif') $sentimen_db = 'baik';
            if ($sentimen_ai === 'negatif') $sentimen_db = 'buruk';

            $tgl_mysql = date('Y-m-d H:i:s', strtotime($tanggal));

            // 5. Insert ke DB
            $sql_insert = "INSERT INTO berita (instansi_id, guid, sumber, judul, link, tanggal, cuplikan, matched_keywords, thumbnail, sentimen, urgensi, kategori_berita) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)";
            $insert = $pdo->prepare($sql_insert);
            $insert->execute([
                $instansi_id, 
                $link, 
                $media['nama'], 
                $judul, 
                $link, 
                $tgl_mysql, 
                mb_strimwidth($deskripsi, 0, 500, '...'), 
                implode(', ', $matched_target_kws), 
                $thumbnail_url, 
                $sentimen_db, 
                $urgensi_ai,
                $kategori_ai
            ]);

            $berita_baru++;
            $count_item++;
            
            cron_log("   [+] Berita masuk: " . substr($judul, 0, 50) . "...");
            sleep(3); // JEDA RATE LIMIT AI MENCEGAH SPAM / BANNED
        }

        cron_log("-> Selesai memproses " . $media['nama'] . ". Dapat $berita_baru berita baru.");
    }

    // =========================================
    // AUTOMATED SOCIAL MEDIA SCRAPING (IG, TikTok, FB)
    // =========================================
    cron_log("-----------------------------------------");
    cron_log(">> Memulai Pengecekan Medsos Otomatis (Instagram, TikTok, Facebook)...");

    $stmt_active_inst = $pdo->query("SELECT * FROM instansi WHERE status = 'aktif'");
    $active_instansis = $stmt_active_inst->fetchAll(PDO::FETCH_ASSOC);

    $sosmed_platforms = [
        'Instagram' => 'site:instagram.com',
        'TikTok' => 'site:tiktok.com',
        'Facebook' => 'site:facebook.com'
    ];

    foreach ($active_instansis as $inst) {
        $inst_id = $inst['id'];
        $api_key = trim($inst['api_key_ai'] ?? '');
        if (empty($api_key)) continue;

        $kw_raw = trim($inst['keyword_global']);
        $kw_list = array_filter(array_map('trim', explode(',', $kw_raw)));
        if (empty($kw_list)) $kw_list = [$inst['nama_instansi']];

        $ai_agent = trim($inst['ai_agent'] ?? 'Groq');
        $ai_model = trim($inst['ai_model'] ?? 'llama3-70b-8192');

        foreach ($sosmed_platforms as $p_name => $p_site) {
            foreach ($kw_list as $kw) {
                $kw_clean = trim($kw);
                if (empty($kw_clean)) continue;

                cron_log("Scraping Medsos Otomatis: $p_name ($kw_clean)...");

                $rss_urls = [
                    "https://news.google.com/rss/search?q=" . urlencode($p_site . ' "' . $kw_clean . '" when:1m') . "&hl=id&gl=ID",
                    "https://www.bing.com/search?q=" . urlencode($p_site . ' "' . $kw_clean . '"') . "&format=rss"
                ];

                foreach ($rss_urls as $rss_url) {
                    $ch = curl_init($rss_url);
                    curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
                    curl_setopt($ch, CURLOPT_TIMEOUT, 10);
                    curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true);
                    curl_setopt($ch, CURLOPT_USERAGENT, 'Mozilla/5.0 (Windows NT 10.0; Win64; x64)');
                    curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false);
                    $rss_content = curl_exec($ch);
                    curl_close($ch);

                    if (!$rss_content) continue;

                    $rss_content = preg_replace('/xmlns[^=]*="[^"]*"/i', '', $rss_content);
                    $rss = @simplexml_load_string($rss_content, 'SimpleXMLElement', LIBXML_NOCDATA);
                    $items = [];
                    if ($rss && isset($rss->channel->item)) $items = $rss->channel->item;
                    elseif ($rss && isset($rss->entry)) $items = $rss->entry;

                    $count_sm = 0;
                    foreach ($items as $item) {
                        if ($count_sm >= 5) break;

                        $judul = isset($item->title) ? strip_tags((string)$item->title) : '';
                        $link = isset($item->link['href']) ? (string)$item->link['href'] : (string)$item->link;
                        $raw_desc = isset($item->description) ? (string)$item->description : ((string)$item->content ?: (string)$item->summary);
                        $tanggal = isset($item->pubDate) ? (string)$item->pubDate : ((string)$item->published ?: (string)$item->updated);
                        $deskripsi = strip_tags($raw_desc);

                        if (empty($judul) || empty($link)) continue;

                        // Anti-duplikasi
                        $stmt_cek = $pdo->prepare("SELECT id FROM berita WHERE instansi_id = ? AND (guid = ? OR link = ? OR judul = ?)");
                        $stmt_cek->execute([$inst_id, $link, $link, $judul]);
                        if ($stmt_cek->rowCount() > 0) continue;

                        // AI Evaluation
                        $sentimen_ai = 'netral';
                        $urgensi_ai = 'rendah';
                        $kategori_ai = 'Lainnya';
                        $is_relevan = false;

                        $system_prompt = "AI monitoring berita instansi. Target: {$kw_clean}. Rule: Relevan=YA jika menyebutkan/berkaitan target. SANGAT PENTING: Tolak (r=TIDAK) jika target adalah institusi/pejabat tapi berita tentang tokoh lain/artis dengan nama sama (misal Lisa Blackpink, dll). Tentukan r(YA/TIDAK), s(POSITIF/NEGATIF/NETRAL), u(TINGGI/SEDANG/RENDAH), k(Infrastruktur/Pelayanan/Pendidikan/Kesehatan/Sosial/Keamanan/Politik/Lingkungan/Ekonomi/Lainnya). Format JSON: {\"r\":\"YA\", \"s\":\"NETRAL\", \"u\":\"RENDAH\", \"k\":\"Lainnya\"}";
                        $user_prompt = $judul . "\n" . mb_substr($deskripsi, 0, 300);

                        $data_ai = [
                            "model" => $ai_model,
                            "messages" => [
                                ["role" => "system", "content" => $system_prompt],
                                ["role" => "user", "content" => $user_prompt]
                            ],
                            "temperature" => 0.2
                        ];

                        $api_url = ($ai_agent === 'KoboiLLM') ? "https://api.koboillm.com/v1/chat/completions" : "https://api.groq.com/openai/v1/chat/completions";

                        $ch_ai = curl_init($api_url);
                        curl_setopt($ch_ai, CURLOPT_RETURNTRANSFER, true);
                        curl_setopt($ch_ai, CURLOPT_POST, true);
                        curl_setopt($ch_ai, CURLOPT_HTTPHEADER, ['Content-Type: application/json', 'Authorization: Bearer ' . $api_key]);
                        curl_setopt($ch_ai, CURLOPT_POSTFIELDS, json_encode($data_ai));
                        curl_setopt($ch_ai, CURLOPT_TIMEOUT, 15);
                        curl_setopt($ch_ai, CURLOPT_SSL_VERIFYPEER, false);
                        $ai_res = curl_exec($ch_ai);
                        curl_close($ch_ai);

                        if ($ai_res) {
                            $res_json = json_decode($ai_res, true);
                            $raw_ai = $res_json['choices'][0]['message']['content'] ?? '';
                            if (preg_match('/\{[\s\S]*\}/', str_replace(['```json', '```'], '', $raw_ai), $m_json)) {
                                $h_ai = json_decode($m_json[0], true);
                                if ($h_ai && isset($h_ai['r']) && trim(strtoupper($h_ai['r'])) === 'YA') {
                                    $is_relevan = true;
                                    $sentimen_ai = strtolower(trim($h_ai['s'] ?? 'netral'));
                                    $urgensi_ai = strtolower(trim($h_ai['u'] ?? 'rendah'));
                                    $kategori_ai = trim($h_ai['k'] ?? 'Lainnya');
                                }
                            }
                        }

                        if (!$is_relevan) continue;

                        $sentimen_db = $sentimen_ai;
                        if ($sentimen_ai === 'positif') $sentimen_db = 'baik';
                        if ($sentimen_ai === 'negatif') $sentimen_db = 'buruk';
                        $tgl_mysql = date('Y-m-d H:i:s', strtotime($tanggal));

                        $sql_ins = "INSERT INTO berita (instansi_id, guid, sumber, judul, link, tanggal, cuplikan, matched_keywords, thumbnail, sentimen, urgensi, kategori_berita) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)";
                        $ins = $pdo->prepare($sql_ins);
                        $ins->execute([
                            $inst_id,
                            $link,
                            $p_name,
                            $judul,
                            $link,
                            $tgl_mysql,
                            mb_strimwidth($deskripsi, 0, 500, '...'),
                            $kw_clean,
                            '',
                            $sentimen_db,
                            $urgensi_ai,
                            $kategori_ai
                        ]);

                        $count_sm++;
                        cron_log("   [+] Medsos terbit: $p_name - " . substr($judul, 0, 45) . "...");
                        sleep(2);
                    }
                }
            }
        }
    }

    cron_log("=== SELESAI CRONJOB ENGINE ===");

} catch (Exception $e) {
    cron_log("Terjadi Kesalahan Server: " . $e->getMessage());
}
?>
