<?php
namespace App\Controllers;

use App\Core\Auth;
use App\Core\Controller;
use App\Core\Database;
use App\Core\Notifier;

class NotificationsController extends Controller
{
    public function index(): void
    {
        if (!Auth::check()) { $this->redirect('/login'); }
        $u = Auth::user();
        $pdo = Database::pdo();
        Notifier::ensureTables($pdo);
        $stmt = $pdo->prepare('SELECT * FROM notifications WHERE user_id = ? ORDER BY created_at DESC LIMIT 100');
        $stmt->execute([(int)$u['id']]);
        $notifications = array_map(static function (array $row): array {
            $row['url'] = Notifier::normalizeUrl($row['url'] ?? null) ?? '';
            return $row;
        }, $stmt->fetchAll() ?: []);
        $this->view('notifications/index', compact('notifications'));
    }

    public function feed(): void
    {
        if (!Auth::check()) {
            http_response_code(401);
            header('Content-Type: application/json; charset=utf-8');
            echo json_encode(['ok' => false, 'error' => 'unauthorized']);
            return;
        }

        $u = Auth::user();
        $pdo = Database::pdo();
        Notifier::ensureTables($pdo);

        $countStmt = $pdo->prepare('SELECT COUNT(*) FROM notifications WHERE user_id = ? AND is_read = 0');
        $countStmt->execute([(int)$u['id']]);
        $unreadCount = (int)($countStmt->fetchColumn() ?: 0);

        $stmt = $pdo->prepare('SELECT id, title, body, url, is_read, created_at FROM notifications WHERE user_id = ? ORDER BY created_at DESC LIMIT 10');
        $stmt->execute([(int)$u['id']]);
        $rows = $stmt->fetchAll() ?: [];

        $notifications = array_map(static function (array $row): array {
            $title = (string)($row['title'] ?? '');
            $body = (string)($row['body'] ?? '');
            $isMention = str_contains(strtolower($title), 'mention')
                || str_contains(strtolower($body), 'mention')
                || (bool)preg_match('/@\[[^\]]+\]|@[a-z0-9_\.-]+/i', $body);

            return [
                'id' => (int)($row['id'] ?? 0),
                'title' => $title,
                'body' => $body,
                'url' => Notifier::normalizeUrl($row['url'] ?? null) ?? '',
                'is_read' => (int)($row['is_read'] ?? 0),
                'created_at' => (string)($row['created_at'] ?? ''),
                'is_mention' => $isMention,
            ];
        }, $rows);

        header('Content-Type: application/json; charset=utf-8');
        echo json_encode([
            'ok' => true,
            'unread' => $unreadCount,
            'notifications' => $notifications,
        ], JSON_UNESCAPED_UNICODE | JSON_UNESCAPED_SLASHES);
    }

    public function readAll(): void
    {
        if (!Auth::check()) { $this->redirect('/login'); }
        $u = Auth::user();
        $pdo = Database::pdo();
        Notifier::ensureTables($pdo);
        $up = $pdo->prepare('UPDATE notifications SET is_read = 1 WHERE user_id = ?');
        $up->execute([(int)$u['id']]);
        if ($this->wantsJson()) {
            header('Content-Type: application/json; charset=utf-8');
            echo json_encode(['ok' => true, 'unread' => 0], JSON_UNESCAPED_UNICODE | JSON_UNESCAPED_SLASHES);
            return;
        }
        $this->redirect('/notifications');
    }

    public function read(): void
    {
        if (!Auth::check()) {
            if ($this->wantsJson()) {
                http_response_code(401);
                header('Content-Type: application/json; charset=utf-8');
                echo json_encode(['ok' => false, 'error' => 'unauthorized']);
                return;
            }
            $this->redirect('/login');
            return;
        }

        $notificationId = (int)($_POST['id'] ?? $_GET['id'] ?? 0);
        if ($notificationId <= 0) {
            if ($this->wantsJson()) {
                http_response_code(422);
                header('Content-Type: application/json; charset=utf-8');
                echo json_encode(['ok' => false, 'error' => 'invalid_notification_id']);
                return;
            }
            $this->redirect('/notifications');
            return;
        }

        $u = Auth::user();
        $pdo = Database::pdo();
        Notifier::ensureTables($pdo);

        $updateStmt = $pdo->prepare('UPDATE notifications SET is_read = 1 WHERE id = ? AND user_id = ?');
        $updateStmt->execute([$notificationId, (int)$u['id']]);

        $countStmt = $pdo->prepare('SELECT COUNT(*) FROM notifications WHERE user_id = ? AND is_read = 0');
        $countStmt->execute([(int)$u['id']]);
        $unreadCount = (int)($countStmt->fetchColumn() ?: 0);

        if ($this->wantsJson()) {
            header('Content-Type: application/json; charset=utf-8');
            echo json_encode([
                'ok' => true,
                'notification_id' => $notificationId,
                'unread' => $unreadCount,
            ], JSON_UNESCAPED_UNICODE | JSON_UNESCAPED_SLASHES);
            return;
        }

        $this->redirect('/notifications');
    }

    private function wantsJson(): bool
    {
        $accept = strtolower((string)($_SERVER['HTTP_ACCEPT'] ?? ''));
        $requestedWith = strtolower((string)($_SERVER['HTTP_X_REQUESTED_WITH'] ?? ''));

        return str_contains($accept, 'application/json') || $requestedWith === 'xmlhttprequest';
    }
}
