Problem/Motivation
KernelTestBase, some tests and some unit tests currently work under the assumption that $this->container is a container builder instance.
This only works, because ContainerBuilder is both a Container and a ContainerBuilder.
However this is an internal implementation detail, which should not be relied upon.
In #2497243: Replace Symfony container with a Drupal one, stored in cache e.g. the Container is changed to always have a production-container and not only when it was loaded from disk.
While it would be possible to continue to run all tests with a container builder this is up to 2 min / 21 min slower => 10% slower and it also means we do not test under production circumstances.
Proposed resolution
- Decouple containerBuilder from container and ensure that things are properly named and used.
- Ensure that the ContainerBuilder is used for asking for definitions and for registering parameters on the fly
- Ensure that the Container is used for testing the system
Remaining tasks
- Fix it
User interface changes
- None
API changes
- Test only changes:
$this->containerBuilder is available in KernelTestBase, while $this->container should only be used as a container implementing IntrospectableContainerInterface.
Data model changes
- None
Beta phase evaluation
| Issue category | Bug because tests rely on internal behavior of the ContainerBuilder, so its misnamed. |
|---|---|
| Issue priority | Major because it blocks a critical. |
| Unfrozen changes | Unfrozen because it only changes tests. |
| Prioritized changes | The main goal of this issue is to reduce fragility, by uncoupling things that had been coupled. |
| Disruption | Potentially disruptive for contributed modules that rely on this behavior in KernelTestBase. |
| Comment | File | Size | Author |
|---|---|---|---|
| #21 | decouple_tests_from-2529516-21.patch | 9.19 KB | kostyashupenko |
| #5 | decouple_tests_from-2529516-5.patch | 10.89 KB | fabianx |
| #5 | interdiff.txt | 2.16 KB | fabianx |
Comments
Comment #1
fabianx commentedUhm, dawehner pointed out that KernelTestBase is potentially deprecated by #2304461: KernelTestBaseTNG™.
=> I tend to won't fix that and remove that chunk from the parent, postponing for now.
Comment #2
fabianx commentedWhile that is true, I tried to detangle it and the best compromise is still the attached patch, which makes it as clean as possible and which still improves KernelTestBase in making it more clean.
Comment #3
dawehner+1
The change in
core/tests/Drupal/Tests/Core/Cache/CacheTagsInvalidatorTest.php:18should be avoidable, given that its an API we work against.In case your container doens't support that, it has a bug.
It should be discouraged to be anything with the container builder, if possible. People might rely on it, even they should not. Let's document that
Datebase now is an unused use statement.
Comment #4
fabianx commented#3: We only use ContainerBuilder elsewhere in unit tests.
The IntrospectableContainerInterface only specifies:
setParameter: sets a parameter
... but the compiled container does also throw an Exception there and the ContainerBuilder() after compile was called ...
Should we add compile(), isFrozen(), etc. to support "compiling" the container?
Currently code would need to use:
new Container([], FALSE);
to be able to use setParameter() with my container, which you implemented for tests.
But that is an implementation detail ...
If controverse, I can remove here and leave this change to parent issue, where it probably makes more sense to discuss anyway.
Comment #5
fabianx commentedFixed the nits of #3 and removed potentially controverse part.
Will switch parent issue over to make container non-frozen by default, then Drupal can pass $frozen = TRUE in explicitly.
Comment #6
dawehnerWell, I know, but why? There is no reason. We always use
->set()which works fine. I'm just saying that its not needed to change this as part of this patch.Comment #7
fabianx commented#6: The part was completely removed and container made unfrozen by default.
Comment #8
dawehnerCan we document the container itself that its the compiled version of it?
Comment #9
fabianx commentedDiscussed and addressed #8 in IRC.
Comment #10
dawehnerThank you
needs though still CR
Comment #11
fabianx commentedAlex asked for a test for the bug and I was able to provide one only with rebuilding the container first with allowDump = TRUE in setUp then calling parent::setUp.
That pointed to my container in the parent issue to always dump - even when allowDump is explicitly FALSE.
Therefore I now take $this->allowDump into account and KernelTestBase can continue to use the ContainerBuilder for everything, so works as designed.
Not yet closing though, because I still think its all really 'interesting' behavior, but not critical to fix for the parent.
Comment #12
mgiffordWhy is this postponed? What are we waiting for?
Comment #13
fabianx commentedIt was postponed on the parent container issue - which is now in.
Thanks, @mgifford
Comment #20
mile23Patch from #9 no longer applies.
Comment #21
kostyashupenkoabout
ServiceProviderTest.phpit was changed few times and moved to tests folder https://github.com/drupal/drupal/commit/20a080288f7342d6fecff46bf7c12286...
so need review.
Comment #25
andypost