hasAnyRole(['super-admin', 'admin'])) { return true; } return $user->can('contabilita.casse-banche'); } public function mount(): void { $this->mountInteractsWithTable(); } protected function getTableQuery(): Builder { $user = Auth::user(); if (! $user instanceof User) { return SaldoConto::query()->whereRaw('1 = 0'); } $stabileId = StabileContext::resolveActiveStabileId($user); if (! $stabileId) { return SaldoConto::query()->whereRaw('1 = 0'); } return SaldoConto::query() ->with('conto') ->where('stabile_id', $stabileId); } public function table(Table $table): Table { return $table ->striped() ->defaultSort('data_saldo', 'desc') ->columns([ TextColumn::make('conto_label') ->label('Conto') ->getStateUsing(function (SaldoConto $record): string { $c = $record->conto; if ($c instanceof DatiBancari) { $iban = is_string($c->iban) ? trim((string) $c->iban) : ''; return trim((string) ($c->denominazione_banca ?: 'Conto') . ($iban !== '' ? (' · ' . $iban) : '')); } $iban = is_string($record->iban) ? trim((string) $record->iban) : ''; return $iban !== '' ? $iban : '—'; }) ->searchable(query: function (Builder $query, string $search): Builder { $search = trim($search); if ($search === '') { return $query; } return $query->where(function (Builder $q) use ($search): void { $q->where('iban', 'like', '%' . $search . '%') ->orWhereHas('conto', fn(Builder $cq) => $cq->where('denominazione_banca', 'like', '%' . $search . '%')); }); }), TextColumn::make('data_saldo') ->label('Data') ->date('d/m/Y') ->sortable(), TextColumn::make('saldo') ->label('Saldo') ->alignEnd() ->formatStateUsing(fn($state) => '€ ' . number_format((float) $state, 2, ',', '.')), TextColumn::make('note') ->label('Note') ->wrap() ->toggleable(isToggledHiddenByDefault: true), TextColumn::make('updated_at') ->label('Aggiornato') ->dateTime('d/m/Y H:i') ->toggleable(isToggledHiddenByDefault: true), ]) ->headerActions([ Action::make('create') ->label('Nuovo saldo') ->icon('heroicon-o-plus') ->form([ Select::make('conto_id') ->label('Conto') ->native(false) ->searchable() ->options(fn(): array => $this->getContiOptions()) ->required(), DatePicker::make('data_saldo')->label('Data')->required(), TextInput::make('saldo')->label('Saldo')->numeric()->required(), Textarea::make('note')->label('Note (opzionale)')->rows(2)->maxLength(255), ]) ->action(function (array $data): void { $user = Auth::user(); if (! $user instanceof User) { return; } $stabileId = StabileContext::resolveActiveStabileId($user); if (! $stabileId) { return; } $contoId = isset($data['conto_id']) && is_numeric($data['conto_id']) ? (int) $data['conto_id'] : 0; if ($contoId <= 0) { return; } $conto = DatiBancari::query() ->where('stabile_id', $stabileId) ->where('id', $contoId) ->first(['id', 'iban']); $iban = $conto && is_string($conto->iban) ? trim((string) $conto->iban) : null; $iban = is_string($iban) && $iban !== '' ? $iban : null; SaldoConto::query()->create([ 'stabile_id' => (int) $stabileId, 'conto_id' => $contoId, 'iban' => $iban, 'data_saldo' => $data['data_saldo'] ?? null, 'saldo' => isset($data['saldo']) ? (float) $data['saldo'] : 0.0, 'note' => isset($data['note']) && is_string($data['note']) ? trim((string) $data['note']) : null, 'created_by' => (int) ($user->id ?? 0) ?: null, 'updated_by' => (int) ($user->id ?? 0) ?: null, ]); }), ]) ->actions([ Action::make('edit') ->label('Modifica') ->icon('heroicon-o-pencil-square') ->form([ DatePicker::make('data_saldo')->label('Data')->required(), TextInput::make('saldo')->label('Saldo')->numeric()->required(), Textarea::make('note')->label('Note (opzionale)')->rows(2)->maxLength(255), ]) ->fillForm(fn(SaldoConto $record): array => [ 'data_saldo' => $record->data_saldo, 'saldo' => (float) $record->saldo, 'note' => $record->note, ]) ->action(function (SaldoConto $record, array $data): void { $user = Auth::user(); $record->fill([ 'data_saldo' => $data['data_saldo'] ?? $record->data_saldo, 'saldo' => isset($data['saldo']) ? (float) $data['saldo'] : (float) $record->saldo, 'note' => isset($data['note']) && is_string($data['note']) ? trim((string) $data['note']) : null, 'updated_by' => $user instanceof User ? ((int) $user->id ?: null) : null, ]); $record->save(); }), Action::make('delete') ->label('Elimina') ->icon('heroicon-o-trash') ->color('danger') ->requiresConfirmation() ->action(fn(SaldoConto $record) => $record->delete()), ]); } /** @return array */ protected function getContiOptions(): array { $user = Auth::user(); if (! $user instanceof User) { return []; } $stabileId = StabileContext::resolveActiveStabileId($user); if (! $stabileId) { return []; } if (! DB::getSchemaBuilder()->hasTable('dati_bancari')) { return []; } return DatiBancari::query() ->where('stabile_id', $stabileId) ->orderBy('stato_conto') ->orderBy('denominazione_banca') ->orderBy('iban') ->orderBy('id') ->get(['id', 'denominazione_banca', 'iban']) ->mapWithKeys(function (DatiBancari $r): array { $iban = is_string($r->iban) ? trim((string) $r->iban) : ''; $label = trim((string) ($r->denominazione_banca ?: 'Conto') . ($iban !== '' ? (' · ' . $iban) : '')); return [(int) $r->id => $label]; }) ->all(); } }