Thanks to visit codestin.com
Credit goes to github.com

Skip to content

[Form] ObjectChoiceList should select initial field value based on the value property. #8825

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
oscherler opened this issue Aug 22, 2013 · 7 comments
Labels

Comments

@oscherler
Copy link
Contributor

When using an ObjectChoiceList with a value path given, and presetting the form data with some initial value, it only works if the object in the form data is the same instance as the corresponding object in the choice list.

I would expect the form data and the choices to be matched by their value (the value of the property at $valuePath) instead. Indeed, this is what happens when the form is submitted: the request contains the value and Symfony uses it to retrieve the matching object from the choices.

Here is a fork of symfony-standard that demonstrates this. The demo is located at /demo/objectchoicelist.

https://github.com/oscherler/symfony-standard/tree/objectchoicelist

In the first 4 fields (Same instance …) I use an object from the choices to populate the form data, and the value is properly selected.

In the next 4 fields (Other instance …) I create a new object with the same properties (same value) as one of the objects in the choice list, and no value is selected.

@webmozart
Copy link
Contributor

Thank you! :) I will look into this ASAP.

@oscherler
Copy link
Contributor Author

I tried to have a look yesterday, but I didn’t really understand what I was doing. It seems to come from the if ($choice === $givenChoice) in ChoiceList::getValuesForChoices() and ChoiceList::getIndicesForChoices(), but if I change anything it breaks a lot of tests.

I first tried overriding fixChoice and fixChoices to call createValue on the choice, but it breaks tests. Then I tried calling createValue on both sides of the comparison in getValuesForChoices and getIndicesForChoices (overriding them), but in the tests, createValue throws a lot of exceptions for NULL arguments, one might need to check against that too, but what to return?

@oscherler
Copy link
Contributor Author

A side effect of the same issue is that the objects given in $preferredChoices also have to be the same instance to be taken into account.

@xabbuh
Copy link
Member

xabbuh commented Sep 8, 2013

I took some effort on this issue. It seemed to me that the problem is the comparison for equality in ChoiceList.

Overriding the getValuesForChoices() method in ObjectChoiceList like this fixed the problem for me (note the use of createValue()):

public function getValuesForChoices(array $choices)
{
    $choices = $this->fixChoices($choices);
    $values = array();

    $availableValues = $this->getValues();
    foreach ($this->getChoices() as $i => $choice) {
        foreach ($choices as $j => $givenChoice) {
            if ($this->createValue($choice) === $this->createValue($givenChoice)) {
                $values[] = $availableValues[$i];
                unset($choices[$j]);

                if (0 === count($choices)) {
                    break 2;
                }
            }
        }
    }

    return $values;
}

But I am not so familiar with the internals of the Form component. Thus, I'm not quite sure if this is a general solution. What do you think, @bschussek?

@xabbuh
Copy link
Member

xabbuh commented Oct 1, 2013

@bschussek should I create a pull request for this?

@Tjeerd
Copy link

Tjeerd commented Nov 11, 2013

👍, same issue here, I agree that, if, at least, a valuePath is given, it should compare on the actual value instead of comparing the (reference of) the objects.

@caseyamcl
Copy link

+1, I am having the same issue. I hope this pull request passes and gets pulled in.

fabpot added a commit that referenced this issue Mar 31, 2014
…value, if a value path is given (webmozart)

This PR was merged into the 2.5-dev branch.

Discussion
----------

[Form] ObjectChoiceList now compares choices by their value, if a value path is given

| Q             | A
| ------------- | ---
| Bug fix?      | no
| New feature?  | yes
| BC breaks?    | no
| Deprecations? | no
| Tests pass?   | yes
| Fixed tickets | #8825
| License       | MIT
| Doc PR        | -

Commits
-------

ce0efb1 [Form] ObjectChoiceList now compares choices by their value, if a value path is given
@fabpot fabpot closed this as completed Mar 31, 2014
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

6 participants