Support for Drupal 7 is ending on 5 January 2025—it’s time to migrate to Drupal 10! Learn about the many benefits of Drupal 10 and find migration tools in our resource center.
Updated: Comment #24
Problem/Motivation
In general we want to get rid of using paths but switch to route names and route parameters to generate URLs. The url generator
defined by symfony defines a method called generate which does not deals with extra options like query, fragment, language or manually set https.
Proposed resolution
- Define a new interface called \Drupal\Core\Routing\UrlGeneratorInterface which extends the one from symfony
- Add a new method called generateFromRoute which accepts $options
- Merge the current PathBasedGeneratorInterface into the new interface
- Make the new Drupal UrlGeneratorInterface extend the symfony VersatileGeneratorInterface so we can insure all expected methods are present
Remaining tasks
Potentially a benchmark.
API changes
New interface etc., see Proposed solution.
Related Issues
TODO
Comment | File | Size | Author |
---|---|---|---|
#33 | routing-2057155-33.patch | 47.78 KB | pwolanin |
#26 | routing-2057155-26.patch | 48.13 KB | dawehner |
#26 | interdiff.txt | 9.35 KB | dawehner |
#23 | generate-2057155-23.patch | 37.13 KB | pwolanin |
#19 | generate-2057155-19.patch | 43.31 KB | pwolanin |
Comments
Comment #1
Damien Tournoud CreditAttribution: Damien Tournoud commentedI would rather see that happening.
Comment #2
pwolanin CreditAttribution: pwolanin commentedHave been having a long conversation about this w/ dawehner and before him with alexpott in IRC.
For me, hacking the 3rd param to generate() would be ok. alexpott didn't like it.
dawehner points out that in Symfony\Cmf they are already hacking/overriding the meaning of the params to generate() in ContentAwareGenerator, so we would be in less violation of the interface than that code.
Comment #3
pwolanin CreditAttribution: pwolanin commentedchanging title
Comment #4
pwolanin CreditAttribution: pwolanin commentedThis adds an overriding interface, marks some things deprecated, and tweaks url() to take path as an array
Comment #5
dawehnerSo we should not support $options['query'] on the longrun, but tell people to use parameters instead?
Comment #6
pwolanin CreditAttribution: pwolanin commented@dawehner - yes, probably so unless we want to handle the query string independently to avoid the Symfony feature(?) that seems to prevent you from having a path slug and query parameter with the same name.
Comment #7
tstoecklerAs @pwolanin pointed out in IRC (per @dawehner) the 'query' stuff is just insane. There's no way to generate the URL http:example.com/node/1?node=foo, for example.
On a more general note: If we're adding a separate interface anyway, what exactly is the benefit of hacking the existing function instead of providing a new one. I might be missing something but I literally see no benefit of that. Avoiding the 'query' madness would be only a nice side-effect of that.
Comment #8
pwolanin CreditAttribution: pwolanin commentedPatch changes direction a little based on converstation with Crell & msonnabaum in IRC. Let's not blow up the exisintg method signature, but add a new method.
From Crell, we are trying to meet the basic requirements:
The last would be handled by using this new code with a link generator for routes.
Comment #9
dawehner+1 for having a proper method to support options!
These changes should kind of be synced. Additional we nee d it on both l and url, right?
It feels like UrlGeneratorWithOptionsInterface would describe it better, what this interface is about. "Generator" in the context of routing has the potential for misunderstanding.
I guess we should start to use @inheritdoc directly?
We certainly have to test this new functionality. Peter, are you okay with helping on the tests?
Comment #10
pwolanin CreditAttribution: pwolanin commentedThe doxygen change to l() will be reverted in the next patch - that was left-over from the rejected changed to url()
Comment #11
pwolanin CreditAttribution: pwolanin commentedAdds tests and moves the interface name to UrlGeneratorWithOptionsInterface
Also, per discussion in IRC with dawhener and Crell, removes $parameters from being passed to getRouteByName() since the neither the Drupal implementation nor any symfony implementation look at them, they make no sesne being there in the interface (see getRoutesByName()) and they make the test mocking harder.
Comment #12
dawehnerI prefer the new name, as it is more descriptive.
oh right, this method was removed some time ago.
Sorry, but this needs an starting "\"
We could just fix the types here
This is just a copy and paste for no real reason ...
Lets add some readability by more empty lines. Note (even the other tests are wrong), the message is just shown, when something fails. Please revert the logic of the messages.
One potential follow up is to extend the test coverage to external URLs, which is not covered yet.
Comment #13
pwolanin CreditAttribution: pwolanin commented@dawehner - the generator doesn't handle external URLs, only absolute. the link generator would do that.
Other fixes made as suggested.
Comment #14
katbailey CreditAttribution: katbailey commentedThis looks pretty reasonable to me - can we not just call the interface UrlGeneratorInterface though? I mean, it's a different namespace, who cares that it supports options?
Also noticed some things about the test changes...
This sentence was referring to the fact that the params for getRouteByName and getRoutesByNames are slightly different (i.e. one takes a single name and the other takes an array of names) - it was not referring to the "parameters" param. And if we don't need the "parameters" param any more, let's not include it in the $return_map_values array and just pass an empty array in the foreach loop.
As for the "Incorrect URL generated" messages, it's not clear to me that they're adding any value at all - let's just leave them out?
Comment #15
dawehnerThe parameters will be marked as deprecated in CMF 1.2, see https://github.com/symfony-cmf/Routing/issues/78#issuecomment-22094967
+1 for not adding messages all over the place.
Comment #16
dawehnerWe seem to do that in quite some other places in core already.
Comment #17
pwolanin CreditAttribution: pwolanin commentedFine for me to use the same interface name if it's not confusing?
Comment #18
dawehnerI don't think that anyone will be confused when there are namespaces involved.
Comment #19
pwolanin CreditAttribution: pwolanin commentedupdated per suggestions
Comment #20
dawehnerThank you!
Comment #21
dawehnerMaybe this also needs some profiling.
Comment #22
pwolanin CreditAttribution: pwolanin commentedIt does need a simple DB query if the route has not been previously loaded - to the extent that we are using this in combination with access checks for rendering, I think it will be net faster.
Comment #23
pwolanin CreditAttribution: pwolanin commentedre-roll for conflicts due to a change in ShortcutSetController.php
Comment #24
alexpottTagging since this issue is changing an API and for the fact that this needs to be documented in the issue summary
Comment #25
dawehnerDone.
Comment #26
dawehnerAlex wondered why @inheritdoc is not used in some places, so let's inheritdoc in the places where we change things
Comment #26.0
dawehneradd issue summary.
Comment #27
pwolanin CreditAttribution: pwolanin commentedThe summary has been updated, and this change would make it a lot easier to finish #2047619: Add a link generator service for route-based links , so bumping to major
Comment #28
andypostSuppose a bit more flexibility is cheap
suppose better to make this optional to allow apply only static route list
Comment #29
dawehner@andypost
This is a good idea for a followup: #2070177: Allow to skip the the path processing in the url generator
Comment #30
dawehnerOpened a follow up for the base_path problem: #2070185: Unify global $base_path and the symfony base_url from the request context.
Comment #31
pwolanin CreditAttribution: pwolanin commented#26: routing-2057155-26.patch queued for re-testing.
Comment #33
pwolanin CreditAttribution: pwolanin commentedRe-roll for conflicts in 2 form classes where use statements and constructors changed.
Comment #34
pwolanin CreditAttribution: pwolanin commentedonly "Stalking Crell" for a +1 - I don't think we need any technical input.
Comment #35
webchickI'll admit I don't really understand the "bigger picture" that this is all leading to yet (despite pwolanin patiently trying to explain it to me; I think I might get it the third or fourth time :)), and I'm extremely concerned that it's going to push an initiative already wildly behind schedule even further behind — we need to be *very* critical about what we deem actual release-blocking issues at this point when we are adding far more of them per week than we are fixing, as is the current state of things.
However, this change itself is fairly straight-forward, so I don't think there's much harm in allowing it in; it simply makes this existing code consistent with the url() function. Tagging as an approved API change.
Here's my review:
Most of the patch is this.
I asked Peter about the nature of this change; basically, because the inheritance hierarchy shifts to extending from Symfony CMF's "VersatileGeneratorInterface" (silliest. name. ever.) which itself descends from *their* version of UrlGeneratorInterface, it makes sense to rename this, because it's effectively our own version of theirs. (I also think it's confusing to have two classes named the same thing that do different things, but as has been pointed out in other issues, namespaces are the differentiator there.)
It shouldn't affect module developers too badly, although I see it does require changes on some entity listings.
I inquired about this too; $parameters isn't used and is deprecated upstream, so we're just bringing our code inline.
$parameters and $options are very close synonyms, so initially I pushed back on this. But $parameters comes from Symfony CMF parlance (meaning either path slugs or query string arguments, as described below), and $options is the standard thing we use in Drupal to say "optional things". So I think this is ok.
(minor) This needs to be only one line long. Fixed in commit.
This change seems kinda weird to me. It seems like if we're getting rid of $parameters, we shouldn't need it in tests anymore ether. I don't really understand this part of the code though, but maybe this needs a follow-up?
Apart from that, not much to complain about.
Committed and pushed to 8.x. Thanks!
Comment #36
pwolanin CreditAttribution: pwolanin commentedchange notice: https://drupal.org/node/2072005
Comment #37
dawehner+1 for the change record.
Comment #38
Crell CreditAttribution: Crell commented/me inserts a +1 based on a read-through of #33.
Comment #39
Crell CreditAttribution: Crell commentedBelatedly, it would seem... :-)
Comment #40.0
(not verified) CreditAttribution: commentedadd an item to the solution