<?php
declare(strict_types=1);

require_once __DIR__ . '/db.php';

function user_normalize_phone(?string $phone): ?string
{
    if ($phone === null) {
        return null;
    }
    $digits = preg_replace('/\D+/', '', $phone) ?? '';
    if ($digits === '') {
        return null;
    }
    return $digits;
}

function user_normalize_email(?string $email): ?string
{
    $email = strtolower(trim((string) $email));
    if ($email === '' || !filter_var($email, FILTER_VALIDATE_EMAIL)) {
        return null;
    }
    return $email;
}

/**
 * Find or create a shop client (users table).
 *
 * @return array{id:int,name:string,phone:?string,email:?string,...}
 */
function user_upsert(
    int $tenantId,
    string $name,
    ?string $phone = null,
    ?string $email = null,
    ?int $carrierId = null,
    ?string $customSmsDomain = null
): array {
    $name = trim($name);
    if ($name === '') {
        throw new InvalidArgumentException('Name is required');
    }
    $phoneNorm = user_normalize_phone($phone);
    $emailNorm = user_normalize_email($email);
    $customSmsDomain = strtolower(trim((string) $customSmsDomain)) ?: null;
    if ($customSmsDomain !== null) {
        $customSmsDomain = ltrim($customSmsDomain, '@');
    }

    $existing = null;
    if ($phoneNorm) {
        $stmt = db()->prepare('SELECT * FROM users WHERE tenant_id = ? AND phone = ? LIMIT 1');
        $stmt->execute([$tenantId, $phoneNorm]);
        $existing = $stmt->fetch() ?: null;
    }
    if (!$existing && $emailNorm) {
        $stmt = db()->prepare('SELECT * FROM users WHERE tenant_id = ? AND email = ? LIMIT 1');
        $stmt->execute([$tenantId, $emailNorm]);
        $existing = $stmt->fetch() ?: null;
    }

    if ($existing) {
        $newName = $name !== '' ? $name : (string) $existing['name'];
        $newPhone = $phoneNorm ?: ($existing['phone'] ?? null);
        $newEmail = $emailNorm ?: ($existing['email'] ?? null);
        $newCarrier = $carrierId ?: ($existing['carrier_id'] ?? null);
        $newCustom = $customSmsDomain ?: ($existing['custom_sms_domain'] ?? null);
        db()->prepare(
            'UPDATE users SET name = ?, phone = ?, email = ?, carrier_id = ?, custom_sms_domain = ? WHERE id = ? AND tenant_id = ?'
        )->execute([$newName, $newPhone, $newEmail, $newCarrier, $newCustom, $existing['id'], $tenantId]);
        $stmt = db()->prepare('SELECT * FROM users WHERE id = ?');
        $stmt->execute([(int) $existing['id']]);
        return $stmt->fetch();
    }

    db()->prepare(
        'INSERT INTO users (tenant_id, name, phone, email, carrier_id, custom_sms_domain, role) VALUES (?,?,?,?,?,?,?)'
    )->execute([$tenantId, $name, $phoneNorm, $emailNorm, $carrierId, $customSmsDomain, 'customer']);
    $id = (int) db()->lastInsertId();
    $stmt = db()->prepare('SELECT * FROM users WHERE id = ?');
    $stmt->execute([$id]);
    return $stmt->fetch();
}

function user_role(array $user): string
{
    $role = strtolower((string) ($user['role'] ?? 'customer'));
    return in_array($role, ['owner', 'admin', 'customer'], true) ? $role : 'customer';
}

function user_is_owner(array $user): bool
{
    return in_array(user_role($user), ['owner', 'admin'], true);
}

function owner_find_login(int $tenantId, string $login): ?array
{
    $login = trim($login);
    if ($login === '') {
        return null;
    }
    $email = user_normalize_email($login);
    $username = strtolower($login);
    $stmt = db()->prepare(
        "SELECT * FROM users
         WHERE tenant_id = ?
           AND role IN ('owner', 'admin')
           AND (LOWER(COALESCE(username, '')) = ? OR email = ?)
         LIMIT 1"
    );
    $stmt->execute([$tenantId, $username, $email ?: $username]);
    $row = $stmt->fetch();
    return $row ?: null;
}

function owner_verify_password(array $user, string $password): bool
{
    $hash = (string) ($user['password_hash'] ?? '');
    if ($hash !== '') {
        return password_verify($password, $hash);
    }
    $username = strtolower((string) ($user['username'] ?? ''));
    return defined('ADMIN_USER') && defined('ADMIN_PASS')
        && $username === strtolower((string) ADMIN_USER)
        && hash_equals((string) ADMIN_PASS, $password);
}
