<?php
// notifications_api.php - REST API for member notifications

// ============================================
// INITIALIZATION & CONFIGURATION
// ============================================

// Load CORS configuration FIRST
require_once __DIR__ . '/includes/cors.php';
configureCors();

// Load environment variables
require_once __DIR__ . '/includes/config_loader.php';

// Load dependencies
require_once __DIR__ . '/includes/config.php';
require_once __DIR__ . '/includes/auth_functions.php'; // Your existing auth functions
require_once __DIR__ . '/includes/sms_helper.php';
require_once __DIR__ . '/includes/email_helper.php'; // If you have separate email helper
require_once __DIR__ . '/auth/AuditLogger.php';
require_once __DIR__ . '/auth/JWTManager.php';

require_once __DIR__ . '/includes/internal_notification_helper.php';

// Set response headers
header('Content-Type: application/json');
header('Cache-Control: no-cache, no-store, must-revalidate');
header('Pragma: no-cache');
header('Expires: 0');

// Security headers
header('X-Frame-Options: DENY');
header('X-Content-Type-Options: nosniff');
header('X-XSS-Protection: 1; mode=block');

// Handle preflight OPTIONS request
if ($_SERVER['REQUEST_METHOD'] === 'OPTIONS') {
    http_response_code(200);
    exit();
}

// ============================================
// AUTHENTICATION
// ============================================

// Check if user is logged in
if (!isset($_SESSION['member_id'])) {
    http_response_code(401);
    echo json_encode([
        'success' => false,
        'error' => 'Authentication required',
        'code' => 'UNAUTHORIZED'
    ]);
    exit();
}

$memberId = (int)$_SESSION['member_id'];
$userRole = $_SESSION['role'] ?? 'member';

// ============================================
// HELPER FUNCTIONS
// ============================================

/**
 * Get all notifications for a member
 */
function getMemberNotifications($pdo, $memberId, $limit = 50, $offset = 0, $status = null) {
    try {
        $params = [$memberId];
        $whereClause = '';
        
        if ($status) {
            $whereClause = 'AND status = ?';
            $params[] = $status;
        }
        
        $sql = "
            SELECT 
                id,
                title,
                message,
                action_url,
                status,
                created_at,
                read_at
            FROM member_internal_notifications
            WHERE member_id = ? $whereClause
            ORDER BY 
                CASE WHEN status = 'unread' THEN 0 ELSE 1 END,
                created_at DESC
            LIMIT ? OFFSET ?
        ";
        
        $stmt = $pdo->prepare($sql);
        
        // Bind parameters with proper types
        $stmt->bindValue(1, $memberId, PDO::PARAM_INT);
        
        $paramIndex = 2;
        if ($status) {
            $stmt->bindValue($paramIndex, $status, PDO::PARAM_STR);
            $paramIndex++;
        }
        
        $stmt->bindValue($paramIndex, (int)$limit, PDO::PARAM_INT);
        $stmt->bindValue($paramIndex + 1, (int)$offset, PDO::PARAM_INT);
        
        $stmt->execute();
        $notifications = $stmt->fetchAll(PDO::FETCH_ASSOC);
        
        // Format timestamps
        foreach ($notifications as &$note) {
            $note['created_at_formatted'] = date('M j, Y g:i a', strtotime($note['created_at']));
            if ($note['read_at']) {
                $note['read_at_formatted'] = date('M j, Y g:i a', strtotime($note['read_at']));
            }
            $note['is_unread'] = ($note['status'] === 'unread');
        }
        
        return $notifications;
        
    } catch (PDOException $e) {
        error_log("Failed to fetch notifications: " . $e->getMessage());
        throw new RuntimeException('Failed to fetch notifications');
    }
}

/**
 * Get notification statistics
 */
function getNotificationStats($pdo, $memberId) {
    try {
        $sql = "
            SELECT 
                COUNT(*) as total,
                SUM(CASE WHEN status = 'unread' THEN 1 ELSE 0 END) as unread,
                SUM(CASE WHEN status = 'read' THEN 1 ELSE 0 END) as read_count
            FROM member_internal_notifications
            WHERE member_id = ?
        ";
        
        $stmt = $pdo->prepare($sql);
        $stmt->execute([$memberId]);
        $stats = $stmt->fetch(PDO::FETCH_ASSOC);
        
        return [
            'total' => (int)$stats['total'] ?? 0,
            'unread' => (int)$stats['unread'] ?? 0,
            'read' => (int)$stats['read_count'] ?? 0
        ];
        
    } catch (PDOException $e) {
        error_log("Failed to fetch notification stats: " . $e->getMessage());
        return [
            'total' => 0,
            'unread' => 0,
            'read' => 0
        ];
    }
}

/**
 * Validate notification ID
 */
function validateNotificationId($notificationId, $memberId) {
    if (!is_numeric($notificationId) || $notificationId <= 0) {
        return false;
    }
    
    // Check if notification belongs to member
    try {
        global $pdo;
        $stmt = $pdo->prepare("
            SELECT id FROM member_internal_notifications 
            WHERE id = ? AND member_id = ?
        ");
        $stmt->execute([$notificationId, $memberId]);
        return $stmt->fetch() !== false;
    } catch (PDOException $e) {
        return false;
    }
}

// ============================================
// REQUEST ROUTING
// ============================================

$method = $_SERVER['REQUEST_METHOD'];
$requestUri = $_SERVER['REQUEST_URI'];
$path = parse_url($requestUri, PHP_URL_PATH);
$basePath = '/api/notifications'; // Adjust based on your routing

try {
    switch ($method) {
        case 'GET':
            handleGetRequest();
            break;
            
        case 'POST':
            handlePostRequest();
            break;
            
        case 'DELETE':
            handleDeleteRequest();
            break;
            
        default:
            http_response_code(405);
            echo json_encode([
                'success' => false,
                'error' => 'Method not allowed',
                'allowed_methods' => ['GET', 'POST', 'DELETE']
            ]);
            break;
    }
} catch (Exception $e) {
    http_response_code(500);
    echo json_encode([
        'success' => false,
        'error' => 'Internal server error',
        'message' => ENVIRONMENT === 'development' ? $e->getMessage() : 'Something went wrong'
    ]);
    error_log("Notifications API Error: " . $e->getMessage());
}

// ============================================
// REQUEST HANDLERS
// ============================================

/**
 * Handle GET requests
 */
function handleGetRequest() {
    global $pdo, $memberId;
    
    // Parse query parameters
    $limit = isset($_GET['limit']) ? (int)$_GET['limit'] : 20;
    $page = isset($_GET['page']) ? (int)$_GET['page'] : 1;
    $status = $_GET['status'] ?? null; // 'read', 'unread', or null for all
    $offset = ($page - 1) * $limit;
    
    // Validate parameters
    if ($limit < 1 || $limit > 100) {
        $limit = 20;
    }
    if ($page < 1) {
        $page = 1;
    }
    if ($status && !in_array($status, ['read', 'unread'])) {
        $status = null;
    }
    
    // Check for specific notification ID
    if (isset($_GET['id'])) {
        $notificationId = (int)$_GET['id'];
        
        if (!validateNotificationId($notificationId, $memberId)) {
            http_response_code(404);
            echo json_encode([
                'success' => false,
                'error' => 'Notification not found'
            ]);
            return;
        }
        
        $sql = "SELECT * FROM member_internal_notifications WHERE id = ? AND member_id = ?";
        $stmt = $pdo->prepare($sql);
        $stmt->execute([$notificationId, $memberId]);
        $notification = $stmt->fetch(PDO::FETCH_ASSOC);
        
        if (!$notification) {
            http_response_code(404);
            echo json_encode([
                'success' => false,
                'error' => 'Notification not found'
            ]);
            return;
        }
        
        // Format response
        $notification['created_at_formatted'] = date('M j, Y g:i a', strtotime($notification['created_at']));
        if ($notification['read_at']) {
            $notification['read_at_formatted'] = date('M j, Y g:i a', strtotime($notification['read_at']));
        }
        $notification['is_unread'] = ($notification['status'] === 'unread');
        
        echo json_encode([
            'success' => true,
            'data' => $notification
        ], JSON_NUMERIC_CHECK);
        
        return;
    }
    
    // Get notifications
    $notifications = getMemberNotifications($pdo, $memberId, $limit, $offset, $status);
    $stats = getNotificationStats($pdo, $memberId);
    
    // Calculate pagination
    $totalPages = ceil($stats['total'] / $limit);
    
    echo json_encode([
        'success' => true,
        'data' => [
            'notifications' => $notifications,
            'pagination' => [
                'current_page' => $page,
                'total_pages' => $totalPages,
                'total_items' => $stats['total'],
                'items_per_page' => $limit,
                'has_next' => $page < $totalPages,
                'has_previous' => $page > 1
            ],
            'stats' => $stats,
            'filters' => [
                'status' => $status
            ]
        ]
    ], JSON_NUMERIC_CHECK);
}

/**
 * Handle POST requests
 */
function handlePostRequest() {
    global $pdo, $memberId;
    
    // Get JSON input
    $input = json_decode(file_get_contents('php://input'), true);
    
    if (json_last_error() !== JSON_ERROR_NONE) {
        http_response_code(400);
        echo json_encode([
            'success' => false,
            'error' => 'Invalid JSON input'
        ]);
        return;
    }
    
    // Determine action
    if (isset($input['action'])) {
        switch ($input['action']) {
            case 'mark_read':
                handleMarkAsRead($input);
                break;
                
            case 'mark_all_read':
                handleMarkAllAsRead();
                break;
                
            case 'create':
                handleCreateNotification($input);
                break;
                
            default:
                http_response_code(400);
                echo json_encode([
                    'success' => false,
                    'error' => 'Invalid action'
                ]);
                break;
        }
    } else {
        http_response_code(400);
        echo json_encode([
            'success' => false,
            'error' => 'Action is required'
        ]);
    }
}

/**
 * Handle DELETE requests
 */
function handleDeleteRequest() {
    global $pdo, $memberId;
    
    // Check if deleting all or specific
    if (isset($_GET['id'])) {
        $notificationId = (int)$_GET['id'];
        
        if (!validateNotificationId($notificationId, $memberId)) {
            http_response_code(404);
            echo json_encode([
                'success' => false,
                'error' => 'Notification not found'
            ]);
            return;
        }
        
        $stmt = $pdo->prepare("DELETE FROM member_internal_notifications WHERE id = ? AND member_id = ?");
        $stmt->execute([$notificationId, $memberId]);
        
        echo json_encode([
            'success' => true,
            'message' => 'Notification deleted successfully'
        ]);
        
    } elseif (isset($_GET['action']) && $_GET['action'] === 'delete_all') {
        // Delete all notifications (with confirmation)
        $confirm = $_GET['confirm'] ?? false;
        
        if (!$confirm) {
            http_response_code(400);
            echo json_encode([
                'success' => false,
                'error' => 'Confirmation required. Add ?confirm=true to delete all notifications'
            ]);
            return;
        }
        
        $stmt = $pdo->prepare("DELETE FROM member_internal_notifications WHERE member_id = ?");
        $stmt->execute([$memberId]);
        $deletedCount = $stmt->rowCount();
        
        echo json_encode([
            'success' => true,
            'message' => "Deleted $deletedCount notifications",
            'count' => $deletedCount
        ]);
        
    } else {
        http_response_code(400);
        echo json_encode([
            'success' => false,
            'error' => 'Specify notification ID or action=delete_all'
        ]);
    }
}

// ============================================
// ACTION HANDLERS
// ============================================

/**
 * Mark a notification as read
 */
function handleMarkAsRead($input) {
    global $pdo, $memberId;
    
    if (!isset($input['notification_id'])) {
        http_response_code(400);
        echo json_encode([
            'success' => false,
            'error' => 'notification_id is required'
        ]);
        return;
    }
    
    $notificationId = (int)$input['notification_id'];
    
    if (!validateNotificationId($notificationId, $memberId)) {
        http_response_code(404);
        echo json_encode([
            'success' => false,
            'error' => 'Notification not found'
        ]);
        return;
    }
    
    try {
        markNotificationAsRead($notificationId, $memberId, $pdo);
        
        echo json_encode([
            'success' => true,
            'message' => 'Notification marked as read'
        ]);
        
    } catch (RuntimeException $e) {
        http_response_code(500);
        echo json_encode([
            'success' => false,
            'error' => 'Failed to mark notification as read',
            'details' => ENVIRONMENT === 'development' ? $e->getMessage() : null
        ]);
    }
}

/**
 * Mark all notifications as read
 */
function handleMarkAllAsRead() {
    global $pdo, $memberId;
    
    try {
        $count = markAllNotificationsAsRead($memberId, $pdo);
        
        echo json_encode([
            'success' => true,
            'message' => "Marked $count notifications as read",
            'count' => $count
        ]);
        
    } catch (RuntimeException $e) {
        http_response_code(500);
        echo json_encode([
            'success' => false,
            'error' => 'Failed to mark all notifications as read',
            'details' => ENVIRONMENT === 'development' ? $e->getMessage() : null
        ]);
    }
}

/**
 * Create a new notification (admin/branch manager only)
 */
function handleCreateNotification($input) {
    global $pdo, $memberId, $userRole;
    
    // Check permissions (only admins and branch managers can create notifications)
    if (!in_array($userRole, ['admin', 'branch_manager'])) {
        http_response_code(403);
        echo json_encode([
            'success' => false,
            'error' => 'Insufficient permissions'
        ]);
        return;
    }
    
    // Validate required fields
    $required = ['target_member_id', 'title', 'message'];
    foreach ($required as $field) {
        if (!isset($input[$field]) || empty(trim($input[$field]))) {
            http_response_code(400);
            echo json_encode([
                'success' => false,
                'error' => "$field is required"
            ]);
            return;
        }
    }
    
    $targetMemberId = (int)$input['target_member_id'];
    $title = trim($input['title']);
    $message = trim($input['message']);
    $actionUrl = $input['action_url'] ?? null;
    
    // Validate target member exists
    $stmt = $pdo->prepare("SELECT id FROM members WHERE id = ? AND deleted_at IS NULL");
    $stmt->execute([$targetMemberId]);
    
    if (!$stmt->fetch()) {
        http_response_code(404);
        echo json_encode([
            'success' => false,
            'error' => 'Target member not found'
        ]);
        return;
    }
    
    // Create notification
    try {
        $sql = "
            INSERT INTO member_internal_notifications 
            (member_id, title, message, action_url, status, created_at)
            VALUES (?, ?, ?, ?, 'unread', NOW())
        ";
        
        $stmt = $pdo->prepare($sql);
        $stmt->execute([$targetMemberId, $title, $message, $actionUrl]);
        $notificationId = $pdo->lastInsertId();
        
        echo json_encode([
            'success' => true,
            'message' => 'Notification created successfully',
            'data' => [
                'notification_id' => $notificationId
            ]
        ]);
        
    } catch (PDOException $e) {
        http_response_code(500);
        echo json_encode([
            'success' => false,
            'error' => 'Failed to create notification'
        ]);
        error_log("Create notification error: " . $e->getMessage());
    }
}