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

Skip to content

[Component][Form][ChoiceType] : Add new option to sort group_by value #22136

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
wants to merge 1 commit into from

Conversation

jsamouh
Copy link
Contributor

@jsamouh jsamouh commented Mar 23, 2017

Q A
Branch? master
Bug fix? no
New feature? yes
BC breaks? no
Deprecations? no
Tests pass? yes
Fixed tickets #21717
License MIT
Doc PR symfony/symfony-docs

A Proposal PR to have the possibility to define an order for group_by value without create a difficult twig rendering or override buildView Form

@jsamouh
Copy link
Contributor Author

jsamouh commented Mar 23, 2017

@HeahDude , @stof , a PR proposal : New option group_by_order to manage the group order
Tell me WDYT

@nicolas-grekas nicolas-grekas added this to the 3.x milestone Mar 24, 2017
@@ -81,6 +81,12 @@ public function createView(ChoiceListInterface $list, $preferredChoices = null,
$otherViews
);
}

if ($groupByOrder && is_array($groupByOrder)) {
uksort($otherViews, function ($key1, $key2) use ($groupByOrder) {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this logic does not seem to support callable values for $groupByOrder, while the interface allows it (and callables can be arrays, making things even worse).

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'd like to see this support both callables and predefined arrays. Something like this should work:

if ($groupByOrder) {
    if (is_callable($groupByOrder)) {
        // TODO
    } elseif (is_array($groupByOrder)) {
        // TODO
    }
}

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@colinodell , thanks
Can you give me an example of callable groupByOrder you need ?
Which parameters you need in the function ?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The callable should be compatible with uksort - anything that takes two parameters, compares them, and returns an integer. Your code would then look something like this:

if ($groupByOrder) {
    if (is_callable($groupByOrder)) {
        uksort($otherViews, $groupByOrder);
    } elseif (is_array($groupByOrder)) {
        // TODO: Your existing code goes here
    }
}

I could then use any type of callable for the groupByOrder option:

  • 'strnatcmp' - Sort them using a "natural order" algorithm via the strnatcmp() function
  • [$this, 'sortGroups'] - Use the sortGroups() function on $this
  • [Foo::class, 'sortGroups'] - Use the static sortGroups() function from the Foo class
  • function ($a, $b) { return $b <=> $a; } - Use some anonymous function

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@colinodell thanks, will do that soon

*
* @return ChoiceListView The choice list view
*/
public function createView(ChoiceListInterface $list, $preferredChoices = null, $label = null, $index = null, $groupBy = null, $attr = null);
public function createView(ChoiceListInterface $list, $preferredChoices = null, $label = null, $index = null, $groupBy = null, $attr = null, $groupByOrder = null);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

adding arguments in an interface is forbidden by our BC policy

@@ -356,6 +357,7 @@ public function configureOptions(OptionsResolver $resolver)
$resolver->setAllowedTypes('choice_attr', array('null', 'array', 'callable', 'string', 'Symfony\Component\PropertyAccess\PropertyPath'));
$resolver->setAllowedTypes('preferred_choices', array('array', '\Traversable', 'callable', 'string', 'Symfony\Component\PropertyAccess\PropertyPath'));
$resolver->setAllowedTypes('group_by', array('null', 'callable', 'string', 'Symfony\Component\PropertyAccess\PropertyPath'));
$resolver->setAllowedTypes('group_by_order', array('null', 'array', '\Traversable'));
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this does not match the types supported by the implementation.

@@ -148,10 +148,11 @@ public function createListFromLoader(ChoiceLoaderInterface $loader, $value = nul
* @param null|callable|string|PropertyPath $index The callable or path generating the view indices
* @param null|callable|string|PropertyPath $groupBy The callable or path generating the group names
* @param null|array|callable|string|PropertyPath $attr The callable or path generating the HTML attributes
* @param null|array|callable|string|PropertyPath $groupByOrder The groupBy order
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this does not support a PropertyPath, as you don't handle it

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Does PropertyPath even make sense here?

@@ -152,7 +152,7 @@ public function createListFromLoader(ChoiceLoaderInterface $loader, $value = nul
/**
* {@inheritdoc}
*/
public function createView(ChoiceListInterface $list, $preferredChoices = null, $label = null, $index = null, $groupBy = null, $attr = null)
public function createView(ChoiceListInterface $list, $preferredChoices = null, $label = null, $index = null, $groupBy = null, $attr = null, $groupByOrder = null)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The new value must be taken into account when building the cache key, otherwise a list could be reused while it was having a different order

@jsamouh
Copy link
Contributor Author

jsamouh commented Mar 31, 2017

@stof thanks for your review. If adding a parameter is a BC break, do you have an advice to deal a new parameter ? or do it differently ?

@jsamouh
Copy link
Contributor Author

jsamouh commented Apr 5, 2017

@stof a little ping on my comments to continue the PR if you want ^^

Also, same remark as @colinodell , How do you see the callable groupByOrder ? Which parameters we propose in the callable function ?

@jsamouh
Copy link
Contributor Author

jsamouh commented Apr 11, 2017

ping @stof

@nicolas-grekas
Copy link
Member

Moving to 4.1. Rebase on master might be needed, where PHP 7.1 features can be used btw.

@nicolas-grekas nicolas-grekas modified the milestones: 3.4, 4.1 Oct 8, 2017
@nicolas-grekas nicolas-grekas modified the milestones: 4.1, next Apr 20, 2018
@webmozart
Copy link
Contributor

I'm 👎 on this feature. The problem solved here can easily be solved by sorting the choices before passing them to the choices option (either with usort() or - better - in the database).

@fabpot fabpot closed this Apr 6, 2019
@webmozart
Copy link
Contributor

@fabpot #21717 should be closed as well.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

7 participants