F
Filament3mo ago
morty

How can I refresh the options on a table filter after an action?

I have a select filter on a table called "collection" that filters records if they belong to that collection. I also have a bulk create action to create a new collection and assign the selected records to the collection. My problem is that if I create a new collection, I can't immediately filter the table with that new collection unless I hard refresh the page because the filter options haven't been updated. What do I need to do to have the filter update itself?
Solution:
OMG I solved it. I changed my form from this: ```php...
Jump to solution
13 Replies
morty
morty3mo ago
As far as I can get is adding a livewire listener on the list page and putting a ->dispatch() on my action but the dispatch sends the event when the button is clicked, not when the form is submitted. bump
toeknee
toeknee3mo ago
After the bulk try? $this->refresh()
morty
morty3mo ago
Where do I do that? This is my code:
Tables\Actions\BulkAction::make('createNewCollection')
->label('Create new collection')
->icon('heroicon-o-rectangle-stack')
->modalIcon('heroicon-o-rectangle-stack')
->modalWidth(MaxWidth::Small)
->modalSubmitActionLabel('Save')
->form([
Forms\Components\TextInput::make('name')
->label('Name')
->required(),
Forms\Components\Toggle::make('public')
->label('Public')
->rule('boolean'),
])
->action(function (array $data, Collection $accounts): void {
$collection = AccountCollection::create($data);
$chunks = $accounts->pluck('id')->chunk(500);
$chunks->each(fn ($chunk) => $collection->accounts()->attach($chunk));
})
->after(fn () => Notification::make()->success()->title('Saved')->send()),
Tables\Actions\BulkAction::make('createNewCollection')
->label('Create new collection')
->icon('heroicon-o-rectangle-stack')
->modalIcon('heroicon-o-rectangle-stack')
->modalWidth(MaxWidth::Small)
->modalSubmitActionLabel('Save')
->form([
Forms\Components\TextInput::make('name')
->label('Name')
->required(),
Forms\Components\Toggle::make('public')
->label('Public')
->rule('boolean'),
])
->action(function (array $data, Collection $accounts): void {
$collection = AccountCollection::create($data);
$chunks = $accounts->pluck('id')->chunk(500);
$chunks->each(fn ($chunk) => $collection->accounts()->attach($chunk));
})
->after(fn () => Notification::make()->success()->title('Saved')->send()),
Also here is a gif of what I'm talking about:
morty
morty3mo ago
No description
morty
morty3mo ago
I tried doing a $livewire->dispatch('$refresh') in my after() method which does refresh the livewire component page but the options in the filter are not refreshed for some reason. I'm thinking maybe because they're filled in the mount() method that only occurs during a hard refresh. Is there a way around this?
Solution
morty
morty3mo ago
OMG I solved it. I changed my form from this:
->options([
// options
]),
->options([
// options
]),
to this:
->options(fn() => [
// options
]),
->options(fn() => [
// options
]),
morty
morty3mo ago
I still don't understand why wrapping it in a closure fixes it. Does anyone else?
toeknee
toeknee3mo ago
Because you’re allowing the closure to be run again, whereas as before it was a static array. As per the docs you should ensure your options are closures, or a full static array if it never changes. Any db selects in options have to be closures otherwise you end up with massive amounts of duplicate queries too.
morty
morty3mo ago
Thanks for the reply. Do you mind linking the docs to me for this specific thing? I can't seem to find it, sorry 😄 This still isn't consistent. I'm so confused. This does not refresh from the database when clicked:
Tables\Filters\SelectFilter::make('country_code')
->label('Country')
->placeholder('All')
->searchable()
->options(
fn (): array => Account::distinct()
->orderBy('country_code')
->pluck('country_code as value', 'country_code as key')
->all()
),
Tables\Filters\SelectFilter::make('country_code')
->label('Country')
->placeholder('All')
->searchable()
->options(
fn (): array => Account::distinct()
->orderBy('country_code')
->pluck('country_code as value', 'country_code as key')
->all()
),
But, a custom filter with this does:
Tables\Filters\Filter::make('collection')
->label('Collection')
->form([
Forms\Components\Select::make('collection')
->label('Collection')
->placeholder('All')
->searchable()
->options(fn (): array => [
'My private collections' => AccountCollection::private()->ownedByCurrentUser()->orderBy('name')->pluck('name', 'id')->all(),
'My public collections' => AccountCollection::public()->ownedByCurrentUser()->orderBy('name')->pluck('name', 'id')->all(),
'Other public collections' => AccountCollection::public()->notOwnedByCurrentUser()->orderBy('name')->pluck('name', 'id')->all(),
]),
])
Tables\Filters\Filter::make('collection')
->label('Collection')
->form([
Forms\Components\Select::make('collection')
->label('Collection')
->placeholder('All')
->searchable()
->options(fn (): array => [
'My private collections' => AccountCollection::private()->ownedByCurrentUser()->orderBy('name')->pluck('name', 'id')->all(),
'My public collections' => AccountCollection::public()->ownedByCurrentUser()->orderBy('name')->pluck('name', 'id')->all(),
'Other public collections' => AccountCollection::public()->notOwnedByCurrentUser()->orderBy('name')->pluck('name', 'id')->all(),
]),
])
toeknee
toeknee3mo ago
try
Tables\Filters\SelectFilter::make('country_code')
->label('Country')
->placeholder('All')
->searchable()
->live()
->options(
fn (): array => Account::distinct()
->orderBy('country_code')
->pluck('country_code as value', 'country_code as key')
->all()
),
Tables\Filters\SelectFilter::make('country_code')
->label('Country')
->placeholder('All')
->searchable()
->live()
->options(
fn (): array => Account::distinct()
->orderBy('country_code')
->pluck('country_code as value', 'country_code as key')
->all()
),
morty
morty3mo ago
No description
morty
morty3mo ago
BadMethodCallException PHP 8.2.16 10.48.4 Method Filament\Tables\Filters\SelectFilter::live does not exist.
mohsin_ismail
mohsin_ismail2w ago
Thank A LOTT.. Its workkk.. I have the same issue for a few hours...