I created this filter for Nova v4.32.11:
class AccountFilter extends Filter
{
public function apply(Request $request, $query, $value)
{
return $query->where('account_id', $value);
}
public function options(Request $request)
{
return Account::all()
->sortBy('name')
->mapWithKeys(function ($account) {
return [$account->id => $account->name];
})
->toArray();
}
}
If I dd() the array being returned in options() it looks like this:
[
1 => 'Foo',
2 => 'Bar',
3 => 'Baz',
]
However, if I inspect the element in Nova I see this for the select options:
<select dusk="Account Filter-select-filter" class="w-full block form-control form-select form-control-sm form-select-bordered">
<option value="">—</option>
<option value="Foo">Foo</option>
<option value="Bar">Bar</option>
<option value="Baz">Baz</option>
</select>
If I dd() the $value in apply() I see that value is indeed the account name instead of the ID as I'd expect from the array returned for the options list.
I decided to manually return exactly what I pasted above as the output...
What is wrong here?


It seems like you need to use the account ID for filtering, but Laravel Nova is using the account name instead. One workaround is to use a custom component for the filter. This way, you can control the select options' value and display text separately.
First, you need to create a new Vue component. This component will be used for the filter. In this component, you can specify the value and the display text of the select options separately.
Here is an example of how you can create this component:
Next, you need to register this component in your Nova service provider:
Finally, you can use this component in your
AccountFilterclass:In this modified version, the
applymethod filters by the account ID, and theoptionsmethod returns an array where the keys are the IDs and the values are the names. Thecomponentsmethod specifies that thecustom-filtercomponent should be used for this filter. This way, the value selected in the Nova interface will match the value used in theapplymethod.