BUGFIX many many through not sorting by join table #8534
Merged
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Resolves #7981
Todo:
many_many
joins work by doing a join with two separate queries.eg.
As you can see, the inner query is sorting correctly on the join table (by Sort ASC). However, the main query has its own sort which overrides that when you get the final set of results.
This inner query is built by SilverStripe using the standard ORM functions and assumes the default sort of the join DataObject (FluentFallbackLocale in this case). Likewise for the main query.
With @robbieaverill's fix it will sort correctly in cases where no default sort is set on the main DataObject and default is set on the join table data object. However, if the default sort is set on the main Dataobject, the fix will essentially be bypassed since sort is already set which is what we're seeing with Fluent.
The fix i've added applies the sort order much earlier, when it first starts building the ORM query objects. It will check to see if there is config which defines a default sort on the join table (this should also work for standard many-many sort too) and applies that if so. If that has no value, it will fallback to whatever sort SilverStripe gives it (default sort on dataobject or natural database sort).
This happens early enough that
->sort()
will function as normal if the user decides to sort by something else and early enough thatupdateManymanyComponents
can be hooked into.