diff --git a/CHANGELOG.md b/CHANGELOG.md index 6fe5954d..74c39ca4 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,9 +1,13 @@ # Yii Dependency Injection Change Log -## 1.0.1 under development +## 1.0.2 under development - no changes in this release. +## 1.0.1 under development + +- Bug #293: Fix `ExtensibleService` normalization bug (yiiliveext) + ## 1.0.0 December 03, 2021 -- Initial release. \ No newline at end of file +- Initial release. diff --git a/src/Container.php b/src/Container.php index de684afd..5e2bd81a 100644 --- a/src/Container.php +++ b/src/Container.php @@ -584,7 +584,7 @@ private function addProviders(array $providers): void /** @var mixed $definition */ $definition = $this->definitions->get($id); if (!$definition instanceof ExtensibleService) { - $definition = new ExtensibleService($definition); + $definition = new ExtensibleService($definition, $id); $this->addDefinitionToStorage($id, $definition); } diff --git a/src/ExtensibleService.php b/src/ExtensibleService.php index af06a982..f770dca2 100644 --- a/src/ExtensibleService.php +++ b/src/ExtensibleService.php @@ -6,7 +6,7 @@ use Psr\Container\ContainerInterface; use Yiisoft\Definitions\Contract\DefinitionInterface; -use Yiisoft\Definitions\Helpers\Normalizer; +use Yiisoft\Di\Helpers\DefinitionNormalizer; /** * A wrapper for a service definition that allows registering extensions. @@ -25,6 +25,8 @@ final class ExtensibleService implements DefinitionInterface */ private $definition; + private string $id; + /** * @var callable[] */ @@ -33,9 +35,10 @@ final class ExtensibleService implements DefinitionInterface /** * @param mixed $definition Definition to allow registering extensions for. */ - public function __construct($definition) + public function __construct($definition, string $id) { $this->definition = $definition; + $this->id = $id; } /** @@ -59,7 +62,7 @@ public function addExtension(callable $closure): void public function resolve(ContainerInterface $container) { /** @var mixed $service */ - $service = Normalizer::normalize($this->definition)->resolve($container); + $service = DefinitionNormalizer::normalize($this->definition, $this->id)->resolve($container); foreach ($this->extensions as $extension) { /** @var mixed $result */ diff --git a/tests/Unit/ContainerTest.php b/tests/Unit/ContainerTest.php index 2e637557..cbffde53 100644 --- a/tests/Unit/ContainerTest.php +++ b/tests/Unit/ContainerTest.php @@ -1604,7 +1604,7 @@ public function testExtensibleServiceDefinition(): void { $config = ContainerConfig::create() ->withDefinitions([ - 'test' => new ExtensibleService([]), + 'test' => new ExtensibleService([], 'test'), ]); $this->expectException(InvalidConfigException::class); diff --git a/tests/Unit/ServiceProviderTest.php b/tests/Unit/ServiceProviderTest.php index f0293478..7ad93876 100644 --- a/tests/Unit/ServiceProviderTest.php +++ b/tests/Unit/ServiceProviderTest.php @@ -5,8 +5,10 @@ namespace Yiisoft\Di\Tests\Unit; use PHPUnit\Framework\TestCase; +use Psr\Container\ContainerInterface; use Yiisoft\Di\Container; use Yiisoft\Di\ContainerConfig; +use Yiisoft\Di\ServiceProviderInterface; use Yiisoft\Di\Tests\Support\Car; use Yiisoft\Di\Tests\Support\CarProvider; use Yiisoft\Di\Tests\Support\CarExtensionProvider; @@ -15,6 +17,7 @@ use Yiisoft\Di\Tests\Support\EngineInterface; use Yiisoft\Di\Tests\Support\EngineMarkOne; use Yiisoft\Di\Tests\Support\EngineMarkTwo; +use Yiisoft\Di\Tests\Support\MethodTestClass; use Yiisoft\Di\Tests\Support\NullCarExtensionProvider; use Yiisoft\Di\Tests\Support\SportCar; use Yiisoft\Definitions\Exception\InvalidConfigException; @@ -139,4 +142,36 @@ public function testExtensionReturnedNull(): void $this->assertInstanceOf(ColorRed::class, $container->get(Car::class)->getColor()); } + + public function testClassMethodsWithExtensible(): void + { + $config = ContainerConfig::create() + ->withDefinitions([ + 'method_test' => [ + 'class' => MethodTestClass::class, + 'setValue()' => [42], + ], + ]) + ->withProviders([ + new class () implements ServiceProviderInterface { + public function getDefinitions(): array + { + return []; + } + + public function getExtensions(): array + { + return [ + 'method_test' => static fn (ContainerInterface $container, MethodTestClass $class) => $class, + ]; + } + }, + ]); + + $container = new Container($config); + + /** @var MethodTestClass $object */ + $object = $container->get('method_test'); + $this->assertSame(42, $object->getValue()); + } }