<?php

namespace App\Filament\Resources;

use App\Filament\Resources\ProviderConnectionResource\Pages;
use App\Jobs\ProviderComplianceSnapshotJob;
use App\Jobs\ProviderInventorySyncJob;
use App\Models\OperationRun;
use App\Models\ProviderConnection;
use App\Models\Tenant;
use App\Models\User;
use App\Services\Auth\CapabilityResolver;
use App\Services\Intune\AuditLogger;
use App\Services\Providers\CredentialManager;
use App\Services\Providers\ProviderOperationStartGate;
use App\Services\Verification\StartVerification;
use App\Support\Auth\Capabilities;
use App\Support\Badges\BadgeDomain;
use App\Support\Badges\BadgeRenderer;
use App\Support\Filament\TablePaginationProfiles;
use App\Support\OperationRunLinks;
use App\Support\OpsUx\OperationUxPresenter;
use App\Support\OpsUx\OpsUxBrowserEvents;
use App\Support\Providers\ProviderReasonCodes;
use App\Support\Rbac\UiEnforcement;
use App\Support\Ui\ActionSurface\ActionSurfaceDeclaration;
use App\Support\Ui\ActionSurface\Enums\ActionSurfaceInspectAffordance;
use App\Support\Ui\ActionSurface\Enums\ActionSurfaceProfile;
use App\Support\Ui\ActionSurface\Enums\ActionSurfaceSlot;
use App\Support\Workspaces\WorkspaceContext;
use BackedEnum;
use Filament\Actions;
use Filament\Facades\Filament;
use Filament\Forms\Components\TextInput;
use Filament\Forms\Components\Toggle;
use Filament\Notifications\Notification;
use Filament\Resources\Resource;
use Filament\Schemas\Components\Section;
use Filament\Schemas\Schema;
use Filament\Tables;
use Filament\Tables\Filters\Filter;
use Filament\Tables\Filters\SelectFilter;
use Filament\Tables\Table;
use Illuminate\Database\Eloquent\Builder;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Database\Query\JoinClause;
use Illuminate\Support\Str;
use UnitEnum;

class ProviderConnectionResource extends Resource
{
    protected static bool $isDiscovered = false;

    protected static bool $isScopedToTenant = false;

    protected static ?string $model = ProviderConnection::class;

    protected static ?string $slug = 'provider-connections';

    protected static bool $isGloballySearchable = false;

    protected static string|BackedEnum|null $navigationIcon = 'heroicon-o-link';

    protected static string|UnitEnum|null $navigationGroup = 'Settings';

    protected static ?string $navigationLabel = 'Provider Connections';

    protected static ?string $recordTitleAttribute = 'display_name';

    public static function getNavigationParentItem(): ?string
    {
        return 'Integrations';
    }

    public static function actionSurfaceDeclaration(): ActionSurfaceDeclaration
    {
        return ActionSurfaceDeclaration::forResource(ActionSurfaceProfile::CrudListAndView)
            ->satisfy(ActionSurfaceSlot::ListHeader, 'Header actions include capability-gated create.')
            ->satisfy(ActionSurfaceSlot::InspectAffordance, ActionSurfaceInspectAffordance::ClickableRow->value)
            ->satisfy(ActionSurfaceSlot::ListRowMoreMenu, 'Secondary row actions are grouped under "More".')
            ->exempt(ActionSurfaceSlot::ListBulkMoreGroup, 'Provider connections intentionally omit bulk actions.')
            ->satisfy(ActionSurfaceSlot::ListEmptyState, 'List page defines empty-state guidance and CTA.')
            ->exempt(ActionSurfaceSlot::DetailHeader, 'View page has no additional header mutations in this resource.');
    }

    public static function canCreate(): bool
    {
        $tenant = static::resolveTenantForCreate();
        $user = auth()->user();

        if (! $tenant instanceof Tenant || ! $user instanceof User) {
            return false;
        }

        /** @var CapabilityResolver $resolver */
        $resolver = app(CapabilityResolver::class);

        return $resolver->isMember($user, $tenant)
            && $resolver->can($user, $tenant, Capabilities::PROVIDER_MANAGE);
    }

    protected static function hasTenantCapability(string $capability): bool
    {
        $tenant = static::resolveScopedTenant();
        $user = auth()->user();

        if (! $tenant instanceof Tenant || ! $user instanceof User) {
            return false;
        }

        /** @var CapabilityResolver $resolver */
        $resolver = app(CapabilityResolver::class);

        return $resolver->isMember($user, $tenant)
            && $resolver->can($user, $tenant, $capability);
    }

    protected static function resolveScopedTenant(): ?Tenant
    {
        $tenantExternalId = static::resolveRequestedTenantExternalId();

        if (is_string($tenantExternalId) && $tenantExternalId !== '') {
            return static::resolveTenantByExternalId($tenantExternalId);
        }

        $routeTenant = request()->route('tenant');

        if ($routeTenant instanceof Tenant) {
            return $routeTenant;
        }

        if (is_string($routeTenant) && $routeTenant !== '') {
            return Tenant::query()
                ->where('external_id', $routeTenant)
                ->first();
        }

        $recordTenant = static::resolveTenantFromRouteRecord();

        if ($recordTenant instanceof Tenant) {
            return $recordTenant;
        }

        $contextTenantExternalId = static::resolveContextTenantExternalId();

        if (is_string($contextTenantExternalId) && $contextTenantExternalId !== '') {
            return static::resolveTenantByExternalId($contextTenantExternalId);
        }

        $filamentTenant = Filament::getTenant();

        return $filamentTenant instanceof Tenant ? $filamentTenant : null;
    }

    public static function resolveTenantForRecord(?ProviderConnection $record = null): ?Tenant
    {
        if ($record instanceof ProviderConnection) {
            $tenant = $record->tenant;

            if (! $tenant instanceof Tenant && is_numeric($record->tenant_id)) {
                $tenant = Tenant::query()->whereKey((int) $record->tenant_id)->first();
            }

            if ($tenant instanceof Tenant) {
                return $tenant;
            }
        }

        return static::resolveScopedTenant();
    }

    public static function resolveRequestedTenantExternalId(): ?string
    {
        $queryTenant = request()->query('tenant_id');

        if (is_string($queryTenant) && $queryTenant !== '') {
            return $queryTenant;
        }

        return static::resolveTenantExternalIdFromLivewireRequest();
    }

    public static function resolveContextTenantExternalId(): ?string
    {
        $workspaceId = app(WorkspaceContext::class)->currentWorkspaceId(request());
        $contextTenantId = app(WorkspaceContext::class)->lastTenantId(request());

        if ($workspaceId !== null && $contextTenantId !== null) {
            $tenant = Tenant::query()
                ->whereKey($contextTenantId)
                ->where('workspace_id', (int) $workspaceId)
                ->first();

            if ($tenant instanceof Tenant) {
                return (string) $tenant->external_id;
            }
        }

        $filamentTenant = Filament::getTenant();

        if ($filamentTenant instanceof Tenant) {
            return (string) $filamentTenant->external_id;
        }

        return null;
    }

    public static function resolveTenantForCreate(): ?Tenant
    {
        $tenantExternalId = static::resolveRequestedTenantExternalId() ?? static::resolveContextTenantExternalId();

        if (! is_string($tenantExternalId) || $tenantExternalId === '') {
            return null;
        }

        $tenant = static::resolveTenantByExternalId($tenantExternalId);
        $user = auth()->user();
        $workspaceId = app(WorkspaceContext::class)->currentWorkspaceId(request());

        if (! $tenant instanceof Tenant || ! $user instanceof User || $workspaceId === null) {
            return null;
        }

        if ((int) $tenant->workspace_id !== (int) $workspaceId) {
            return null;
        }

        if (! $user->canAccessTenant($tenant)) {
            return null;
        }

        return $tenant;
    }

    private static function resolveTenantExternalIdFromLivewireRequest(): ?string
    {
        if (! request()->headers->has('x-livewire') && ! request()->headers->has('x-livewire-navigate')) {
            return null;
        }

        try {
            $url = \Livewire\Livewire::originalUrl();

            if (is_string($url) && $url !== '') {
                $externalId = static::extractTenantExternalIdFromUrl($url);

                if (is_string($externalId) && $externalId !== '') {
                    return $externalId;
                }
            }
        } catch (\Throwable) {
            // Ignore and fall back to referer.
        }

        $referer = request()->headers->get('referer');

        if (! is_string($referer) || $referer === '') {
            return null;
        }

        return static::extractTenantExternalIdFromUrl($referer);
    }

    private static function extractTenantExternalIdFromUrl(string $url): ?string
    {
        $query = parse_url($url, PHP_URL_QUERY);

        if (is_string($query) && $query !== '') {
            parse_str($query, $queryParams);

            $tenantExternalId = $queryParams['tenant_id'] ?? null;

            if (is_string($tenantExternalId) && $tenantExternalId !== '') {
                return $tenantExternalId;
            }
        }

        $path = parse_url($url, PHP_URL_PATH);

        if (! is_string($path) || $path === '') {
            $path = $url;
        }

        if (preg_match('~/(?:admin)/(?:tenants|t)/([0-9a-fA-F-]{36})(?:/|$)~', $path, $matches) !== 1) {
            return null;
        }

        return (string) $matches[1];
    }

    private static function resolveTenantByExternalId(?string $externalId): ?Tenant
    {
        if (! is_string($externalId) || $externalId === '') {
            return null;
        }

        return Tenant::query()
            ->where('external_id', $externalId)
            ->first();
    }

    private static function resolveTenantFromRouteRecord(): ?Tenant
    {
        $record = request()->route('record');

        if ($record instanceof ProviderConnection) {
            return static::resolveTenantForRecord($record);
        }

        if (! is_numeric($record)) {
            return null;
        }

        $providerConnection = ProviderConnection::query()
            ->with('tenant')
            ->whereKey((int) $record)
            ->first();

        if (! $providerConnection instanceof ProviderConnection) {
            return null;
        }

        return static::resolveTenantForRecord($providerConnection);
    }

    private static function applyMembershipScope(Builder $query): Builder
    {
        $workspaceId = app(WorkspaceContext::class)->currentWorkspaceId(request());
        $user = auth()->user();

        if (! is_int($workspaceId)) {
            $filamentTenant = Filament::getTenant();

            if ($filamentTenant instanceof Tenant) {
                $workspaceId = (int) $filamentTenant->workspace_id;
            }
        }

        if (! is_int($workspaceId) || ! $user instanceof User) {
            return $query->whereRaw('1 = 0');
        }

        return $query
            ->where('provider_connections.workspace_id', $workspaceId)
            ->whereExists(function ($membershipScope) use ($user, $workspaceId): void {
                $membershipScope
                    ->selectRaw('1')
                    ->from('tenants as scoped_tenants')
                    ->join('tenant_memberships as scoped_memberships', function (JoinClause $join) use ($user): void {
                        $join->on('scoped_memberships.tenant_id', '=', 'scoped_tenants.id')
                            ->where('scoped_memberships.user_id', '=', (int) $user->getKey());
                    })
                    ->whereColumn('scoped_tenants.id', 'provider_connections.tenant_id')
                    ->where('scoped_tenants.workspace_id', '=', $workspaceId);
            });
    }

    /**
     * @return array<string, string>
     */
    private static function tenantFilterOptions(): array
    {
        $workspaceId = app(WorkspaceContext::class)->currentWorkspaceId(request());
        $user = auth()->user();

        if (! is_int($workspaceId) || ! $user instanceof User) {
            return [];
        }

        return Tenant::query()
            ->select(['tenants.external_id', 'tenants.name', 'tenants.environment'])
            ->join('tenant_memberships as filter_memberships', function (JoinClause $join) use ($user): void {
                $join->on('filter_memberships.tenant_id', '=', 'tenants.id')
                    ->where('filter_memberships.user_id', '=', (int) $user->getKey());
            })
            ->where('tenants.workspace_id', $workspaceId)
            ->orderBy('tenants.name')
            ->get()
            ->mapWithKeys(function (Tenant $tenant): array {
                $environment = strtoupper((string) ($tenant->environment ?? ''));
                $label = $environment !== '' ? "{$tenant->name} ({$environment})" : (string) $tenant->name;

                return [(string) $tenant->external_id => $label];
            })
            ->all();
    }

    private static function sanitizeErrorMessage(?string $value): ?string
    {
        if (! is_string($value) || trim($value) === '') {
            return null;
        }

        $normalized = preg_replace('/\s+/', ' ', strip_tags($value));
        $normalized = is_string($normalized) ? trim($normalized) : '';

        if ($normalized === '') {
            return null;
        }

        return Str::limit($normalized, 120);
    }

    public static function form(Schema $schema): Schema
    {
        return $schema
            ->schema([
                Section::make('Connection')
                    ->schema([
                        TextInput::make('display_name')
                            ->label('Display name')
                            ->required()
                            ->disabled(fn (): bool => ! static::hasTenantCapability(Capabilities::PROVIDER_MANAGE))
                            ->maxLength(255),
                        TextInput::make('entra_tenant_id')
                            ->label('Entra tenant ID')
                            ->required()
                            ->maxLength(255)
                            ->disabled(fn (): bool => ! static::hasTenantCapability(Capabilities::PROVIDER_MANAGE))
                            ->rules(['uuid']),
                        Toggle::make('is_default')
                            ->label('Default connection')
                            ->disabled(fn (): bool => ! static::hasTenantCapability(Capabilities::PROVIDER_MANAGE))
                            ->helperText('Exactly one default connection is required per tenant/provider.'),
                    ])
                    ->columns(2)
                    ->columnSpanFull(),
                Section::make('Status')
                    ->schema([
                        TextInput::make('status')
                            ->label('Status')
                            ->disabled()
                            ->dehydrated(false),
                        TextInput::make('health_status')
                            ->label('Health')
                            ->disabled()
                            ->dehydrated(false),
                    ])
                    ->columns(2)
                    ->columnSpanFull(),
            ]);
    }

    public static function table(Table $table): Table
    {
        return $table
            ->modifyQueryUsing(function (Builder $query): Builder {
                $query->with('tenant');

                $tenantExternalId = static::resolveRequestedTenantExternalId();

                if (! is_string($tenantExternalId) || $tenantExternalId === '') {
                    return $query;
                }

                return $query->whereHas('tenant', function (Builder $tenantQuery) use ($tenantExternalId): void {
                    $tenantQuery->where('external_id', $tenantExternalId);
                });
            })
            ->defaultSort('display_name')
            ->paginated(TablePaginationProfiles::resource())
            ->persistFiltersInSession()
            ->persistSearchInSession()
            ->persistSortInSession()
            ->recordUrl(fn (ProviderConnection $record): string => static::getUrl('view', ['record' => $record]))
            ->columns([
                Tables\Columns\TextColumn::make('tenant.name')
                    ->label('Tenant')
                    ->description(function (ProviderConnection $record): ?string {
                        $environment = $record->tenant?->environment;

                        if (! is_string($environment) || trim($environment) === '') {
                            return null;
                        }

                        return strtoupper($environment);
                    })
                    ->url(function (ProviderConnection $record): ?string {
                        $tenant = static::resolveTenantForRecord($record);

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

                        return TenantResource::getUrl('view', ['record' => $tenant], panel: 'admin');
                    }),
                Tables\Columns\TextColumn::make('display_name')->label('Name')->searchable()->sortable(),
                Tables\Columns\TextColumn::make('provider')->label('Provider')->toggleable(isToggledHiddenByDefault: true),
                Tables\Columns\TextColumn::make('entra_tenant_id')->label('Entra tenant ID')->copyable()->toggleable(isToggledHiddenByDefault: true),
                Tables\Columns\IconColumn::make('is_default')->label('Default')->boolean(),
                Tables\Columns\TextColumn::make('status')
                    ->label('Status')
                    ->badge()
                    ->formatStateUsing(BadgeRenderer::label(BadgeDomain::ProviderConnectionStatus))
                    ->color(BadgeRenderer::color(BadgeDomain::ProviderConnectionStatus))
                    ->icon(BadgeRenderer::icon(BadgeDomain::ProviderConnectionStatus))
                    ->iconColor(BadgeRenderer::iconColor(BadgeDomain::ProviderConnectionStatus)),
                Tables\Columns\TextColumn::make('health_status')
                    ->label('Health')
                    ->badge()
                    ->formatStateUsing(BadgeRenderer::label(BadgeDomain::ProviderConnectionHealth))
                    ->color(BadgeRenderer::color(BadgeDomain::ProviderConnectionHealth))
                    ->icon(BadgeRenderer::icon(BadgeDomain::ProviderConnectionHealth))
                    ->iconColor(BadgeRenderer::iconColor(BadgeDomain::ProviderConnectionHealth)),
                Tables\Columns\TextColumn::make('last_health_check_at')->label('Last check')->since()->sortable(),
                Tables\Columns\TextColumn::make('last_error_reason_code')
                    ->label('Last error reason')
                    ->toggleable(isToggledHiddenByDefault: true),
                Tables\Columns\TextColumn::make('last_error_message')
                    ->label('Last error message')
                    ->formatStateUsing(fn (?string $state): ?string => static::sanitizeErrorMessage($state))
                    ->toggleable(isToggledHiddenByDefault: true),
            ])
            ->filters([
                SelectFilter::make('tenant')
                    ->label('Tenant')
                    ->default(static::resolveScopedTenant()?->external_id)
                    ->options(static::tenantFilterOptions())
                    ->query(function (Builder $query, array $data): Builder {
                        $value = $data['value'] ?? null;

                        if (! is_string($value) || $value === '') {
                            return $query;
                        }

                        return $query->whereHas('tenant', function (Builder $tenantQuery) use ($value): void {
                            $tenantQuery->where('external_id', $value);
                        });
                    }),
                SelectFilter::make('provider')
                    ->label('Provider')
                    ->options([
                        'microsoft' => 'Microsoft',
                    ])
                    ->query(function (Builder $query, array $data): Builder {
                        $value = $data['value'] ?? null;

                        if (! is_string($value) || $value === '') {
                            return $query;
                        }

                        return $query->where('provider_connections.provider', $value);
                    }),
                SelectFilter::make('status')
                    ->label('Status')
                    ->options([
                        'connected' => 'Connected',
                        'needs_consent' => 'Needs consent',
                        'error' => 'Error',
                        'disabled' => 'Disabled',
                    ])
                    ->query(function (Builder $query, array $data): Builder {
                        $value = $data['value'] ?? null;

                        if (! is_string($value) || $value === '') {
                            return $query;
                        }

                        return $query->where('provider_connections.status', $value);
                    }),
                SelectFilter::make('health_status')
                    ->label('Health')
                    ->options([
                        'ok' => 'OK',
                        'degraded' => 'Degraded',
                        'down' => 'Down',
                        'unknown' => 'Unknown',
                    ])
                    ->query(function (Builder $query, array $data): Builder {
                        $value = $data['value'] ?? null;

                        if (! is_string($value) || $value === '') {
                            return $query;
                        }

                        return $query->where('provider_connections.health_status', $value);
                    }),
                Filter::make('default_only')
                    ->label('Default only')
                    ->query(fn (Builder $query): Builder => $query->where('provider_connections.is_default', true)),
            ])
            ->actions([
                Actions\ActionGroup::make([
                    UiEnforcement::forAction(
                        Actions\EditAction::make()
                    )
                        ->requireCapability(Capabilities::PROVIDER_MANAGE)
                        ->apply(),

                    UiEnforcement::forAction(
                        Actions\Action::make('check_connection')
                            ->label('Check connection')
                            ->icon('heroicon-o-check-badge')
                            ->color('success')
                            ->visible(fn (ProviderConnection $record): bool => $record->status !== 'disabled')
                            ->action(function (ProviderConnection $record, StartVerification $verification, \Filament\Tables\Contracts\HasTable $livewire): void {
                                $tenant = static::resolveTenantForRecord($record);
                                $user = auth()->user();

                                if (! $tenant instanceof Tenant) {
                                    abort(404);
                                }

                                if (! $user instanceof User) {
                                    abort(403);
                                }

                                $result = $verification->providerConnectionCheck(
                                    tenant: $tenant,
                                    connection: $record,
                                    initiator: $user,
                                );

                                if ($result->status === 'scope_busy') {
                                    Notification::make()
                                        ->title('Scope busy')
                                        ->body('Another provider operation is already running for this connection.')
                                        ->warning()
                                        ->actions([
                                            Actions\Action::make('view_run')
                                                ->label('View run')
                                                ->url(OperationRunLinks::view($result->run, $tenant)),
                                            Actions\Action::make('manage_connections')
                                                ->label('Manage Provider Connections')
                                                ->url(static::getUrl('index', tenant: $tenant)),
                                        ])
                                        ->send();

                                    return;
                                }

                                if ($result->status === 'deduped') {
                                    OpsUxBrowserEvents::dispatchRunEnqueued($livewire);

                                    OperationUxPresenter::alreadyQueuedToast((string) $result->run->type)
                                        ->actions([
                                            Actions\Action::make('view_run')
                                                ->label('View run')
                                                ->url(OperationRunLinks::view($result->run, $tenant)),
                                            Actions\Action::make('manage_connections')
                                                ->label('Manage Provider Connections')
                                                ->url(static::getUrl('index', tenant: $tenant)),
                                        ])
                                        ->send();

                                    return;
                                }

                                if ($result->status === 'blocked') {
                                    $reasonCode = is_string($result->run->context['reason_code'] ?? null)
                                        ? (string) $result->run->context['reason_code']
                                        : 'unknown_error';

                                    Notification::make()
                                        ->title('Connection check blocked')
                                        ->body("Blocked by provider configuration ({$reasonCode}).")
                                        ->warning()
                                        ->actions([
                                            Actions\Action::make('view_run')
                                                ->label('View run')
                                                ->url(OperationRunLinks::view($result->run, $tenant)),
                                            Actions\Action::make('manage_connections')
                                                ->label('Manage Provider Connections')
                                                ->url(static::getUrl('index', tenant: $tenant)),
                                        ])
                                        ->send();

                                    return;
                                }

                                OpsUxBrowserEvents::dispatchRunEnqueued($livewire);

                                OperationUxPresenter::queuedToast((string) $result->run->type)
                                    ->actions([
                                        Actions\Action::make('view_run')
                                            ->label('View run')
                                            ->url(OperationRunLinks::view($result->run, $tenant)),
                                    ])
                                    ->send();
                            })
                    )
                        ->preserveVisibility()
                        ->requireCapability(Capabilities::PROVIDER_RUN)
                        ->apply(),

                    UiEnforcement::forAction(
                        Actions\Action::make('inventory_sync')
                            ->label('Inventory sync')
                            ->icon('heroicon-o-arrow-path')
                            ->color('info')
                            ->visible(fn (ProviderConnection $record): bool => $record->status !== 'disabled')
                            ->action(function (ProviderConnection $record, ProviderOperationStartGate $gate, \Filament\Tables\Contracts\HasTable $livewire): void {
                                $tenant = static::resolveTenantForRecord($record);
                                $user = auth()->user();

                                if (! $tenant instanceof Tenant || ! $user instanceof User) {
                                    return;
                                }

                                $initiator = $user;

                                $result = $gate->start(
                                    tenant: $tenant,
                                    connection: $record,
                                    operationType: 'inventory_sync',
                                    dispatcher: function (OperationRun $operationRun) use ($tenant, $initiator, $record): void {
                                        ProviderInventorySyncJob::dispatch(
                                            tenantId: (int) $tenant->getKey(),
                                            userId: (int) $initiator->getKey(),
                                            providerConnectionId: (int) $record->getKey(),
                                            operationRun: $operationRun,
                                        );
                                    },
                                    initiator: $initiator,
                                );

                                if ($result->status === 'scope_busy') {
                                    Notification::make()
                                        ->title('Scope is busy')
                                        ->body('Another provider operation is already running for this connection.')
                                        ->danger()
                                        ->actions([
                                            Actions\Action::make('view_run')
                                                ->label('View run')
                                                ->url(OperationRunLinks::view($result->run, $tenant)),
                                        ])
                                        ->send();

                                    return;
                                }

                                if ($result->status === 'deduped') {
                                    OpsUxBrowserEvents::dispatchRunEnqueued($livewire);

                                    OperationUxPresenter::alreadyQueuedToast((string) $result->run->type)
                                        ->actions([
                                            Actions\Action::make('view_run')
                                                ->label('View run')
                                                ->url(OperationRunLinks::view($result->run, $tenant)),
                                        ])
                                        ->send();

                                    return;
                                }

                                if ($result->status === 'blocked') {
                                    $reasonCode = is_string($result->run->context['reason_code'] ?? null)
                                        ? (string) $result->run->context['reason_code']
                                        : 'unknown_error';

                                    Notification::make()
                                        ->title('Inventory sync blocked')
                                        ->body("Blocked by provider configuration ({$reasonCode}).")
                                        ->warning()
                                        ->actions([
                                            Actions\Action::make('view_run')
                                                ->label('View run')
                                                ->url(OperationRunLinks::view($result->run, $tenant)),
                                        ])
                                        ->send();

                                    return;
                                }

                                OpsUxBrowserEvents::dispatchRunEnqueued($livewire);

                                OperationUxPresenter::queuedToast((string) $result->run->type)
                                    ->actions([
                                        Actions\Action::make('view_run')
                                            ->label('View run')
                                            ->url(OperationRunLinks::view($result->run, $tenant)),
                                    ])
                                    ->send();
                            })
                    )
                        ->preserveVisibility()
                        ->requireCapability(Capabilities::PROVIDER_RUN)
                        ->apply(),

                    UiEnforcement::forAction(
                        Actions\Action::make('compliance_snapshot')
                            ->label('Compliance snapshot')
                            ->icon('heroicon-o-shield-check')
                            ->color('info')
                            ->visible(fn (ProviderConnection $record): bool => $record->status !== 'disabled')
                            ->action(function (ProviderConnection $record, ProviderOperationStartGate $gate, \Filament\Tables\Contracts\HasTable $livewire): void {
                                $tenant = static::resolveTenantForRecord($record);
                                $user = auth()->user();

                                if (! $tenant instanceof Tenant || ! $user instanceof User) {
                                    return;
                                }

                                $initiator = $user;

                                $result = $gate->start(
                                    tenant: $tenant,
                                    connection: $record,
                                    operationType: 'compliance.snapshot',
                                    dispatcher: function (OperationRun $operationRun) use ($tenant, $initiator, $record): void {
                                        ProviderComplianceSnapshotJob::dispatch(
                                            tenantId: (int) $tenant->getKey(),
                                            userId: (int) $initiator->getKey(),
                                            providerConnectionId: (int) $record->getKey(),
                                            operationRun: $operationRun,
                                        );
                                    },
                                    initiator: $initiator,
                                );

                                if ($result->status === 'scope_busy') {
                                    Notification::make()
                                        ->title('Scope is busy')
                                        ->body('Another provider operation is already running for this connection.')
                                        ->danger()
                                        ->actions([
                                            Actions\Action::make('view_run')
                                                ->label('View run')
                                                ->url(OperationRunLinks::view($result->run, $tenant)),
                                        ])
                                        ->send();

                                    return;
                                }

                                if ($result->status === 'deduped') {
                                    OpsUxBrowserEvents::dispatchRunEnqueued($livewire);

                                    OperationUxPresenter::alreadyQueuedToast((string) $result->run->type)
                                        ->actions([
                                            Actions\Action::make('view_run')
                                                ->label('View run')
                                                ->url(OperationRunLinks::view($result->run, $tenant)),
                                        ])
                                        ->send();

                                    return;
                                }

                                if ($result->status === 'blocked') {
                                    $reasonCode = is_string($result->run->context['reason_code'] ?? null)
                                        ? (string) $result->run->context['reason_code']
                                        : 'unknown_error';

                                    Notification::make()
                                        ->title('Compliance snapshot blocked')
                                        ->body("Blocked by provider configuration ({$reasonCode}).")
                                        ->warning()
                                        ->actions([
                                            Actions\Action::make('view_run')
                                                ->label('View run')
                                                ->url(OperationRunLinks::view($result->run, $tenant)),
                                        ])
                                        ->send();

                                    return;
                                }

                                OpsUxBrowserEvents::dispatchRunEnqueued($livewire);

                                OperationUxPresenter::queuedToast((string) $result->run->type)
                                    ->actions([
                                        Actions\Action::make('view_run')
                                            ->label('View run')
                                            ->url(OperationRunLinks::view($result->run, $tenant)),
                                    ])
                                    ->send();
                            })
                    )
                        ->preserveVisibility()
                        ->requireCapability(Capabilities::PROVIDER_RUN)
                        ->apply(),

                    UiEnforcement::forAction(
                        Actions\Action::make('set_default')
                            ->label('Set as default')
                            ->icon('heroicon-o-star')
                            ->color('primary')
                            ->requiresConfirmation()
                            ->visible(fn (ProviderConnection $record): bool => $record->status !== 'disabled' && ! $record->is_default)
                            ->action(function (ProviderConnection $record, AuditLogger $auditLogger): void {
                                $tenant = static::resolveTenantForRecord($record);

                                if (! $tenant instanceof Tenant) {
                                    return;
                                }

                                $record->makeDefault();

                                $user = auth()->user();
                                $actorId = $user instanceof User ? (int) $user->getKey() : null;
                                $actorEmail = $user instanceof User ? $user->email : null;
                                $actorName = $user instanceof User ? $user->name : null;

                                $auditLogger->log(
                                    tenant: $tenant,
                                    action: 'provider_connection.default_set',
                                    context: [
                                        'metadata' => [
                                            'provider' => $record->provider,
                                            'entra_tenant_id' => $record->entra_tenant_id,
                                        ],
                                    ],
                                    actorId: $actorId,
                                    actorEmail: $actorEmail,
                                    actorName: $actorName,
                                    resourceType: 'provider_connection',
                                    resourceId: (string) $record->getKey(),
                                    status: 'success',
                                );

                                Notification::make()
                                    ->title('Default connection updated')
                                    ->success()
                                    ->send();
                            })
                    )
                        ->preserveVisibility()
                        ->requireCapability(Capabilities::PROVIDER_MANAGE)
                        ->apply(),

                    UiEnforcement::forAction(
                        Actions\Action::make('update_credentials')
                            ->label('Update credentials')
                            ->icon('heroicon-o-key')
                            ->color('primary')
                            ->requiresConfirmation()
                            ->modalDescription('Client secret is stored encrypted and will never be shown again.')
                            ->form([
                                TextInput::make('client_id')
                                    ->label('Client ID')
                                    ->required()
                                    ->maxLength(255),
                                TextInput::make('client_secret')
                                    ->label('Client secret')
                                    ->password()
                                    ->required()
                                    ->maxLength(255),
                            ])
                            ->action(function (array $data, ProviderConnection $record, CredentialManager $credentials, AuditLogger $auditLogger): void {
                                $tenant = static::resolveTenantForRecord($record);

                                if (! $tenant instanceof Tenant) {
                                    return;
                                }

                                $credentials->upsertClientSecretCredential(
                                    connection: $record,
                                    clientId: (string) $data['client_id'],
                                    clientSecret: (string) $data['client_secret'],
                                );

                                $user = auth()->user();
                                $actorId = $user instanceof User ? (int) $user->getKey() : null;
                                $actorEmail = $user instanceof User ? $user->email : null;
                                $actorName = $user instanceof User ? $user->name : null;

                                $auditLogger->log(
                                    tenant: $tenant,
                                    action: 'provider_connection.credentials_updated',
                                    context: [
                                        'metadata' => [
                                            'provider' => $record->provider,
                                            'entra_tenant_id' => $record->entra_tenant_id,
                                            'client_id' => (string) $data['client_id'],
                                        ],
                                    ],
                                    actorId: $actorId,
                                    actorEmail: $actorEmail,
                                    actorName: $actorName,
                                    resourceType: 'provider_connection',
                                    resourceId: (string) $record->getKey(),
                                    status: 'success',
                                );

                                Notification::make()
                                    ->title('Credentials updated')
                                    ->success()
                                    ->send();
                            })
                    )
                        ->requireCapability(Capabilities::PROVIDER_MANAGE)
                        ->apply(),

                    UiEnforcement::forAction(
                        Actions\Action::make('enable_connection')
                            ->label('Enable connection')
                            ->icon('heroicon-o-play')
                            ->color('success')
                            ->requiresConfirmation()
                            ->visible(fn (ProviderConnection $record): bool => $record->status === 'disabled')
                            ->action(function (ProviderConnection $record, AuditLogger $auditLogger): void {
                                $tenant = static::resolveTenantForRecord($record);

                                if (! $tenant instanceof Tenant) {
                                    return;
                                }

                                $hadCredentials = $record->credential()->exists();
                                $previousStatus = (string) $record->status;

                                $status = $hadCredentials ? 'connected' : 'error';
                                $errorReasonCode = $hadCredentials ? null : ProviderReasonCodes::ProviderCredentialMissing;
                                $errorMessage = $hadCredentials ? null : 'Provider connection credentials are missing.';

                                $record->update([
                                    'status' => $status,
                                    'health_status' => 'unknown',
                                    'last_health_check_at' => null,
                                    'last_error_reason_code' => $errorReasonCode,
                                    'last_error_message' => $errorMessage,
                                ]);

                                $user = auth()->user();
                                $actorId = $user instanceof User ? (int) $user->getKey() : null;
                                $actorEmail = $user instanceof User ? $user->email : null;
                                $actorName = $user instanceof User ? $user->name : null;

                                $auditLogger->log(
                                    tenant: $tenant,
                                    action: 'provider_connection.enabled',
                                    context: [
                                        'metadata' => [
                                            'provider' => $record->provider,
                                            'entra_tenant_id' => $record->entra_tenant_id,
                                            'from_status' => $previousStatus,
                                            'to_status' => $status,
                                            'credentials_present' => $hadCredentials,
                                        ],
                                    ],
                                    actorId: $actorId,
                                    actorEmail: $actorEmail,
                                    actorName: $actorName,
                                    resourceType: 'provider_connection',
                                    resourceId: (string) $record->getKey(),
                                    status: 'success',
                                );

                                if (! $hadCredentials) {
                                    Notification::make()
                                        ->title('Connection enabled (credentials missing)')
                                        ->body('Add credentials before running checks or operations.')
                                        ->warning()
                                        ->send();

                                    return;
                                }

                                Notification::make()
                                    ->title('Provider connection enabled')
                                    ->success()
                                    ->send();
                            })
                    )
                        ->preserveVisibility()
                        ->requireCapability(Capabilities::PROVIDER_MANAGE)
                        ->apply(),

                    UiEnforcement::forAction(
                        Actions\Action::make('disable_connection')
                            ->label('Disable connection')
                            ->icon('heroicon-o-archive-box-x-mark')
                            ->color('danger')
                            ->requiresConfirmation()
                            ->visible(fn (ProviderConnection $record): bool => $record->status !== 'disabled')
                            ->action(function (ProviderConnection $record, AuditLogger $auditLogger): void {
                                $tenant = static::resolveTenantForRecord($record);

                                if (! $tenant instanceof Tenant) {
                                    return;
                                }

                                $previousStatus = (string) $record->status;

                                $record->update([
                                    'status' => 'disabled',
                                ]);

                                $user = auth()->user();
                                $actorId = $user instanceof User ? (int) $user->getKey() : null;
                                $actorEmail = $user instanceof User ? $user->email : null;
                                $actorName = $user instanceof User ? $user->name : null;

                                $auditLogger->log(
                                    tenant: $tenant,
                                    action: 'provider_connection.disabled',
                                    context: [
                                        'metadata' => [
                                            'provider' => $record->provider,
                                            'entra_tenant_id' => $record->entra_tenant_id,
                                            'from_status' => $previousStatus,
                                        ],
                                    ],
                                    actorId: $actorId,
                                    actorEmail: $actorEmail,
                                    actorName: $actorName,
                                    resourceType: 'provider_connection',
                                    resourceId: (string) $record->getKey(),
                                    status: 'success',
                                );

                                Notification::make()
                                    ->title('Provider connection disabled')
                                    ->warning()
                                    ->send();
                            })
                    )
                        ->preserveVisibility()
                        ->requireCapability(Capabilities::PROVIDER_MANAGE)
                        ->apply(),
                ])
                    ->label('More')
                    ->icon('heroicon-o-ellipsis-vertical')
                    ->color('gray'),
            ])
            ->bulkActions([]);
    }

    public static function getEloquentQuery(): Builder
    {
        $query = parent::getEloquentQuery()
            ->with('tenant');

        return static::applyMembershipScope($query)
            ->latest('provider_connections.id');
    }

    public static function getPages(): array
    {
        return [
            'index' => Pages\ListProviderConnections::route('/'),
            'create' => Pages\CreateProviderConnection::route('/create'),
            'view' => Pages\ViewProviderConnection::route('/{record}'),
            'edit' => Pages\EditProviderConnection::route('/{record}/edit'),
        ];
    }

    private static function normalizeTenantExternalId(mixed $tenant): ?string
    {
        if ($tenant instanceof Tenant) {
            return (string) $tenant->external_id;
        }

        if (is_string($tenant) && $tenant !== '') {
            return $tenant;
        }

        if (is_numeric($tenant)) {
            $tenantModel = Tenant::query()->whereKey((int) $tenant)->first();

            if ($tenantModel instanceof Tenant) {
                return (string) $tenantModel->external_id;
            }
        }

        return null;
    }

    /**
     * @param  array<mixed>  $parameters
     */
    public static function getUrl(?string $name = null, array $parameters = [], bool $isAbsolute = true, ?string $panel = null, ?Model $tenant = null, bool $shouldGuessMissingParameters = false): string
    {
        $panel ??= 'admin';
        $tenantExternalId = null;

        if (array_key_exists('tenant', $parameters)) {
            $tenantExternalId = static::normalizeTenantExternalId($parameters['tenant']);
            unset($parameters['tenant']);
        }

        if ($tenantExternalId === null && $tenant instanceof Tenant) {
            $tenantExternalId = (string) $tenant->external_id;
        }

        if ($tenantExternalId === null) {
            $record = $parameters['record'] ?? null;

            if ($record instanceof ProviderConnection) {
                $tenantExternalId = static::resolveTenantForRecord($record)?->external_id;
            }
        }

        if ($tenantExternalId === null) {
            $tenantExternalId = static::resolveScopedTenant()?->external_id;
        }

        if (! array_key_exists('tenant_id', $parameters) && is_string($tenantExternalId) && $tenantExternalId !== '') {
            $parameters['tenant_id'] = $tenantExternalId;
        }

        return parent::getUrl($name, $parameters, $isAbsolute, $panel, null, $shouldGuessMissingParameters);
    }
}
