<?php

namespace App\Controllers;

use App\Core\Controller;

class AuthController extends Controller {
    
    public function loginForm() {
        if (isset($_SESSION['user_id'])) {
            $this->redirect('/profile');
        }
        $this->view('auth/login');
    }

    public function registerForm() {
        if (isset($_SESSION['user_id'])) {
            $this->redirect('/profile');
        }
        // Check GET first, then Session
        $ref = $_GET['ref'] ?? ($_SESSION['global_ref'] ?? '');
        $this->view('auth/register', ['ref' => $ref]);
    }

    public function login() {
        $username = $_POST['username'] ?? '';
        $password = $_POST['password'] ?? '';
        $ip = get_client_ip();

        $db = db_pdo();
        
        // Anti-Brute Force check by IP (for non-existent users)
        $stmt = $db->prepare("SELECT attempts, last_attempt FROM login_logs WHERE ip_address = ?");
        $stmt->execute([$ip]);
        $ip_log = $stmt->fetch();
        
        if ($ip_log && $ip_log['attempts'] >= 10 && (time() - strtotime($ip_log['last_attempt'])) < 900) {
            $this->view('auth/login', ['error' => 'Too many failed attempts from this IP. Please try again in 15 minutes.']);
            return;
        }

        $stmt = $db->prepare("SELECT * FROM users WHERE username = ?");
        $stmt->execute([$username]);
        $user = $stmt->fetch();

        if ($user) {
            // Check if account is banned
            if ($user['is_banned']) {
                $this->view('auth/login', ['error' => 'Your account has been banned. Please contact support.']);
                return;
            }

            // Check brute force for specific user
            if ($user['login_attempts'] >= 5 && (time() - strtotime($user['last_attempt_time'])) < 900) {
                $this->view('auth/login', ['error' => 'Too many failed attempts. Please try again in 15 minutes.']);
                return;
            }

            if (password_verify($password, $user['password'])) {
                // Reset attempts
                $stmt = $db->prepare("UPDATE users SET login_attempts = 0, last_ip = ? WHERE id = ?");
                $stmt->execute([$ip, $user['id']]);

                $_SESSION['user_id'] = $user['id'];
                $_SESSION['username'] = $user['username'];
                $_SESSION['role'] = $user['role'];
                
                if ($user['role'] === 'admin') {
                    $this->redirect('/admin');
                } else {
                    $this->redirect('/profile');
                }
            } else {
                // Increment attempts
                $stmt = $db->prepare("UPDATE users SET login_attempts = login_attempts + 1, last_attempt_time = NOW() WHERE id = ?");
                $stmt->execute([$user['id']]);
                
                $this->view('auth/login', ['error' => __('error_invalid_login')]);
            }
        } else {
            // Log failed attempt by IP
            if ($ip_log) {
                $stmt = $db->prepare("UPDATE login_logs SET attempts = attempts + 1, last_attempt = NOW() WHERE ip_address = ?");
                $stmt->execute([$ip]);
            } else {
                $stmt = $db->prepare("INSERT INTO login_logs (ip_address, attempts) VALUES (?, 1)");
                $stmt->execute([$ip]);
            }
            $this->view('auth/login', ['error' => __('error_invalid_login')]);
        }
    }

    public function register() {
        $username = $_POST['username'] ?? '';
        $password = $_POST['password'] ?? '';
        $confirm_password = $_POST['confirm_password'] ?? '';
        $ref_code = $_POST['ref_code'] ?? '';
        $honeypot = $_POST['full_name'] ?? ''; // Hidden field
        $ip = get_client_ip();

        // Bot protection (Honeypot)
        if (!empty($honeypot)) {
            // Silent fail or show error
            $this->view('auth/register', ['error' => 'Bot detected.', 'ref' => $ref_code]);
            return;
        }

        if ($password !== $confirm_password) {
            $this->view('auth/register', ['error' => __('error_password_mismatch'), 'ref' => $ref_code]);
            return;
        }

        $db = db_pdo();
        
        // Multi-account check (Anti-bot/Anti-cheat)
        $stmt = $db->prepare("SELECT COUNT(*) FROM users WHERE registration_ip = ? AND created_at > DATE_SUB(NOW(), INTERVAL 1 HOUR)");
        $stmt->execute([$ip]);
        if ($stmt->fetchColumn() >= 3) {
            $this->view('auth/register', ['error' => 'Too many registrations from this IP. Please try again later.', 'ref' => $ref_code]);
            return;
        }

        // Check if username exists
        $stmt = $db->prepare("SELECT id FROM users WHERE username = ?");
        $stmt->execute([$username]);
        if ($stmt->fetch()) {
            $this->view('auth/register', ['error' => __('error_username_exists'), 'ref' => $ref_code]);
            return;
        }

        $hashed_password = password_hash($password, PASSWORD_DEFAULT);
        $referral_code = substr(md5(uniqid($username, true)), 0, 8);
        
        $referred_by = null;
        if (!empty($ref_code)) {
            $stmt = $db->prepare("SELECT id FROM users WHERE referral_code = ?");
            $stmt->execute([$ref_code]);
            $referrer = $stmt->fetch();
            if ($referrer) {
                $referred_by = $referrer['id'];
                
                // Anti-self referral check
                $stmt_ip = $db->prepare("SELECT registration_ip FROM users WHERE id = ?");
                $stmt_ip->execute([$referred_by]);
                $referrer_ip = $stmt_ip->fetchColumn();
                
                if ($referrer_ip === $ip) {
                    // Possible self-referral, mark but allow or block? 
                    // Let's block if IP matches exactly
                    $this->view('auth/register', ['error' => 'Self-referral is not allowed.', 'ref' => $ref_code]);
                    return;
                }
            }
        }

        $stmt = $db->prepare("INSERT INTO users (username, password, referral_code, referred_by, role, balance, registration_ip, last_ip) VALUES (?, ?, ?, ?, 'user', 0, ?, ?)");
        $stmt->execute([$username, $hashed_password, $referral_code, $referred_by, $ip, $ip]);
        $userId = $db->lastInsertId();

        if ($referred_by) {
            // Reward referrer
            $stmt = $db->prepare("UPDATE users SET points = points + 10, total_referrals = total_referrals + 1 WHERE id = ?");
            $stmt->execute([$referred_by]);
        }

        $_SESSION['user_id'] = $userId;
        $_SESSION['username'] = $username;
        $_SESSION['role'] = 'user';
        
        $this->redirect('/profile');
    }

    public function logout() {
        session_destroy();
        $this->redirect('/');
    }

    public function profile() {
        if (!isset($_SESSION['user_id'])) {
            $this->redirect('/login');
        }
        
        $db = db_pdo();
        $stmt = $db->prepare("SELECT * FROM users WHERE id = ?");
        $stmt->execute([$_SESSION['user_id']]);
        $user = $stmt->fetch();

        $stmt = $db->prepare("SELECT * FROM withdrawals WHERE user_id = ? ORDER BY created_at DESC");
        $stmt->execute([$user['id']]);
        $withdrawals = $stmt->fetchAll();
        
        $this->view('auth/profile', [
            'user' => $user,
            'withdrawals' => $withdrawals,
            'success' => $_SESSION['success'] ?? null,
            'error' => $_SESSION['error'] ?? null
        ]);
        unset($_SESSION['success'], $_SESSION['error']);
    }

    public function requestWithdrawal() {
        if (!isset($_SESSION['user_id'])) {
            if (is_ajax()) {
                header('Content-Type: application/json');
                echo json_encode(['error' => 'Unauthorized']);
                exit;
            }
            $this->redirect('/login');
        }

        $amount = (float)($_POST['amount'] ?? 0);
        $method = $_POST['method'] ?? '';
        $details = $_POST['details'] ?? '';

        if ($amount < 10000) { // Minimum WD
            $error = __('error_min_withdraw');
            if (is_ajax()) {
                header('Content-Type: application/json');
                echo json_encode(['error' => $error]);
                exit;
            }
            $_SESSION['error'] = $error;
            $this->redirect('/profile');
        }

        $db = db_pdo();
        $stmt = $db->prepare("SELECT balance FROM users WHERE id = ?");
        $stmt->execute([$_SESSION['user_id']]);
        $balance = $stmt->fetchColumn();

        if ($balance < $amount) {
            $error = __('error_insufficient_balance');
            if (is_ajax()) {
                header('Content-Type: application/json');
                echo json_encode(['error' => $error]);
                exit;
            }
            $_SESSION['error'] = $error;
            $this->redirect('/profile');
        }

        // Deduct balance
        $stmt = $db->prepare("UPDATE users SET balance = balance - ? WHERE id = ?");
        $stmt->execute([$amount, $_SESSION['user_id']]);

        // Create WD request
        $stmt = $db->prepare("INSERT INTO withdrawals (user_id, amount, method, account_details, status) VALUES (?, ?, ?, ?, 'pending')");
        $stmt->execute([$_SESSION['user_id'], $amount, $method, $details]);

        $success = __('success_withdraw_submitted');
        if (is_ajax()) {
            header('Content-Type: application/json');
            echo json_encode(['success' => $success, 'new_balance' => $balance - $amount]);
            exit;
        }
        
        $_SESSION['success'] = $success;
        $this->redirect('/profile');
    }
}