Follow-up to #2408371: Proxies of module interfaces don't work

Problem/Motivation

In #2408371: Proxies of module interfaces don't work we had to introduce ReflectionClass hack to ensure we could reset the singleton to avoid a memory leak.

Upstream now committed a ::reset method on the singleton, hence we can remove the hack again.

It was merged into Symfony 2.3 and upwards.

( https://github.com/symfony/symfony/pull/15110/files )

Proposed resolution

- Remove the hack

Remaining tasks

User interface changes

API changes

Data model changes

Beta phase evaluation

Reference: https://www.drupal.org/core/beta-changes
Issue category Task because nothing is broken
Issue priority Normal, because the hack works.
Prioritized changes The main goal of this issue is to remove a hack that was added as part of a critical, hence a follow-up change.
Disruption Not disruptive as no-one should store global state like singletons.

Comments

fabianx’s picture

Issue tags: -Performance, -needs profiling, -D8 Accelerate, -D8 critical triage deferred +Quickfix
fabianx’s picture

Assigned: fabianx » Unassigned
dawehner’s picture

Thank you for creating the issue!

Kazanir’s picture

The hack actually broke compatibility with HHVM's repo authoritative mode (i.e. their production-mode "no new code allowed" rules) because they don't allow Reflection to change accessibility in this mode:

Fatal error: We've already made many assumptions about private variables. You can't change accessibility in Whole Program mode in /tmp/hhvm-nginx/drupal/core/lib/Drupal/Core/File/MimeType/MimeTypeGuesser.php on line 111

dawehner’s picture

This is why we better try to remove the hack and update symfony ...

fabianx’s picture

Category: Task » Bug report
Priority: Normal » Major
Issue tags: +hhvm

I have no idea how to update Symfony, but now its a major bug ...

neclimdul’s picture

https://twitter.com/symfony/status/620658883716075520 should make it easier so we don't have to track a commit. After that is done I can roll a patch.

neclimdul’s picture

Status: Active » Needs work
StatusFileSize
new237.21 KB

Within hours... #2504967: Upgrade to Symfony 2.7.1 oh well.

2.7.2 excluding this mess. #2531796: Fix hiddeninput.exe in symfony/console. Does not contain the static fix because... I'm actually not sure what needs to be done.

jibran’s picture

Status: Needs work » Needs review
neclimdul’s picture

StatusFileSize
new238.51 KB
new1.3 KB

nm, that was pretty straightforward.

hussainweb’s picture

I am thinking this should be separate issues, so that review is easier (or at least separate patches?)

jibran’s picture

It's fine as it is because it's not a critical so no hurry.

Status: Needs review » Needs work

The last submitted patch, 10: update_symfony-2526412-10.patch, failed testing.

hussainweb’s picture

@jibran: This issue is not critical, but the Symfony update may be. I see there are a few security fixes from the changelog and we could stay up to date. This issue can then just deal with removing the hack and fix the tests (and not worry about a 200 kb patch file with unrelated, but necessary changes).

hussainweb’s picture

Status: Needs work » Needs review
StatusFileSize
new2.11 KB
new242.16 KB

Fixing the test. To review the actual changes pertinent to this issue, see the interdiff in this comment and the interdiff in #10. This is the reason I was asking for a different issue. Should we still create one?

neclimdul’s picture

StatusFileSize
new239.98 KB
new1.47 KB
new2.77 KB

hack-fix just has the fix. but really the previous interdiff covered it.

Fix tests. They where holding on to the instance but upstream unsets the instance not the property.

Status: Needs review » Needs work

The last submitted patch, 16: hack-fix.patch, failed testing.

hussainweb’s picture

@neclimdul: I think you deleted my patch in #15 by mistake (instead of hiding them?). That was the fix for the failing tests.

hussainweb’s picture

Status: Needs work » Needs review
StatusFileSize
new242.16 KB
new2.11 KB

I am just uploading it again for review. It is essentially the same fix but slightly different. Same filenames as in #15.

hussainweb’s picture

That's weird. It shows green but there was a random failure. The same patch in test job in #15 shows all tests passed. So, I think the patch is good for review.

dawehner’s picture

Status: Needs review » Reviewed & tested by the community

Looks fine for me!

jibran’s picture

Is it related?
Drupal\system\Tests\System\UncaughtExceptionTest 27 passes 4 exceptions

alexpott’s picture

Status: Reviewed & tested by the community » Needs work
+++ b/core/lib/Drupal/Core/File/MimeType/MimeTypeGuesser.php
@@ -100,21 +100,9 @@ protected function sortGuessers() {
+    // Reset state, so we store more and more services during test runs.

This comment looks incorrect... I don't think we want to store more and more services during test runs :)

re #22 nope - thats #2532434: UncaughtException test doesn't quite uncatch everything

neclimdul’s picture

Status: Needs work » Needs review
StatusFileSize
new821 bytes
new239.99 KB

Woops

Status: Needs review » Needs work

The last submitted patch, 24: update_symfony-2526412-24.patch, failed testing.

neclimdul’s picture

Status: Needs work » Needs review
StatusFileSize
new240.04 KB

hm... weird. I didn't pull before diff'ing so I guess there was a conflict. Here is a rebase, no change.

neclimdul’s picture

The conflict #2392559: Remove all uses of file_stream_wrapper_get_* and file_get_stream_wrappers

Directly diffing the patches:

 diff --git a/core/tests/Drupal/Tests/Core/File/MimeTypeGuesserTest.php b/core/tests/Drupal/Tests/Core/File/MimeTypeGuesserTest.php
-index 154c3ec..70287bf 100644
+index 9a712a6..6e3f0e8 100644
 --- a/core/tests/Drupal/Tests/Core/File/MimeTypeGuesserTest.php
 +++ b/core/tests/Drupal/Tests/Core/File/MimeTypeGuesserTest.php
-@@ -36,14 +36,18 @@ public function testSymfonyGuesserRegistration() {
+@@ -37,14 +37,18 @@ public function testSymfonyGuesserRegistration() {
      $container = new ContainerBuilder();
-     $container->set('file.mime_type.guesser', new MimeTypeGuesser());
+     $container->set('file.mime_type.guesser', new MimeTypeGuesser(new StreamWrapperManager()));
      MimeTypeGuesser::registerWithSymfonyGuesser($container);
 +    $symfony_guesser = SymfonyMimeTypeGuesser::getInstance();
      $guessers = $this->readAttribute($symfony_guesser, 'guessers');
@@ -452,7 +452,7 @@ index 154c3ec..70287bf 100644
      $count = count($guessers);
  
      $container = new ContainerBuilder();
-     $container->set('file.mime_type.guesser', new MimeTypeGuesser());
+     $container->set('file.mime_type.guesser', new MimeTypeGuesser(new StreamWrapperManager()));
      MimeTypeGuesser::registerWithSymfonyGuesser($container);
 +    $symfony_guesser = SymfonyMimeTypeGuesser::getInstance();
      $guessers = $this->readAttribute($symfony_guesser, 'guessers');
jibran’s picture

Status: Needs review » Reviewed & tested by the community

Back to RTBC.

hussainweb’s picture

+++ b/core/tests/Drupal/Tests/Core/File/MimeTypeGuesserTest.php
@@ -37,14 +37,18 @@ public function testSymfonyGuesserRegistration() {
+    $symfony_guesser = SymfonyMimeTypeGuesser::getInstance();

Should we add a comment explaining why we are calling getInstance() repeatedly?

In that vein, it seems like a code smell that a method called registerWithSymfonyGuesser also resets the SymfonyMimeTypeGuesser. I would even suggest renaming that method (but that could be in a follow-up, this patch contains Symfony updates as well).

PS I still think it would have been a good idea to split the Symfony update in another issue so that this could have been a simpler patch to review. I have created #2533360: Upgrade to Symfony 2.7.2. Feel free to close this one if you think this is done anyway.

hussainweb’s picture

If #2533360: Upgrade to Symfony 2.7.2 is handled separately, the patch in #26 becomes this.

EDIT: Hopefully, this is easier to review.

hussainweb’s picture

StatusFileSize
new2.83 KB

#2533360: Upgrade to Symfony 2.7.2 is in. I am reuploading the patch in #30 (which is basically the one I derived from #26) for review. My concerns in #29 still stand:

In that vein, it seems like a code smell that a method called registerWithSymfonyGuesser also resets the SymfonyMimeTypeGuesser. I would even suggest renaming that method.

Since the patch is essentially the same, I am leaving it at RTBC although I'd still like to consider the point above.

fabianx’s picture

#31 As we only do that once very early in Kernel bootstrap that should be fine.

The only case where it would have implications is where we boot a Kernel within a Kernel, in which case we could ignore that.

hussainweb’s picture

#32, okay. I was concerned with something in contrib calling that method. But if it is only early in the kernel bootstrap, it should be fine. However, if for some reason we boot kernel within a kernel, and a contrib is using that, this would be a problem. A very edge case scenario, I know.

dawehner’s picture

I don't think we need to document why we are calling things multiple times in the test.

alexpott’s picture

Title: Update Symfony components and remove Singleton hack » Remove Singleton hack in registerWithSymfonyGuesser

Fixing title

alexpott’s picture

Status: Reviewed & tested by the community » Fixed

Committed 2873e81 and pushed to 8.0.x. Thanks!

  • alexpott committed 2873e81 on 8.0.x
    Issue #2526412 by neclimdul, hussainweb, Fabianx: Remove Singleton hack...

Status: Fixed » Closed (fixed)

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