<?php
header("Access-Control-Allow-Origin: *");
header("Content-Type: application/json; charset=UTF-8");
header("Access-Control-Allow-Methods: GET, POST, PUT, DELETE, OPTIONS");
header("Access-Control-Allow-Headers: Content-Type, Access-Control-Allow-Headers, Authorization, X-Requested-With");

if ($_SERVER['REQUEST_METHOD'] == 'OPTIONS') {
    exit(0);
}

require_once __DIR__ . '/../config/database.php';
require_once __DIR__ . '/../models/User.php';
require_once __DIR__ . '/../middleware/auth.php';

// Start session for authentication
session_start();

$database = new Database();
$db = $database->getConnection();

$user = new User($db);
$auth = new AuthMiddleware($db);

// Authenticate user
$current_user = $auth->authenticate();
if (!$current_user) {
    $auth->sendUnauthorizedResponse();
}

$request_method = $_SERVER['REQUEST_METHOD'];

switch($request_method) {
    case 'GET':
        if(isset($_GET['id'])) {
            $user_id = $_GET['id'];
            
            // Check authorization: Admin can access any user, users can only access their own profile
            if (!$auth->canAccess($current_user, null, $user_id)) {
                $auth->sendForbiddenResponse();
            }
            
            $user->id = $user_id;
            $user->readOne();
            
            if($user->username != null) {
                // Remove sensitive data for non-admin users accessing their own profile
                $user_arr = array(
                    "id" => $user->id,
                    "username" => $user->username,
                    "email" => $user->email,
                    "first_name" => $user->first_name,
                    "last_name" => $user->last_name,
                    "role" => $user->role,
                    "is_active" => $user->is_active,
                    "last_login" => $user->last_login,
                    "created_at" => $user->created_at,
                    "updated_at" => $user->updated_at
                );
                
                // Add admin-only data if current user is admin
                if ($auth->isAdmin($current_user)) {
                    $user_arr["role_badge"] = $user->getRoleBadge();
                    $user_arr["status_badge"] = $user->getStatusBadge();
                }
                
                http_response_code(200);
                echo json_encode($user_arr);
            } else {
                http_response_code(404);
                echo json_encode(array("message" => "User not found."));
            }
        } else {
            // List all users - admin only
            if (!$auth->isAdmin($current_user)) {
                $auth->sendForbiddenResponse();
            }
            
            $stmt = $user->read();
            $num = $stmt->rowCount();
            
            if($num > 0) {
                $users_arr = array();
                $users_arr["records"] = array();
                
                while ($row = $stmt->fetch(PDO::FETCH_ASSOC)) {
                    extract($row);
                    
                    $user_item = array(
                        "id" => $id,
                        "username" => $username,
                        "email" => $email,
                        "first_name" => $first_name,
                        "last_name" => $last_name,
                        "role" => $role,
                        "is_active" => $is_active,
                        "last_login" => $last_login,
                        "created_at" => $created_at,
                        "updated_at" => $updated_at,
                        "role_badge" => getRoleBadge($role),
                        "status_badge" => getStatusBadge($is_active)
                    );
                    
                    array_push($users_arr["records"], $user_item);
                }
                
                http_response_code(200);
                echo json_encode($users_arr);
            } else {
                http_response_code(200);
                echo json_encode(array("records" => array()));
            }
        }
        break;
        
    case 'POST':
        // Only admins can create users
        if (!$auth->isAdmin($current_user)) {
            $auth->sendForbiddenResponse();
        }
        
        $data = json_decode(file_get_contents("php://input"));
        
        if(!empty($data->username) && !empty($data->email) && !empty($data->first_name) && !empty($data->last_name) && !empty($data->password)) {
            
            // Check if username or email already exists
            $existing_user = $user->findByEmail($data->email);
            if($existing_user) {
                http_response_code(409);
                echo json_encode(array("message" => "Email already exists"));
                break;
            }
            
            $existing_user = $user->findByUsername($data->username);
            if($existing_user) {
                http_response_code(409);
                echo json_encode(array("message" => "Username already exists"));
                break;
            }
            
            $user->username = $data->username;
            $user->email = $data->email;
            $user->password_hash = $data->password;
            $user->first_name = $data->first_name;
            $user->last_name = $data->last_name;
            $user->role = $data->role ?? 'user';
            $user->is_active = $data->is_active ?? true;
            
            if($user->create()) {
                http_response_code(201);
                echo json_encode(array("message" => "User was created."));
            } else {
                http_response_code(503);
                echo json_encode(array("message" => "Unable to create user."));
            }
        } else {
            http_response_code(400);
            echo json_encode(array("message" => "Unable to create user. Data is incomplete."));
        }
        break;
        
    case 'PUT':
        $data = json_decode(file_get_contents("php://input"));
        
        if(!empty($data->id) && !empty($data->username) && !empty($data->email) && !empty($data->first_name) && !empty($data->last_name)) {
            $user_id = $data->id;
            
            // Check authorization: Admin can update any user, users can only update their own profile
            if (!$auth->canAccess($current_user, null, $user_id)) {
                $auth->sendForbiddenResponse();
            }
            
            $user->id = $user_id;
            $user->username = $data->username;
            $user->email = $data->email;
            $user->first_name = $data->first_name;
            $user->last_name = $data->last_name;
            
            // Only admins can change role and is_active status
            if ($auth->isAdmin($current_user)) {
                $user->role = $data->role ?? 'user';
                $user->is_active = $data->is_active ?? true;
            } else {
                // For regular users, preserve existing role and active status
                $existing_user = new User($db);
                $existing_user->id = $user_id;
                $existing_user->readOne();
                $user->role = $existing_user->role;
                $user->is_active = $existing_user->is_active;
            }
            
            // Update password if provided
            $update_password = !empty($data->password);
            if($update_password) {
                $user->password_hash = $data->password;
            }
            
            if($user->update($update_password)) {
                http_response_code(200);
                echo json_encode(array("message" => "User was updated."));
            } else {
                http_response_code(503);
                echo json_encode(array("message" => "Unable to update user."));
            }
        } else {
            http_response_code(400);
            echo json_encode(array("message" => "Unable to update user. Data is incomplete."));
        }
        break;
        
    case 'DELETE':
        // Only admins can delete users
        if (!$auth->isAdmin($current_user)) {
            $auth->sendForbiddenResponse();
        }
        
        if(isset($_GET['id'])) {
            $user_id = $_GET['id'];
            
            // Prevent admin from deleting themselves
            if ($user_id == $current_user['id']) {
                http_response_code(400);
                echo json_encode(array("message" => "Cannot delete your own account."));
                break;
            }
            
            $user->id = $user_id;
            
            if($user->delete()) {
                http_response_code(200);
                echo json_encode(array("message" => "User was deleted."));
            } else {
                http_response_code(503);
                echo json_encode(array("message" => "Unable to delete user."));
            }
        } else {
            http_response_code(400);
            echo json_encode(array("message" => "Unable to delete user. ID is missing."));
        }
        break;
        
    default:
        http_response_code(405);
        echo json_encode(array("message" => "Method not allowed."));
        break;
}

// Helper functions
function getRoleBadge($role) {
    $badges = array(
        'admin' => '<span style="background-color: #dc3545; color: white; padding: 2px 8px; border-radius: 12px; font-size: 12px; font-weight: 500;">Admin</span>',
        'manager' => '<span style="background-color: #28a745; color: white; padding: 2px 8px; border-radius: 12px; font-size: 12px; font-weight: 500;">Manager</span>',
        'user' => '<span style="background-color: #6c757d; color: white; padding: 2px 8px; border-radius: 12px; font-size: 12px; font-weight: 500;">User</span>'
    );
    return $badges[$role] ?? $badges['user'];
}

function getStatusBadge($is_active) {
    if($is_active) {
        return '<span style="background-color: #28a745; color: white; padding: 2px 8px; border-radius: 12px; font-size: 12px; font-weight: 500;">Active</span>';
    } else {
        return '<span style="background-color: #6c757d; color: white; padding: 2px 8px; border-radius: 12px; font-size: 12px; font-weight: 500;">Inactive</span>';
    }
}
?>
