symfony / ux

Symfony UX initiative: a JavaScript ecosystem for Symfony
https://ux.symfony.com/
MIT License
820 stars 298 forks source link

[Autocomplete] AJAX Autocomplete not working after upgrade to v.2.17 - ExtraLazyChoiceLoader problem #1770

Closed vesselind closed 5 months ago

vesselind commented 5 months ago

I have my own custom autocompleteField class which worked properly till now. After upgrading the ux-autocomplete to v.2.17 and replacing the parent class ParentEntityAutocompleteType::class with the new one BaseEntityAutocompleteType::class I receive the following error: Symfony\UX\Autocomplete\Form\ChoiceList\Loader\ExtraLazyChoiceLoader::__construct(): Argument #1 ($decorated) must be of type Symfony\Component\Form\ChoiceList\Loader\ChoiceLoaderInterface, null given, called in D:\laragon\www\youcook.online\vendor\symfony\ux-autocomplete\src\Form\BaseEntityAutocompleteType.php on line 41

Here is the code of my class:

public function configureOptions(OptionsResolver $resolver)
    {
        $resolver->setDefaults([
            'class' => RecipeCategory::class,
            'placeholder' => 'placeholder.recipe_category',
            'choices' =>  $this->treeBuilder->buildTree(),
            'choice_label' => function ($category) {
                return sprintf('%s %s', str_repeat('-', $category->level), $category);
            },
        ]);
    }

    public function getParent(): string
    {
        return BaseEntityAutocompleteType::class;
    }

Perhaps the problem has something to do with the choices option. I pass the $this->treeBuilder->buildTree() which returns an array. This seemed to be okay in the past, but somehow is problematic now.

yceruto commented 5 months ago

When the choices option is set, the Doctrine loader is omitted, meaning that you don't need a loader at all as your choices are hardcoded. Thus, the parent loader will be null

https://github.com/symfony/ux/blob/80b36bcbeb2902a55495db2afd544f738c73148f/src/Autocomplete/src/Form/BaseEntityAutocompleteType.php#L38-L42

In your case, in the meantime, you can fix it by setting choice_loader to null directly.

In our case, we should update BaseEntityAutocompleteType so we ignore the ExtraLazyChoiceLoader if the parent $loader is null which is the case here:

$choiceLoader = static function (Options $options, $loader) {
    if (null === $loader) {
        return null;
    }

    return new ExtraLazyChoiceLoader($loader);
};

@vesselind would you like send a PR fixing it?