<?php
declare(strict_types=1);

require_once __DIR__ . '/payment_service.php';
require_once __DIR__ . '/mailer.php';

function golder_portal_session_start(): void
{
    if (session_status() === PHP_SESSION_ACTIVE) {
        return;
    }
    session_name('golder_sales_portal');
    session_start([
        'cookie_httponly' => true,
        'cookie_samesite' => 'Lax',
        'use_strict_mode' => true,
    ]);
}

function golder_portal_current_user(): ?array
{
    golder_portal_session_start();
    $row = $_SESSION['golder_sales_portal_user'] ?? null;
    return is_array($row) ? $row : null;
}

function golder_portal_current_user_id(): int
{
    $user = golder_portal_current_user();
    return (int)($user['id'] ?? 0);
}

function golder_portal_login_user(array $user): void
{
    golder_portal_session_start();
    session_regenerate_id(true);
    $_SESSION['golder_sales_portal_user'] = [
        'id' => (int)($user['id'] ?? 0),
        'full_name' => (string)($user['full_name'] ?? ''),
        'email' => (string)($user['email'] ?? ''),
        'phone' => (string)($user['phone'] ?? ''),
    ];
}

function golder_portal_logout_user(): void
{
    golder_portal_session_start();
    unset($_SESSION['golder_sales_portal_user']);
}

function golder_portal_user_by_id(PDO $master, int $userId): ?array
{
    golder_ensure_payment_tables($master);
    if ($userId <= 0) {
        return null;
    }
    $st = $master->prepare(
        'SELECT id, full_name, email, phone, email_verified_at, is_active, created_at, last_login_at
         FROM sales_portal_users
         WHERE id = :id
         LIMIT 1'
    );
    $st->execute([':id' => $userId]);
    $row = $st->fetch();
    return is_array($row) ? $row : null;
}

function golder_portal_user_by_email(PDO $master, string $email): ?array
{
    golder_ensure_payment_tables($master);
    $email = strtolower(trim($email));
    if ($email === '') {
        return null;
    }
    $st = $master->prepare(
        'SELECT *
         FROM sales_portal_users
         WHERE email = :e
         LIMIT 1'
    );
    $st->execute([':e' => $email]);
    $row = $st->fetch();
    return is_array($row) ? $row : null;
}

function golder_portal_password_valid(string $password): bool
{
    return strlen($password) >= 8;
}

function golder_portal_create_email_token(PDO $master, int $userId, string $purpose = 'verify_email', int $ttlHours = 24): array
{
    golder_ensure_payment_tables($master);
    $raw = bin2hex(random_bytes(24));
    $hash = hash('sha256', $raw);
    $expiresAt = gmdate('Y-m-d H:i:s', time() + max(1, $ttlHours) * 3600);

    $master->prepare(
        'INSERT INTO sales_portal_email_tokens (user_id, token_hash, purpose, expires_at, used_at, created_at)
         VALUES (:uid, :th, :p, :ex, NULL, UTC_TIMESTAMP())'
    )->execute([
        ':uid' => $userId,
        ':th' => $hash,
        ':p' => $purpose,
        ':ex' => $expiresAt,
    ]);

    return [
        'token' => $raw,
        'expires_at' => $expiresAt,
    ];
}

function golder_portal_register(PDO $master, string $fullName, string $email, string $phone, string $password): array
{
    golder_ensure_payment_tables($master);

    $fullName = trim($fullName);
    $email = strtolower(trim($email));
    $phone = trim($phone);

    if ($fullName === '') {
        return ['ok' => false, 'message' => 'full_name is required.'];
    }
    if ($email === '' || filter_var($email, FILTER_VALIDATE_EMAIL) === false) {
        return ['ok' => false, 'message' => 'email is invalid.'];
    }
    if ($phone === '' || preg_match('/^[0-9+()\\-\\s]{7,20}$/', $phone) !== 1) {
        return ['ok' => false, 'message' => 'phone is invalid.'];
    }
    if (!golder_portal_password_valid($password)) {
        return ['ok' => false, 'message' => 'password must be at least 8 chars.'];
    }

    $existing = golder_portal_user_by_email($master, $email);
    if ($existing) {
        return ['ok' => false, 'message' => 'email is already registered.'];
    }

    $passwordHash = password_hash($password, PASSWORD_DEFAULT);
    if (!is_string($passwordHash) || $passwordHash === '') {
        return ['ok' => false, 'message' => 'password hash failed.'];
    }

    $master->prepare(
        'INSERT INTO sales_portal_users (full_name, email, phone, password_hash, email_verified_at, is_active, created_at, updated_at)
         VALUES (:n, :e, :p, :h, NULL, 1, UTC_TIMESTAMP(), UTC_TIMESTAMP())'
    )->execute([
        ':n' => $fullName,
        ':e' => $email,
        ':p' => $phone,
        ':h' => $passwordHash,
    ]);
    $userId = (int)$master->lastInsertId();

    $token = golder_portal_create_email_token($master, $userId, 'verify_email', 24);

    return [
        'ok' => true,
        'user_id' => $userId,
        'verification_token' => (string)$token['token'],
        'verification_expires_at' => (string)$token['expires_at'],
    ];
}

function golder_portal_verify_email(PDO $master, string $tokenRaw): array
{
    golder_ensure_payment_tables($master);
    $tokenRaw = trim($tokenRaw);
    if ($tokenRaw === '') {
        return ['ok' => false, 'message' => 'token is required.'];
    }
    $tokenHash = hash('sha256', $tokenRaw);

    $st = $master->prepare(
        'SELECT t.id AS token_id, t.user_id, t.expires_at, t.used_at,
                u.id, u.full_name, u.email, u.phone, u.email_verified_at, u.is_active
         FROM sales_portal_email_tokens t
         INNER JOIN sales_portal_users u ON u.id = t.user_id
         WHERE t.token_hash = :th
           AND t.purpose = :p
         LIMIT 1'
    );
    $st->execute([':th' => $tokenHash, ':p' => 'verify_email']);
    $row = $st->fetch();
    if (!$row) {
        return ['ok' => false, 'message' => 'token is invalid.'];
    }
    if (!empty($row['used_at'])) {
        return ['ok' => false, 'message' => 'token is already used.'];
    }
    if (strtotime((string)($row['expires_at'] ?? '')) < time()) {
        return ['ok' => false, 'message' => 'token is expired.'];
    }

    $master->prepare('UPDATE sales_portal_email_tokens SET used_at = UTC_TIMESTAMP() WHERE id = :id')->execute([
        ':id' => (int)$row['token_id'],
    ]);
    $master->prepare(
        'UPDATE sales_portal_users
         SET email_verified_at = COALESCE(email_verified_at, UTC_TIMESTAMP()), updated_at = UTC_TIMESTAMP()
         WHERE id = :id'
    )->execute([':id' => (int)$row['user_id']]);

    $user = golder_portal_user_by_id($master, (int)$row['user_id']);
    return ['ok' => true, 'user' => $user];
}

function golder_portal_authenticate(PDO $master, string $email, string $password): array
{
    golder_ensure_payment_tables($master);
    $email = strtolower(trim($email));
    $password = (string)$password;

    if ($email === '' || $password === '') {
        return ['ok' => false, 'message' => 'email and password are required.'];
    }

    $row = golder_portal_user_by_email($master, $email);
    if (!$row) {
        return ['ok' => false, 'message' => 'invalid credentials.'];
    }
    if ((int)($row['is_active'] ?? 0) !== 1) {
        return ['ok' => false, 'message' => 'account is inactive.'];
    }
    if (trim((string)($row['email_verified_at'] ?? '')) === '') {
        return ['ok' => false, 'message' => 'email is not verified.'];
    }
    $storedHash = trim((string)($row['password_hash'] ?? ''));
    if ($storedHash === '' || !password_verify($password, $storedHash)) {
        return ['ok' => false, 'message' => 'invalid credentials.'];
    }

    $master->prepare('UPDATE sales_portal_users SET last_login_at = UTC_TIMESTAMP() WHERE id = :id')->execute([
        ':id' => (int)$row['id'],
    ]);

    $user = golder_portal_user_by_id($master, (int)$row['id']);
    return ['ok' => true, 'user' => $user];
}

function golder_portal_send_verification_email(string $email, string $fullName, string $verifyUrl): array
{
    $subject = 'Golder portal email verification';
    $text = "Hello {$fullName},\n\nPlease verify your email by opening this link:\n{$verifyUrl}\n\nIf you did not create this account, ignore this email.";
    $html = '<p>Hello ' . htmlspecialchars($fullName, ENT_QUOTES, 'UTF-8') . ',</p>'
        . '<p>Please verify your email by opening this link:</p>'
        . '<p><a href="' . htmlspecialchars($verifyUrl, ENT_QUOTES, 'UTF-8') . '">' . htmlspecialchars($verifyUrl, ENT_QUOTES, 'UTF-8') . '</a></p>'
        . '<p>If you did not create this account, ignore this email.</p>';
    return golder_send_smtp_mail($email, $subject, $text, $html);
}


