diff --git a/src/Symfony/Component/DependencyInjection/Container.php b/src/Symfony/Component/DependencyInjection/Container.php index 3cfdd616c5a17..7bd1a8749f8af 100644 --- a/src/Symfony/Component/DependencyInjection/Container.php +++ b/src/Symfony/Component/DependencyInjection/Container.php @@ -191,9 +191,7 @@ public function set($id, $service, $scope = self::SCOPE_CONTAINER) $this->scopedServices[$scope][$id] = $service; } - if (isset($this->aliases[$id])) { - unset($this->aliases[$id]); - } + unset($this->aliases[$id], $this->methodMap[$id]); $this->services[$id] = $service; @@ -222,6 +220,7 @@ public function has($id) for ($i = 2;;) { if ('service_container' === $id || isset($this->aliases[$id]) + || isset($this->methodMap[$id]) || isset($this->services[$id]) ) { return true; @@ -357,15 +356,20 @@ public function initialized($id) */ public function getServiceIds() { - $ids = array(); + $ids = array_keys($this->methodMap + $this->services); + $reversedMethodMap = array_change_key_case(array_flip($this->methodMap), \CASE_LOWER); foreach (get_class_methods($this) as $method) { if (preg_match('/^get(.+)Service$/', $method, $match)) { - $ids[] = self::underscore($match[1]); + if (isset($reversedMethodMap[$methodLc = 'get'.strtolower($match[1]).'service'])) { + $ids[] = $reversedMethodMap[$methodLc]; + } else { + $ids[] = self::underscore($match[1]); + } } } $ids[] = 'service_container'; - return array_unique(array_merge($ids, array_keys($this->services))); + return array_values(array_unique($ids)); } /** diff --git a/src/Symfony/Component/DependencyInjection/Tests/ContainerTest.php b/src/Symfony/Component/DependencyInjection/Tests/ContainerTest.php index 013ee82316084..a3f4178407779 100644 --- a/src/Symfony/Component/DependencyInjection/Tests/ContainerTest.php +++ b/src/Symfony/Component/DependencyInjection/Tests/ContainerTest.php @@ -123,11 +123,11 @@ public function testGetServiceIds() $sc = new Container(); $sc->set('foo', $obj = new \stdClass()); $sc->set('bar', $obj = new \stdClass()); - $this->assertEquals(array('service_container', 'foo', 'bar'), $sc->getServiceIds(), '->getServiceIds() returns all defined service ids'); + $this->assertEquals(array('foo', 'bar', 'service_container'), $sc->getServiceIds(), '->getServiceIds() returns all defined service ids'); $sc = new ProjectServiceContainer(); $sc->set('foo', $obj = new \stdClass()); - $this->assertEquals(array('scoped', 'scoped_foo', 'scoped_synchronized_foo', 'inactive', 'bar', 'foo_bar', 'foo.baz', 'circular', 'throw_exception', 'throws_exception_on_service_configuration', 'service_container', 'foo'), $sc->getServiceIds(), '->getServiceIds() returns defined service ids by getXXXService() methods, followed by service ids defined by set()'); + $this->assertEquals(array('mapped_method_id', 'mapped_method_id2', 'foo', 'scoped', 'scoped_foo', 'scoped_synchronized_foo', 'inactive', 'bar', 'foo_bar', 'foo.baz', 'circular', 'throw_exception', 'throws_exception_on_service_configuration', 'service_container'), $sc->getServiceIds(), '->getServiceIds() returns defined service ids resolved from methods, followed by service ids defined by set()'); } public function testSet() @@ -202,6 +202,7 @@ public function testGet() $this->assertEquals($sc->__foo_bar, $sc->get('foo_bar'), '->get() returns the service if a get*Method() is defined'); $this->assertEquals($sc->__foo_baz, $sc->get('foo.baz'), '->get() returns the service if a get*Method() is defined'); $this->assertEquals($sc->__foo_baz, $sc->get('foo\\baz'), '->get() returns the service if a get*Method() is defined'); + $this->assertEquals(new \stdClass(), $sc->get('mapped_method_id2'), '->get() returns the service if a method is mapped custom'); $sc->set('bar', $bar = new \stdClass()); $this->assertEquals($bar, $sc->get('bar'), '->get() prefers to return a service defined with set() than one defined with a getXXXMethod()'); @@ -234,7 +235,7 @@ public function testGetThrowServiceNotFoundException() $this->fail('->get() throws an Symfony\Component\DependencyInjection\Exception\ServiceNotFoundException if the key does not exist'); } catch (\Exception $e) { $this->assertInstanceOf('Symfony\Component\DependencyInjection\Exception\ServiceNotFoundException', $e, '->get() throws an Symfony\Component\DependencyInjection\Exception\ServiceNotFoundException if the key does not exist'); - $this->assertEquals('You have requested a non-existent service "bag". Did you mean one of these: "bar", "baz"?', $e->getMessage(), '->get() throws an Symfony\Component\DependencyInjection\Exception\ServiceNotFoundException with some advices'); + $this->assertEquals('You have requested a non-existent service "bag". Did you mean one of these: "baz", "bar"?', $e->getMessage(), '->get() throws an Symfony\Component\DependencyInjection\Exception\ServiceNotFoundException with some advices'); } } @@ -266,6 +267,7 @@ public function testHas() $this->assertTrue($sc->has('foo_bar'), '->has() returns true if a get*Method() is defined'); $this->assertTrue($sc->has('foo.baz'), '->has() returns true if a get*Method() is defined'); $this->assertTrue($sc->has('foo\\baz'), '->has() returns true if a get*Method() is defined'); + $this->assertTrue($sc->has('mapped_method_id'), '->has() returns true if a method is mapped custom'); } public function testInitialized() @@ -611,6 +613,10 @@ public function __construct() $this->__foo_bar = new \stdClass(); $this->__foo_baz = new \stdClass(); $this->synchronized = false; + $this->methodMap = array( + 'mapped_method_id' => 'get_CamelcasedMethodEndingWith_Service', + 'mapped_method_id2' => '_get_by_different_convention', + ); $this->aliases = array('alias' => 'bar'); } @@ -651,6 +657,16 @@ protected function getInactiveService() throw new InactiveScopeException('request', 'request'); } + protected function get_camelcasedmethodendingwith_Service() + { + return new \stdClass(); + } + + protected function _get_by_different_convention() + { + return new \stdClass(); + } + protected function getBarService() { return $this->__bar;