<?php

namespace App\Filament\Central\Resources\CompanyResource\Pages;

use App\Filament\Central\Resources\CompanyResource;
use App\Models\Central\Company;
use App\Models\Central\Subscription;
use App\Models\Tenant\Client;
use App\Models\Tenant\Part;
use App\Models\Tenant\Payment;
use App\Models\Tenant\User as TenantUser;
use App\Models\Tenant\Vehicle;
use App\Models\Tenant\WorkOrder;
use App\Tenancy\TenantManager;
use Filament\Actions;
use Filament\Forms;
use Filament\Notifications\Notification;
use Filament\Resources\Pages\Page;

class ViewCompany extends Page
{
    protected static string $resource = CompanyResource::class;

    protected string $view = 'filament.central.resources.company.view';

    public Company $record;

    public function mount(int|string $record): void
    {
        // The {record} route param may arrive as a scalar id, an Eloquent model,
        // or (via Livewire's typed-property hydration) a JSON-encoded model.
        // Normalize all of these down to the integer primary key.
        $key = $this->resolveRecordKey($record);

        $this->record = Company::with(['plan', 'subscriptions' => fn ($q) => $q->latest('period_end')->limit(10)])
            ->findOrFail($key);
    }

    private function resolveRecordKey(mixed $record): int|string
    {
        if ($record instanceof Company) {
            return $record->getKey();
        }
        if (is_string($record) && str_starts_with(ltrim($record), '{')) {
            $decoded = json_decode($record, true);
            if (is_array($decoded) && isset($decoded['id'])) {
                return $decoded['id'];
            }
        }
        return $record;
    }

    public function getTitle(): string
    {
        return $this->record->display_name ?? $this->record->name;
    }

    public function getStats(): array
    {
        // Set tenant context to query scoped tables.
        app(TenantManager::class)->setCurrent($this->record);
        app(\Spatie\Permission\PermissionRegistrar::class)
            ->setPermissionsTeamId($this->record->id);

        $stats = [
            'users' => TenantUser::count(),
            'clients' => Client::count(),
            'vehicles' => Vehicle::count(),
            'work_orders' => WorkOrder::count(),
            'work_orders_open' => WorkOrder::whereNotIn('status', ['done', 'cancelled'])->count(),
            'parts' => Part::count(),
            'parts_low_stock' => Part::where('is_active', true)
                ->whereColumn('qty', '<=', 'min_qty')
                ->where('qty', '>', 0)
                ->count(),
            'revenue_this_month' => (float) Payment::whereYear('paid_at', date('Y'))
                ->whereMonth('paid_at', date('m'))->sum('amount'),
            'revenue_last_month' => (float) Payment::whereYear('paid_at', now()->subMonth()->year)
                ->whereMonth('paid_at', now()->subMonth()->month)->sum('amount'),
            'last_login' => TenantUser::whereNotNull('last_login_at')->max('last_login_at'),
            'storage_mb' => $this->calculateStorageMb(),
        ];

        app(TenantManager::class)->setCurrent(null);
        return $stats;
    }

    private function calculateStorageMb(): float
    {
        try {
            $bytes = (int) \DB::table('media')
                ->where('model_type', \App\Models\Central\Company::class)
                ->where('model_id', $this->record->id)
                ->sum('size');
            return round($bytes / 1024 / 1024, 2);
        } catch (\Throwable) {
            return 0;
        }
    }

    public function getDaysUntilExpiry(): ?int
    {
        $until = $this->record->active_until ?? $this->record->trial_ends_at;
        if (! $until) return null;
        $diff = now()->diffInDays($until, false);
        return (int) $diff;
    }

    protected function getHeaderActions(): array
    {
        return [
            Actions\Action::make('view_as')
                ->label('Deschide tenantul')
                ->icon('heroicon-m-arrow-top-right-on-square')
                ->color('primary')
                ->url(fn () => $this->record->url('/app'))
                ->openUrlInNewTab(),
            Actions\Action::make('issue_invoice')
                ->label('Generează factură')
                ->icon('heroicon-m-document-plus')
                ->color('success')
                ->visible(fn () => (bool) $this->record->plan_id)
                ->schema([
                    Forms\Components\Select::make('period')->options(\App\Models\Central\Subscription::PERIODS)->default('monthly')->required(),
                ])
                ->action(function (array $data) {
                    $plan = $this->record->plan;
                    if (! $plan) return;
                    $start = today();
                    $end = $data['period'] === 'yearly' ? $start->copy()->addYear() : $start->copy()->addMonth();
                    $sub = Subscription::create([
                        'company_id' => $this->record->id,
                        'plan_id' => $plan->id,
                        'period' => $data['period'],
                        'amount' => $data['period'] === 'yearly' ? $plan->price_yearly : $plan->price_monthly,
                        'currency' => $plan->currency,
                        'status' => 'pending',
                        'period_start' => $start,
                        'period_end' => $end,
                        'due_at' => $start->copy()->addDays(7),
                        'invoice_number' => Subscription::generateInvoiceNumber(),
                    ]);
                    Notification::make()
                        ->title('Factură generată: ' . $sub->invoice_number)
                        ->body('Suma: ' . number_format($sub->amount, 2) . ' ' . $sub->currency)
                        ->success()->send();
                    $this->dispatch('$refresh');
                }),
            Actions\Action::make('upload_logo')
                ->label('Logo')
                ->icon('heroicon-m-photo')
                ->color('gray')
                ->schema([
                    Forms\Components\FileUpload::make('logo')
                        ->image()
                        ->imageEditor()
                        ->disk('public')
                        ->directory('central-uploads')
                        ->maxSize(2048)
                        ->required(),
                ])
                ->action(function (array $data) {
                    if (empty($data['logo'])) return;
                    $abs = \Illuminate\Support\Facades\Storage::disk('public')->path($data['logo']);
                    if (file_exists($abs)) {
                        $this->record->clearMediaCollection('logo');
                        $this->record->addMedia($abs)->preservingOriginal()->toMediaCollection('logo');
                        @unlink($abs);
                        Notification::make()->title('Logo actualizat')->success()->send();
                    }
                }),
            Actions\Action::make('edit')
                ->label('Editează')
                ->icon('heroicon-m-pencil')
                ->url(fn () => CompanyResource::getUrl('edit', ['record' => $this->record])),
            Actions\Action::make('suspend')
                ->label('Suspendă')->icon('heroicon-m-no-symbol')->color('danger')
                ->visible(fn () => in_array($this->record->status, ['active', 'trial']))
                ->requiresConfirmation()
                ->action(function () {
                    app(\App\Services\CompanyProvisioner::class)->suspend($this->record);
                    Notification::make()->title('Tenant suspendat.')->success()->send();
                    $this->dispatch('$refresh');
                }),
            Actions\Action::make('activate')
                ->label('Reactivează')->icon('heroicon-m-check-circle')->color('success')
                ->visible(fn () => in_array($this->record->status, ['suspended', 'expired']))
                ->requiresConfirmation()
                ->action(function () {
                    app(\App\Services\CompanyProvisioner::class)->reactivate($this->record);
                    Notification::make()->title('Tenant activat.')->success()->send();
                    $this->dispatch('$refresh');
                }),
        ];
    }
}
