<?php
date_default_timezone_set('Asia/Singapore');

require_once('Constants.php');
require_once(PATH_LIB . 'AutoLoader.php');
require_once(PATH_CONTROLLERS . 'Common.php');
require_once(PATH_LIB . 'Log.php');
require_once(PATH_MESSAGE . 'Message.php');
require_once(PATH_CODE . "database/MsSqlDb.php");
require_once(PATH_CODE . "database/MySqlDb.php");
require_once(PATH_CODE . "database/MySqliDb.php");
require_once('ConfigDb.php');
require_once(PATH_MODELS . "prospect/PersonContactClass.php");
require_once(PATH_TABLES . "prospect/PersonContactTable.php");

class Unsubscribe
{
    private $db;
    private $personContactClass;

    function __construct()
    {
        if (!isset($_SESSION[SE_DB])) {
            $config = new ConfigDb(PATH_CODE . 'db.xml');
            $config->loadConfig();
            if ($config->getDbType() == DbType::MySql)
                $_SESSION[SE_DB] = new MySqlDb($config->getHost(), $config->getDbName(), $config->getUserName(), $config->getPassword(), $config->getPortNo());
            else if ($config->getDbType() == DbType::MySqli)
                $_SESSION[SE_DB] = new MySqliDb($config->getHost(), $config->getDbName(), $config->getUserName(), $config->getPassword(), $config->getPortNo());
            else
                $_SESSION[SE_DB] = new MsSqlDb($config->getHost(), $config->getDbName(), $config->getUserName(), $config->getPassword(), $config->getPortNo());
            unset($config);
        }
        $this->db = $_SESSION[SE_DB];
        $this->personContactClass = new PersonContactClass($this->db);
    }

    function __destruct()
    {
        unset($this->personContactClass);
    }

    public function processRequest($params)
    {
        Log::write('[Unsubscribe] Received request with parameters: ' . json_encode($params));
        try {
            $this->db->open();
            $token      = isset($params['token']) ? trim($params['token']) : '';
            $email      = isset($params['email']) ? trim($params['email']) : '';
            $action     = isset($params['action']) ? trim($params['action']) : 'unsubscribe';
            $comp_type  = isset($params['comp_type']) ? trim($params['comp_type']) : '1';

            if (empty($token) && empty($email)) {
                $this->displayErrorPage("Token or email is required.");
                return true;
            }

            // build safe query
            if (!empty($token)) {
                $quoted = $this->db->getConnection()->quote($token);
                if($comp_type == 1){
                    $query = "SELECT * FROM " . PersonContactTable::C_TABLE . " WHERE " . PersonContactTable::C_UNSUBSCRIBE_TOKEN . " = " . $quoted;
                }else{
                    $query = "SELECT * FROM " . CustomerContactTable::C_TABLE . " WHERE " . CustomerContactTable::C_UNSUBSCRIBE_TOKEN . " = " . $quoted;
                }
            } else {
                $quoted = $this->db->getConnection()->quote($email);
                if($comp_type == 1){
                    $query = "SELECT * FROM " . PersonContactTable::C_TABLE . " WHERE " . PersonContactTable::C_EMAIL . " = " . $quoted;
                }else{
                    $query = "SELECT * FROM " . CustomerContactTable::C_TABLE . " WHERE " . CustomerContactTable::C_EMAIL . " = " . $quoted;
                }
            }
            Log::write('[Unsubscribe] Executing query: ' . $query);

            $result = $this->db->getTable($query);

            if (!$result || count($result) == 0) {
                $this->displayErrorPage("You are not subscribed to promotional emails or the token/email is invalid.");
                return true;
            }

            $contact = $result[0];
            if($comp_type == 1){
                $contactId = $contact[PersonContactTable::C_ID];
            }else{
                $contactId = $contact[CustomerContactTable::C_CONTACT_ID];
            }

            if ($action === 'unsubscribe') {
                $this->updateUnsubscribe($contactId, $comp_type);
                $this->displaySuccessPage("You have been successfully unsubscribed from promotional emails.");
            } elseif ($action === 'resubscribe') {
                $this->updateResubscribe($contactId, $comp_type);
                $this->displaySuccessPage("You have been successfully resubscribed to promotional emails.");
            } else {
                $this->displayErrorPage("Invalid action specified.");
            }

            return true;
        } catch (Exception $e) {
            Log::write('[Unsubscribe] Error: ' . $e->getMessage());
            $this->displayErrorPage("An error occurred while processing your request. Please try again later.");
            return true;
        }
    }

    private function displaySuccessPage($message)
    {
        ?>
        <!DOCTYPE html>
        <html lang="en">
        <head>
            <meta charset="UTF-8">
            <meta name="viewport" content="width=device-width, initial-scale=1.0">
            <title>Subscription Updated</title>
            <style>
                body {
                    font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, "Helvetica Neue", Arial, sans-serif;
                    background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
                    display: flex;
                    justify-content: center;
                    align-items: center;
                    min-height: 100vh;
                    margin: 0;
                    padding: 20px;
                }
                .container {
                    background: white;
                    border-radius: 8px;
                    box-shadow: 0 10px 25px rgba(0, 0, 0, 0.2);
                    padding: 40px;
                    max-width: 500px;
                    text-align: center;
                }
                .success-icon {
                    width: 60px;
                    height: 60px;
                    background: #4caf50;
                    border-radius: 50%;
                    display: flex;
                    align-items: center;
                    justify-content: center;
                    margin: 0 auto 20px;
                    font-size: 32px;
                    color: white;
                }
                h1 {
                    color: #333;
                    margin: 20px 0 10px;
                    font-size: 24px;
                }
                p {
                    color: #666;
                    font-size: 16px;
                    line-height: 1.6;
                    margin: 10px 0 30px;
                }
                .button {
                    background: #667eea;
                    color: white;
                    padding: 12px 30px;
                    border: none;
                    border-radius: 4px;
                    text-decoration: none;
                    font-size: 16px;
                    cursor: pointer;
                    transition: background 0.3s;
                    display: inline-block;
                }
                .button:hover {
                    background: #764ba2;
                }
            </style>
        </head>
        <body>
            <div class="container">
                <div class="success-icon">✓</div>
                <h1>Success</h1>
                <p><?php echo htmlspecialchars($message); ?></p>
                <p style="font-size: 14px; color: #999; margin-top: 20px;">Thank you for managing your subscription preferences.</p>
            </div>
        </body>
        </html>
        <?php
    }

    private function displayErrorPage($message)
    {
        ?>
        <!DOCTYPE html>
        <html lang="en">
        <head>
            <meta charset="UTF-8">
            <meta name="viewport" content="width=device-width, initial-scale=1.0">
            <title>Error</title>
            <style>
                body {
                    font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, "Helvetica Neue", Arial, sans-serif;
                    background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
                    display: flex;
                    justify-content: center;
                    align-items: center;
                    min-height: 100vh;
                    margin: 0;
                    padding: 20px;
                }
                .container {
                    background: white;
                    border-radius: 8px;
                    box-shadow: 0 10px 25px rgba(0, 0, 0, 0.2);
                    padding: 40px;
                    max-width: 500px;
                    text-align: center;
                }
                .error-icon {
                    width: 60px;
                    height: 60px;
                    background: #f44336;
                    border-radius: 50%;
                    display: flex;
                    align-items: center;
                    justify-content: center;
                    margin: 0 auto 20px;
                    font-size: 32px;
                    color: white;
                }
                h1 {
                    color: #333;
                    margin: 20px 0 10px;
                    font-size: 24px;
                }
                p {
                    color: #666;
                    font-size: 16px;
                    line-height: 1.6;
                    margin: 10px 0 30px;
                }
                .button {
                    background: #667eea;
                    color: white;
                    padding: 12px 30px;
                    border: none;
                    border-radius: 4px;
                    text-decoration: none;
                    font-size: 16px;
                    cursor: pointer;
                    transition: background 0.3s;
                    display: inline-block;
                }
                .button:hover {
                    background: #764ba2;
                }
            </style>
        </head>
        <body>
            <div class="container">
                <div class="error-icon">✕</div>
                <h1>Error</h1>
                <p><?php echo htmlspecialchars($message); ?></p>
                <!-- <p style="font-size: 14px; color: #999; margin-top: 20px;">If you continue to experience issues, please contact support.</p> -->
            </div>
        </body>
        </html>
        <?php
    }

    private function updateUnsubscribe($contactId, $type)
    {
        $now = date_create('now')->format('Y-m-d H:i:s');
        $id = intval($contactId);

        if($type == 1){
            $sql = "UPDATE " . PersonContactTable::C_TABLE . " SET " .
                PersonContactTable::C_PREFER_PROMOTION . " = 0, " .
                PersonContactTable::C_UNSUBSCRIBE_TOKEN . " = '', " .
                PersonContactTable::C_UNSUBSCRIBE_DATE . " = '" . $now . "' " .
                "WHERE " . PersonContactTable::C_ID . " = " . $id;
        }else{
            $sql = "UPDATE " . CustomerContactTable::C_TABLE . " SET " .
                CustomerContactTable::C_UNSUBSCRIBE_TOKEN . " = '', " .
                CustomerContactTable::C_UNSUBSCRIBE_DATE . " = '" . $now . "' " .
                "WHERE " . CustomerContactTable::C_CONTACT_ID . " = " . $id;
        }
        Log::write('[Unsubscribe] Executing SQL: ' . $sql);
        $this->db->executeSql($sql);
    }

    private function updateResubscribe($contactId, $type)
    {
        $resubscribeToken = bin2hex(random_bytes(16));
        $id = intval($contactId);
        $quotedToken = $this->db->getConnection()->quote($resubscribeToken);

        if($type == 1){
            $sql = "UPDATE " . PersonContactTable::C_TABLE . " SET " .
                PersonContactTable::C_PREFER_PROMOTION . " = 1, " .
                PersonContactTable::C_UNSUBSCRIBE_TOKEN . " = " . $quotedToken . ", " .
                PersonContactTable::C_UNSUBSCRIBE_DATE . " = NULL " .
                "WHERE " . PersonContactTable::C_ID . " = " . $id;
        }else{
            $sql = "UPDATE " . CustomerContactTable::C_TABLE . " SET " . 
                CustomerContactTable::C_UNSUBSCRIBE_TOKEN . " = " . $quotedToken . ", " .
                CustomerContactTable::C_UNSUBSCRIBE_DATE . " = NULL " .
                "WHERE " . CustomerContactTable::C_CONTACT_ID . " = " . $id;
        }

        Log::write('[Unsubscribe] Executing SQL: ' . $sql);
        $this->db->executeSql($sql);
    }

    public function generateUnsubscribeToken($contactId, $type)
    {
		if($type == 1){
			$token = bin2hex(random_bytes(16));
			$quotedToken = $this->db->getConnection()->quote($token);
			$sql = "UPDATE " . PersonContactTable::C_TABLE . " SET " .
				PersonContactTable::C_UNSUBSCRIBE_TOKEN . " = " . $quotedToken . " " .
				"WHERE " . PersonContactTable::C_ID . " = " . intval($contactId);
		}else{
			$token = bin2hex(random_bytes(16));
			$quotedToken = $this->db->getConnection()->quote($token);
			$sql = "UPDATE " . CustomerContactTable::C_TABLE . " SET " .
				CustomerContactTable::C_UNSUBSCRIBE_TOKEN . " = " . $quotedToken . " " .
				"WHERE " . CustomerContactTable::C_CONTACT_ID . " = " . intval($contactId);
		}

        $this->db->executeSql($sql);
        return $token;
    }

    public function validateToken($token)
    {
        if (empty($token)) {
            return null;
        }

        $quoted = $this->db->getConnection()->quote($token);
        $query = "SELECT * FROM " . PersonContactTable::C_TABLE .
            " WHERE " . PersonContactTable::C_UNSUBSCRIBE_TOKEN . " = " . $quoted;

        $result = $this->db->getTable($query);

        if ($result && count($result) > 0) {
            return $result[0];
        }

        return null;
    }
}

?>
