<?php
/**
 * Automated FTP Deployment Script
 * Syncs local SMS app to FTPS server
 */

// FTPS Configuration
$ftpHost = 'ftp.shanesmith.com.au';
$ftpPort = 21;
$ftpUser = 'sms@sms.praetorianx.au';
$ftpPass = '1Fuck3dP@ssw0rd';
$ftpPath = '/sms.praetorianx.au'; // Adjust to your remote path

// Local app directory
$localDir = __DIR__;

// Files/dirs to ignore
$ignorePatterns = [
    '/.git',
    '/.deployignore',
    '/deploy.php',
    '/messages.json',
    '/token_cache.json',
    '/webhook_log.json',
    '/.env',
    '/node_modules',
];

class FTPDeployer
{
    private $conn;
    private $host;
    private $user;
    private $pass;
    private $port;
    private $remoteDir;
    private $uploadedFiles = [];
    private $errors = [];

    public function __construct($host, $port, $user, $pass, $remoteDir)
    {
        $this->host = $host;
        $this->port = $port;
        $this->user = $user;
        $this->pass = $pass;
        $this->remoteDir = $remoteDir;
    }

    public function connect()
    {
        echo "[*] Connecting to FTPS server...\n";

        if (function_exists('ftp_ssl_connect')) {
            $this->conn = ftp_ssl_connect($this->host, $this->port);
        } elseif (function_exists('ftp_connect')) {
            echo "[!] Warning: Using insecure FTP connection. SSL not supported by local PHP.\n";
            $this->conn = ftp_connect($this->host, $this->port);
        } else {
            $this->errors[] = "FTP extension is not enabled in PHP.";
            return false;
        }

        if (!$this->conn) {
            $this->errors[] = "Failed to connect to $this->host:$this->port";
            echo "[!] Connection failed: " . implode(", ", $this->errors) . "\n";
            return false;
        }

        if (!@ftp_login($this->conn, $this->user, $this->pass)) {
            $this->errors[] = "Login failed for user $this->user";
            echo "[!] Login failed: " . implode(", ", $this->errors) . "\n";
            ftp_close($this->conn);
            return false;
        }

        ftp_pasv($this->conn, true);
        echo "[✓] Connected successfully\n";
        return true;
    }

    public function deploy($localDir, $ignorePatterns)
    {
        echo "[*] Starting deployment...\n";

        if (!$this->createRemoteDir($this->remoteDir)) {
            return false;
        }

        $this->syncDirectory($localDir, $this->remoteDir, $ignorePatterns);

        if (count($this->errors) > 0) {
            echo "\n[!] Errors occurred:\n";
            foreach ($this->errors as $error) {
                echo "    - $error\n";
            }
        }

        echo "\n[✓] Deployment complete!\n";
        echo "    Uploaded: " . count($this->uploadedFiles) . " files\n";

        return count($this->errors) === 0;
    }

    private function createRemoteDir($dir)
    {
        if (!$this->remoteDirectoryExists($dir)) {
            echo "[*] Creating remote directory: $dir\n";
            if (!@ftp_mkdir($this->conn, $dir)) {
                $this->errors[] = "Failed to create remote directory: $dir";
                return false;
            }
        }
        return true;
    }

    private function remoteDirectoryExists($dir)
    {
        $currentDir = @ftp_pwd($this->conn);
        $result = @ftp_chdir($this->conn, $dir);
        if ($currentDir) {
            @ftp_chdir($this->conn, $currentDir);
        }
        return $result;
    }

    private function shouldIgnore($path, $ignorePatterns)
    {
        foreach ($ignorePatterns as $pattern) {
            if (strpos($path, $pattern) !== false) {
                return true;
            }
        }
        return false;
    }

    private function syncDirectory($localPath, $remotePath, $ignorePatterns)
    {
        $files = scandir($localPath);

        foreach ($files as $file) {
            if ($file === '.' || $file === '..')
                continue;

            $localFile = $localPath . DIRECTORY_SEPARATOR . $file;
            $remoteFile = $remotePath . '/' . $file;

            if ($this->shouldIgnore($localFile, $ignorePatterns)) {
                echo "[⊘] Skipping: $file\n";
                continue;
            }

            if (is_dir($localFile)) {
                echo "[*] Creating directory: $file\n";
                @ftp_mkdir($this->conn, $remoteFile);
                $this->syncDirectory($localFile, $remoteFile, $ignorePatterns);
            } else {
                echo "[↑] Uploading: $file\n";
                if (!ftp_put($this->conn, $remoteFile, $localFile, FTP_BINARY)) {
                    $this->errors[] = "Failed to upload: $file";
                } else {
                    $this->uploadedFiles[] = $file;
                }
            }
        }
    }

    public function disconnect()
    {
        if ($this->conn) {
            ftp_close($this->conn);
        }
    }
}

// Run deployment
$deployer = new FTPDeployer($ftpHost, $ftpPort, $ftpUser, $ftpPass, $ftpPath);

if ($deployer->connect()) {
    $deployer->deploy($localDir, $ignorePatterns);
}

$deployer->disconnect();
?>