Comments

stefanos.petrakis created an issue. See original summary.

stefanos.petrakis’s picture

Status: Active » Needs review
StatusFileSize
new1.64 KB

Here is the patch.

longwave’s picture

Status: Needs review » Needs work

Thanks for working on this!

I think you need to implement ContainerFactoryPluginInterface to inject the killswitch service from the container when the plugin is instantiated - we don't have autowiring yet, unfortunately.

+++ b/core/modules/language/src/Plugin/LanguageNegotiation/LanguageNegotiationBrowser.php
@@ -25,6 +26,23 @@ class LanguageNegotiationBrowser extends LanguageNegotiationMethodBase {
+  public function __construct(KillSwitch $killSwitch) {
+    $this->killSwitch = $killSwitch;

While it looks awkward Drupal uses snake_case for all variables, except member variables which use camelCase, so this should be:

public function __construct(KillSwitch $kill_switch) {
  $this->killSwitch = $kill_switch;
stefanos.petrakis’s picture

Status: Needs work » Needs review
StatusFileSize
new1.8 KB
new2.3 KB

Many thanks for double checking, here is the better version of the patch.

longwave’s picture

Status: Needs review » Reviewed & tested by the community

Looks great now!

plach’s picture

Version: 8.9.x-dev » 9.1.x-dev

Looks good to me as well, however this is now a 9.1.x issue (that might still be considered for backporting).

plach’s picture

Status: Reviewed & tested by the community » Needs work

Spoke with @xjm about this: to be able to safely backport this to 8.9, we need to add a BC layer for the constructor param and a deprecation error stating that the param is optional in 9.0 and required in 10.0. See FileTranslation::__construct() for an example. The unit test should cover also the deprecation, so we could add the unit test class here and the actual test coverage in #3130104: Add unit test coverage for LanguageNegotiationBrowser.

stefanos.petrakis’s picture

Status: Needs work » Needs review
StatusFileSize
new3 KB
new4.55 KB

Thanks for all the infos @plach.

I guessed first off we would need a CR for the deprecation error, here is a draft => https://www.drupal.org/node/3132773

I updated the constructor and implemented a single deprecation check test.

Back to review mode.

andypost’s picture

It could be done backward compatible way like #3126127-11: Fix LanguageNegotiationMethodInterface::getLangcode() result docblock

As negotiator is plugin then setter injection instead of constructor one makes the change future-proof.
Tldr kill switch will change in session related issues so better not introduce constructor argument which could be deprecated

plach’s picture

Good point, that's probably the reason why DI wasn't used in the first place...

stefanos.petrakis’s picture

Status: Needs review » Needs work

Thanks a lot @andypost for the feedback, very enlightening. Will pick this up again.

stefanos.petrakis’s picture

Status: Needs work » Needs review
StatusFileSize
new2.33 KB

This is a different implementation than what was proposed so far, therefore:

Asking the bot.

andypost’s picture

Great! Btw I find this setter useless as you can access class's property directly.

CR maybe required... Because plugin now implements the new interface

plach’s picture

Status: Needs review » Needs work

Thanks!

  1. +++ b/core/modules/language/src/Plugin/LanguageNegotiation/LanguageNegotiationBrowser.php
    @@ -25,6 +28,29 @@ class LanguageNegotiationBrowser extends LanguageNegotiationMethodBase {
    +  private $pageCacheKillSwitch;
    

    Usage of private visibility is controversial and whether it should be considered ok is still being decided, so let's make this protected to avoid discussions down the line.

  2. +++ b/core/modules/language/src/Plugin/LanguageNegotiation/LanguageNegotiationBrowser.php
    @@ -25,6 +28,29 @@ class LanguageNegotiationBrowser extends LanguageNegotiationMethodBase {
    +  public function setPageCacheKillSwitch(KillSwitch $page_cache_kill_switch) {
    

    I agree with Andy: given that we can access private/protected members from a static method, the setter is not needed. It would be if this were a service exploiting setter injection via the container.

stefanos.petrakis’s picture

Status: Needs work » Needs review
StatusFileSize
new2.13 KB
new1.3 KB

One more try here, thanks for the feedback and patience.
@plach, point 1. is definitely an invitation for more questions :) Any links to where I can read some more on this controversy? I am coming from a place in my mind where I would favor private over protected.

This kind of injection - neither a setter nor a constructor one - does it go by a specific name?

andypost’s picture

It looks RTBC for me

andypost’s picture

Status: Needs review » Reviewed & tested by the community
plach’s picture

Looks good to me as well. I'm not sure we'd normally need a CR for such a change, given that plugins are not public API, but since we already have one, can we update it?

  • plach committed b152620 on 9.1.x
    Issue #3130438 by stefanos.petrakis, andypost, longwave: Inject...

  • plach committed f32f77f on 9.0.x
    Issue #3130438 by stefanos.petrakis, andypost, longwave: Inject...

  • plach committed f520ad6 on 8.9.x
    Issue #3130438 by stefanos.petrakis, andypost, longwave: Inject...
plach’s picture

Status: Reviewed & tested by the community » Fixed

Committed b152620 and pushed to 9.1.x and friends. Thanks!

plach’s picture

Any links to where I can read some more on this controversy? I am coming from a place in my mind where I would favor private over protected.

I cannot find the issue I had in mind, asked in Slack, I will post it here once I get a reply.

plach’s picture

stefanos.petrakis’s picture

@plach, @andypost, @longwave: Many thanks! I will update the CR accordingly and post back here a short update.

andypost’s picture

I think related exactly about it

andypost’s picture

Maybe CR needs better wording, like "service explicitly depends on policy"

Because it's plugin it should not be created directly - there's plugin manager

But implementation of interface should be mentioned

plach’s picture

@stefanos.petrakis:

The oldest issue I could find discussing private visibility is #2081945: [Policy, no patch] Reintroduce 'private' visibility to object-oriented code., a related discussion then took place at #3019332: Use final to define classes that are NOT extension points.

plach’s picture

This kind of injection - neither a setter nor a constructor one - does it go by a specific name?

Not that I know of. If it were me, I'd probably call it "static factory method injection" ;)

andypost’s picture

stefanos.petrakis’s picture

Just updated the CR to reflect the committed changes and taking comments into consideration.

According to https://www.drupal.org/contributor-tasks/draft-change-record, one should now set this issue to "Needs review", but I think we are past this point. But, the CR still needs some review I guess before it's published. Suggestions?

andypost’s picture

Looks great and could be published!

stefanos.petrakis’s picture

Issue summary: View changes
stefanos.petrakis’s picture

All right then, just published the CR.

andypost’s picture

+++ b/core/modules/language/src/Plugin/LanguageNegotiation/LanguageNegotiationBrowser.php
@@ -25,6 +28,22 @@ class LanguageNegotiationBrowser extends LanguageNegotiationMethodBase {
+  public static function create(ContainerInterface $container, array $configuration, $plugin_id, $plugin_definition) {
+    $instance = new static();

Just found that it missing unittest coverage #3130104: Add unit test coverage for LanguageNegotiationBrowser

This plugin does not use plugin arguments ($configuration, $plugin_id, $plugin_definition) which are not passed to constructor now, the pointed issue should catch and solve it

Status: Fixed » Closed (fixed)

Automatically closed - issue fixed for 2 weeks with no activity.