-
-
Notifications
You must be signed in to change notification settings - Fork 9.6k
[DI] Inline trivial private servives #23674
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
Conversation
* | ||
* @return bool | ||
*/ | ||
private function isTrivialInstance(Definition $definition) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Instead of this method name (isTrivialInstance()
) which feels like an internal detail, maybe we could use a more generic and future-proof name, such as canBeInlined()
?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
actually, as a private method, this is an internal detail :)
more importantly, the "trivial" is important here. It's not only that the instantiation can be inlined, it's also that the instantiation is trivial, this meaning that it mostly a simple new Foo()
.
More complex instantiation would also be inlineable (eg Factory::create(new Foo($this->get('bar')))
), but we don't want to inline those (we need a limit, being trivial is the one, for what it means (it only means whatever logic is in the method, see patch :) .)
In this respect, canBeInlined()
would be confusing.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
OK. My reasoning was that in the future, if you add new optimizations, the code will complicate a lot (if ($this->isTrivialInstance() || $this->isServiceLengthSmall() || $this->isDevEnvironment())
vs if ($this->canBeInlined())
and then adding more optimizations to that method).
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Well, if in the future we decide that more cases would benefit from this, we could still change the defining of what a trivial service is. And we can decide to rename the method if actually necessary.
canBeInlined
has another reason to be confusing: we have another concept called inlining
in the component (although a bit related)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can it actually be done in 3.4 ? Private services can still be accessed there, even though it is deprecated. I think your code breaks it.
} | ||
|
||
foreach ($definition->getArguments() as $arg) { | ||
if (!$arg || ($arg instanceof Reference && 'service_container' !== (string) $arg)) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
why the special case about referencing the container ?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
because this considers new Foo($this)
a trivial case ($this being the dumped container reference of course)
52aa321
to
f2749d7
Compare
f2749d7
to
24ee277
Compare
Hum right, rebased now |
24ee277
to
acf0d37
Compare
if (!$v || ($v instanceof Reference && 'service_container' !== (string) $v)) { | ||
continue; | ||
} | ||
if (!\is_scalar($v) || $this->dumpValue($v) !== $this->dumpValue($v, false)) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
be careful. null
is not a scalar, but it is a trivial value
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
null
will be handled by if (!$v
just above
1017368
to
f96fc19
Compare
@@ -125,6 +125,7 @@ | |||
$container | |||
->register('factory_simple', 'SimpleFactoryClass') | |||
->addArgument('foo') | |||
->setDeprecated(true) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
added this to have at least one private service that cannot be inlined.
fabbot failure is false positive, PR ready. |
f96fc19
to
515b014
Compare
@@ -38,7 +38,7 @@ public function isProxyCandidate(Definition $definition); | |||
* | |||
* @return string | |||
*/ | |||
public function getProxyFactoryCode(Definition $definition, $id, $methodName); | |||
public function getProxyFactoryCode(Definition $definition, $id, $methodName = null); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
spotted meanwhile: not allowing null breaks our forward compat policy (being able to upgrade a 3.4 code so that it works with 4.0)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
are you sure about that ? Implementors are allowed to add = null
for their argument even if the interface does not have it (the opposite is false).
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
sure, that's even what we planned for in 3.4, see
https://github.com/symfony/symfony/blob/3.4/src/Symfony/Component/DependencyInjection/LazyProxy/PhpDumper/DumperInterface.php#L41
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Well, I mean, we can make the argument required in 4.0. It will not forbid making 3.4 code compatible with 4.x (you need to make the argument optional in your implementation to support the 3.4 interface, but this does not forbid 4.x to make it required in the interface)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
indeed, dunno why I did that now :) reverted
515b014
to
cb196d8
Compare
cb196d8
to
0caed93
Compare
Thank you @nicolas-grekas. |
This PR was merged into the 4.0-dev branch. Discussion ---------- [DI] Inline trivial private servives | Q | A | ------------- | --- | Branch? | 4.0 | Bug fix? | no | New feature? | yes | BC breaks? | no | Deprecations? | no | Tests pass? | yes | Fixed tickets | - | License | MIT | Doc PR | - There is no need to generate a method when the instantiation is just as verbose as calling that method. Commits ------- 0caed93 [DI] Inline trivial private servives
There is no need to generate a method when the instantiation is just as verbose as calling that method.