<?php

declare(strict_types=1);

namespace App\Services\System;

use App\Models\ManagedEnvironment;
use Illuminate\Database\Eloquent\Builder;
use Illuminate\Validation\ValidationException;

class AllowedTenantUniverse
{
    public const PLATFORM_TENANT_EXTERNAL_ID = 'platform';

    public function query(): Builder
    {
        return ManagedEnvironment::query()
            ->where('slug', '!=', self::PLATFORM_TENANT_EXTERNAL_ID);
    }

    public function isAllowed(ManagedEnvironment $tenant): bool
    {
        return (string) $tenant->external_id !== self::PLATFORM_TENANT_EXTERNAL_ID;
    }

    public function ensureAllowed(ManagedEnvironment $tenant): void
    {
        if ($this->isAllowed($tenant)) {
            return;
        }

        throw ValidationException::withMessages([
            'managed_environment_id' => 'This tenant is not eligible for System runbooks.',
        ]);
    }

    public function resolveAllowed(int|string|null $tenantId): ?ManagedEnvironment
    {
        if (! is_numeric($tenantId)) {
            return null;
        }

        $tenant = ManagedEnvironment::query()->whereKey((int) $tenantId)->first();

        if (! $tenant instanceof ManagedEnvironment) {
            return null;
        }

        $this->ensureAllowed($tenant);

        return $tenant;
    }

    public function resolveAllowedOrFail(int|string|null $tenantId): ManagedEnvironment
    {
        if (! is_numeric($tenantId) || (int) $tenantId <= 0) {
            throw ValidationException::withMessages([
                'managed_environment_id' => 'Select a tenant.',
            ]);
        }

        $tenant = ManagedEnvironment::query()->whereKey((int) $tenantId)->first();

        if (! $tenant instanceof ManagedEnvironment) {
            throw ValidationException::withMessages([
                'managed_environment_id' => 'Select a valid tenant.',
            ]);
        }

        $this->ensureAllowed($tenant);

        return $tenant;
    }
}
