<?php
error_reporting(0); // Desactivar para producción, E_ALL para debug
session_start();

// ==========================================
// CONFIGURACIÓN FIJA
// ==========================================
$SSH_HOST = "127.0.0.1"; 
$SSH_PORT = 22;
$SSH_USER = "root";
// ==========================================

// --- AUTOLOADER (phpseclib 2.0) ---
$libPath = __DIR__ . '/phpseclib2.0';
spl_autoload_register(function ($class) use ($libPath) {
    $prefix = 'phpseclib\\';
    if (strpos($class, $prefix) === 0) {
        $file = $libPath . '/' . str_replace('\\', '/', substr($class, strlen($prefix))) . '.php';
        if (file_exists($file)) require $file;
    }
});

use phpseclib\Net\SSH2;

// Inicializar sesión
if (!isset($_SESSION['current_pwd'])) { $_SESSION['current_pwd'] = '~'; }

// LOGIN
if (isset($_POST['ssh_pass'])) {
    $ssh = new SSH2($SSH_HOST, $SSH_PORT);
    if ($ssh->login($SSH_USER, $_POST['ssh_pass'])) {
        $_SESSION['ssh_pass'] = $_POST['ssh_pass'];
        $_SESSION['is_logged'] = true;
        $_SESSION['current_pwd'] = trim($ssh->exec('pwd'));
    } else { $error = "Contraseña incorrecta."; }
}

if (isset($_GET['logout'])) { session_destroy(); header("Location: ?"); exit; }

// --- LÓGICA DE AUTOCOMPLETAR (TAB) ---
if (isset($_GET['complete']) && isset($_SESSION['is_logged'])) {
    header('Content-Type: application/json');
    $ssh = new SSH2($SSH_HOST, $SSH_PORT);
    if ($ssh->login($SSH_USER, $_SESSION['ssh_pass'])) {
        $partial = $_POST['partial'] ?? '';
        $cwd = $_SESSION['current_pwd'];
        // Usamos 'compgen' de Linux para buscar coincidencias
        $matches = $ssh->exec("cd $cwd && compgen -f -- " . escapeshellarg($partial));
        echo json_encode(['matches' => array_filter(explode("\n", trim($matches)))]);
    }
    exit;
}

// --- EJECUCIÓN DE COMANDOS ---
if (isset($_GET['exec']) && isset($_SESSION['is_logged'])) {
    header('Content-Type: application/json');
    $ssh = new SSH2($SSH_HOST, $SSH_PORT);
    if ($ssh->login($SSH_USER, $_SESSION['ssh_pass'])) {
        $cmd = $_POST['cmd'] ?? '';
        $cwd = $_SESSION['current_pwd'];

        if (preg_match('/^cd\s+(.+)/', $cmd, $matches)) {
            $target = $matches[1];
            $new_pwd = trim($ssh->exec("cd $cwd && cd $target && pwd"));
            if (!empty($new_pwd)) { $_SESSION['current_pwd'] = $new_pwd; $output = ""; }
            else { $output = "-bash: cd: $target: No existe el directorio\n"; }
        } else {
            $output = $ssh->exec("cd $cwd && $cmd 2>&1");
        }
        echo json_encode(['output' => $output, 'cwd' => $_SESSION['current_pwd']]);
    }
    exit;
}
?>
<!DOCTYPE html>
<html lang="es">
<head>
    <meta charset="UTF-8">
    <title>Sytem Terminal Pro</title>
    <link href="https://cdn.jsdelivr.net/npm/bootstrap@5.3.0/dist/css/bootstrap.min.css" rel="stylesheet">
    <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/xterm@5.1.0/css/xterm.css" />
    <style>
        body { background: #1a1a1a; height: 100vh; display: flex; align-items: center; justify-content: center; margin: 0; }
        .term-card {
            width: 90%; max-width: 1100px; height: 70vh;
            background: #300a24; border-radius: 12px; overflow: hidden;
            box-shadow: 0 40px 80px rgba(0,0,0,0.8); display: flex; flex-direction: column;
            border: 1px solid #4f4f4f;
        }
        .term-header {
            background: linear-gradient(to bottom, #5c5c5c, #404040); 
            padding: 10px 18px; display: flex; justify-content: space-between; align-items: center;
        }
        .dots span { height: 12px; width: 12px; border-radius: 50%; display: inline-block; margin-right: 6px; }
        .close { background: #ff5f56; } .min { background: #ffbd2e; } .max { background: #27c93f; }
        #terminal { flex-grow: 1; padding: 10px; }
        .login-box { background: #252525; border: 1px solid #444; border-radius: 15px; width: 400px; padding: 40px; }
    </style>
</head>
<body>

<?php if (!isset($_SESSION['is_logged'])): ?>
    <div class="login-box text-center shadow-lg">
        <h4 class="text-white mb-4">🖥️ Iniciar Sesión SSH</h4>
        <form method="POST">
            <input type="password" name="ssh_pass" class="form-control bg-dark text-white border-secondary mb-3 text-center" placeholder="Contraseña SSH" autofocus required>
            <button class="btn btn-primary w-100 fw-bold">CONECTAR</button>
            <?php if(isset($error)) echo "<div class='text-danger mt-3 small'>$error</div>"; ?>
        </form>
    </div>
<?php else: ?>
    <div class="term-card">
        <div class="term-header">
            <div class="dots"><span class="close"></span><span class="min"></span><span class="max"></span><span class="ms-2 text-white small"><?php echo "$SSH_USER@$SSH_HOST"; ?></span></div>
            <a href="?logout=1" class="btn btn-sm btn-outline-light border-0 opacity-50">Salir</a>
        </div>
        <div id="terminal"></div>
    </div>

    <script src="https://cdn.jsdelivr.net/npm/xterm@5.1.0/lib/xterm.js"></script>
    <script>
        const term = new Terminal({
            cursorBlink: true,
            theme: { background: '#300a24', foreground: '#ffffff' },
            fontSize: 15, fontFamily: '"Ubuntu Mono", monospace'
        });

        term.open(document.getElementById('terminal'));
        let currentCwd = '<?php echo $_SESSION['current_pwd']; ?>';
        let buffer = '';
        let history = [];
        let historyIndex = -1;

        const getPrompt = () => `\r\n\x1b[1;32m<?php echo $SSH_USER; ?>@server\x1b[0m:\x1b[1;34m${currentCwd}\x1b[0m$ `;
        
        term.writeln('\x1b[1;33mSesión SSH Iniciada. [Tab] para completar, [Flechas] para historial.\x1b[0m');
        term.write(getPrompt());

        term.onData(async e => {
            switch(e) {
                case '\r': // ENTER
                    term.write('\r\n');
                    if (buffer.trim()) {
                        history.unshift(buffer);
                        historyIndex = -1;
                        await execute(buffer);
                    } else term.write(getPrompt());
                    buffer = '';
                    break;
                case '\t': // TAB (Autocompletar)
                    const parts = buffer.split(' ');
                    const lastPart = parts.pop();
                    const res = await fetch('?complete=1', { method: 'POST', body: new URLSearchParams({partial: lastPart}) });
                    const data = await res.json();
                    if(data.matches && data.matches.length === 1) {
                        const missing = data.matches[0].substring(lastPart.length);
                        buffer += missing;
                        term.write(missing);
                    } else if (data.matches.length > 1) {
                        term.write('\r\n' + data.matches.join('  ') + getPrompt() + buffer);
                    }
                    break;
                case '\u001b[A': // FLECHA ARRIBA
                    if (historyIndex < history.length - 1) {
                        historyIndex++;
                        clearLine();
                        buffer = history[historyIndex];
                        term.write(buffer);
                    }
                    break;
                case '\u001b[B': // FLECHA ABAJO
                    if (historyIndex > 0) {
                        historyIndex--;
                        clearLine();
                        buffer = history[historyIndex];
                        term.write(buffer);
                    } else {
                        historyIndex = -1;
                        clearLine();
                        buffer = '';
                    }
                    break;
                case '\u007F': // BACKSPACE
                    if (buffer.length > 0) {
                        buffer = buffer.slice(0, -1);
                        term.write('\b \b');
                    }
                    break;
                default:
                    if (e.length === 1) {
                        buffer += e;
                        term.write(e);
                    }
            }
        });

        function clearLine() {
            term.write('\b \b'.repeat(buffer.length));
        }

        async function execute(cmd) {
            const res = await fetch('?exec=1', { method: 'POST', body: new URLSearchParams({cmd: cmd}) });
            const data = await res.json();
            currentCwd = data.cwd;
            if(data.output) term.write(data.output.replace(/\n/g, '\r\n'));
            term.write(getPrompt());
        }
    </script>
<?php endif; ?>
</body>
</html>