<?php
class MultiTenantAuth {
    private $pdo;
    
    public function __construct($pdo) {
        $this->pdo = $pdo;
    }
    
    /**
     * Authenticate sub-admin login
     */
    public function authenticateSubAdmin($username, $password, $siteId = null) {
        try {
            // If siteId is not provided, try to get it from current domain
            if (!$siteId) {
                // Load dependencies if needed
                if (!class_exists('Database')) {
                    require_once __DIR__ . '/database.php';
                }
                if (!class_exists('SiteManager')) {
                    require_once __DIR__ . '/site-manager.php';
                }
                $siteManager = new SiteManager(new Database());
                $currentSite = $siteManager->getCurrentSite();
                $siteId = $currentSite ? $currentSite['id'] : null;
            }
            
            $sql = "SELECT sa.*, s.site_name, s.domain 
                    FROM site_admins sa 
                    JOIN sites s ON sa.site_id = s.id 
                    WHERE sa.username = ? AND sa.is_active = 1";
            
            $params = [$username];
            
            // If siteId specified, limit to that site only
            if ($siteId) {
                $sql .= " AND sa.site_id = ?";
                $params[] = $siteId;
            }
            
            $stmt = $this->pdo->prepare($sql);
            $stmt->execute($params);
            $admin = $stmt->fetch(PDO::FETCH_ASSOC);
            
            if ($admin && password_verify($password, $admin['password'])) {
                // Update last login
                $updateStmt = $this->pdo->prepare("UPDATE site_admins SET last_login = NOW() WHERE id = ?");
                $updateStmt->execute([$admin['id']]);
                
                // Load permissions
                $admin['permissions'] = $this->getAdminPermissions($admin['id']);
                $admin['market_access'] = $this->getAdminMarketAccess($admin['id']);
                
                // Create session
                $sessionId = $this->createAdminSession($admin['id'], $admin['site_id']);
                $admin['session_id'] = $sessionId;
                
                // Log activity
                $this->logActivity($admin['id'], 'login', 'Sub-admin login successful');
                
                return $admin;
            }
            
            return false;
        } catch (Exception $e) {
            error_log("Sub-admin authentication error: " . $e->getMessage());
            return false;
        }
    }
    
    /**
     * Authenticate master admin
     */
    public function authenticateMasterAdmin($email, $password, $siteId = null) {
        try {
            $sql = "SELECT id, site_name, domain, master_admin_email, master_admin_password 
                    FROM sites WHERE master_admin_email = ?";
            
            $params = [$email];
            
            if ($siteId) {
                $sql .= " AND id = ?";
                $params[] = $siteId;
            }
            
            $stmt = $this->pdo->prepare($sql);
            $stmt->execute($params);
            $site = $stmt->fetch(PDO::FETCH_ASSOC);
            
            if ($site && password_verify($password, $site['master_admin_password'])) {
                return [
                    'id' => 'master_' . $site['id'],
                    'username' => 'master',
                    'email' => $site['master_admin_email'],
                    'full_name' => 'Master Admin',
                    'site_id' => $site['id'],
                    'site_name' => $site['site_name'],
                    'domain' => $site['domain'],
                    'is_master' => true,
                    'permissions' => $this->getAllPermissions(), // Master has all permissions
                    'market_access' => [] // Master has access to all markets
                ];
            }
            
            return false;
        } catch (Exception $e) {
            error_log("Master admin authentication error: " . $e->getMessage());
            return false;
        }
    }
    
    /**
     * Get admin permissions
     */
    public function getAdminPermissions($adminId) {
        try {
            $stmt = $this->pdo->prepare("
                SELECT pt.permission_key, pt.permission_name, pt.permission_description 
                FROM admin_permissions ap 
                JOIN permission_types pt ON ap.permission_type_id = pt.id 
                WHERE ap.admin_id = ? AND pt.is_active = 1
            ");
            $stmt->execute([$adminId]);
            
            $permissions = [];
            while ($row = $stmt->fetch(PDO::FETCH_ASSOC)) {
                $permissions[$row['permission_key']] = [
                    'name' => $row['permission_name'],
                    'description' => $row['permission_description']
                ];
            }
            
            return $permissions;
        } catch (Exception $e) {
            error_log("Error getting admin permissions: " . $e->getMessage());
            return [];
        }
    }
    
    /**
     * Get admin market access
     */
    public function getAdminMarketAccess($adminId) {
        try {
            $stmt = $this->pdo->prepare("
                SELECT market_name, can_view, can_edit, can_manage_results 
                FROM admin_market_access 
                WHERE admin_id = ?
            ");
            $stmt->execute([$adminId]);
            
            $marketAccess = [];
            while ($row = $stmt->fetch(PDO::FETCH_ASSOC)) {
                $marketAccess[$row['market_name']] = [
                    'can_view' => (bool)$row['can_view'],
                    'can_edit' => (bool)$row['can_edit'],
                    'can_manage_results' => (bool)$row['can_manage_results']
                ];
            }
            
            return $marketAccess;
        } catch (Exception $e) {
            error_log("Error getting market access: " . $e->getMessage());
            return [];
        }
    }
    
    /**
     * Get all available permissions (for master admin)
     */
    public function getAllPermissions() {
        try {
            $stmt = $this->pdo->prepare("SELECT permission_key, permission_name, permission_description FROM permission_types WHERE is_active = 1");
            $stmt->execute();
            
            $permissions = [];
            while ($row = $stmt->fetch(PDO::FETCH_ASSOC)) {
                $permissions[$row['permission_key']] = [
                    'name' => $row['permission_name'],
                    'description' => $row['permission_description']
                ];
            }
            
            return $permissions;
        } catch (Exception $e) {
            error_log("Error getting all permissions: " . $e->getMessage());
            return [];
        }
    }
    
    /**
     * Create admin session
     */
    public function createAdminSession($adminId, $siteId) {
        try {
            $sessionId = bin2hex(random_bytes(32));
            $expiresAt = date('Y-m-d H:i:s', strtotime('+24 hours'));
            
            $stmt = $this->pdo->prepare("
                INSERT INTO admin_sessions (id, admin_id, site_id, ip_address, user_agent, expires_at) 
                VALUES (?, ?, ?, ?, ?, ?)
            ");
            $stmt->execute([
                $sessionId,
                $adminId,
                $siteId,
                $_SERVER['REMOTE_ADDR'] ?? '127.0.0.1',
                $_SERVER['HTTP_USER_AGENT'] ?? 'Unknown',
                $expiresAt
            ]);
            
            return $sessionId;
        } catch (Exception $e) {
            error_log("Error creating admin session: " . $e->getMessage());
            return false;
        }
    }
    
    /**
     * Validate admin session
     */
    public function validateSession($sessionId) {
        try {
            $stmt = $this->pdo->prepare("
                SELECT s.*, sa.username, sa.email, sa.full_name, sa.site_id, 
                       si.site_name, si.domain
                FROM admin_sessions s
                JOIN site_admins sa ON s.admin_id = sa.id
                JOIN sites si ON s.site_id = si.id
                WHERE s.id = ? AND s.expires_at > NOW() AND sa.is_active = 1
            ");
            $stmt->execute([$sessionId]);
            $session = $stmt->fetch(PDO::FETCH_ASSOC);
            
            if ($session) {
                // Load permissions and market access
                $session['permissions'] = $this->getAdminPermissions($session['admin_id']);
                $session['market_access'] = $this->getAdminMarketAccess($session['admin_id']);
                
                // Update last activity
                $updateStmt = $this->pdo->prepare("UPDATE admin_sessions SET last_activity = NOW() WHERE id = ?");
                $updateStmt->execute([$sessionId]);
                
                return $session;
            }
            
            return false;
        } catch (Exception $e) {
            error_log("Error validating session: " . $e->getMessage());
            return false;
        }
    }
    
    /**
     * Check if admin has specific permission
     */
    public function hasPermission($adminData, $permissionKey) {
        // Master admin has all permissions
        if (isset($adminData['is_master']) && $adminData['is_master']) {
            return true;
        }
        
        return isset($adminData['permissions'][$permissionKey]);
    }
    
    /**
     * Check if admin has access to specific market
     */
    public function hasMarketAccess($adminData, $marketName, $accessType = 'can_view') {
        // Master admin has access to all markets
        if (isset($adminData['is_master']) && $adminData['is_master']) {
            return true;
        }
        
        if (!isset($adminData['market_access'][$marketName])) {
            return false;
        }
        
        return $adminData['market_access'][$marketName][$accessType] ?? false;
    }
    
    /**
     * Get accessible markets for admin
     */
    public function getAccessibleMarkets($adminData, $accessType = 'can_view') {
        // Master admin sees all markets
        if (isset($adminData['is_master']) && $adminData['is_master']) {
            // Get all markets from database or return common ones
            return ['SGP', 'HK', 'SDY', 'PCSO', 'PCB', 'CN', 'TWN', 'JP', 'KR'];
        }
        
        $accessibleMarkets = [];
        foreach ($adminData['market_access'] as $market => $access) {
            if ($access[$accessType]) {
                $accessibleMarkets[] = $market;
            }
        }
        
        return $accessibleMarkets;
    }
    
    /**
     * Log admin activity
     */
    public function logActivity($adminId, $actionType, $description, $targetTable = null, $targetId = null) {
        try {
            $stmt = $this->pdo->prepare("
                INSERT INTO admin_activity_log_multi (admin_id, action_type, action_description, target_table, target_id, ip_address, user_agent) 
                VALUES (?, ?, ?, ?, ?, ?, ?)
            ");
            $stmt->execute([
                $adminId,
                $actionType,
                $description,
                $targetTable,
                $targetId,
                $_SERVER['REMOTE_ADDR'] ?? '127.0.0.1',
                $_SERVER['HTTP_USER_AGENT'] ?? 'Unknown'
            ]);
        } catch (Exception $e) {
            error_log("Error logging activity: " . $e->getMessage());
        }
    }
    
    /**
     * Logout admin (destroy session)
     */
    public function logout($sessionId) {
        try {
            $stmt = $this->pdo->prepare("DELETE FROM admin_sessions WHERE id = ?");
            $stmt->execute([$sessionId]);
            return true;
        } catch (Exception $e) {
            error_log("Error during logout: " . $e->getMessage());
            return false;
        }
    }
    
    /**
     * Clean expired sessions
     */
    public function cleanExpiredSessions() {
        try {
            $stmt = $this->pdo->prepare("DELETE FROM admin_sessions WHERE expires_at < NOW()");
            $stmt->execute();
        } catch (Exception $e) {
            error_log("Error cleaning expired sessions: " . $e->getMessage());
        }
    }
}
?>