AgileTillIDie
AgileTillIDie

Reputation: 469

ZF2 service locator & dependency injection

The good people at Zend, and a number of bloggers, are recommending the new service locator/manager for ZF2, rather than its inbuilt Dependency Injection system.

My question is, is it possible/convenient to inject mock objects into a service? I have seen some slightly clumsy attempts to do this in the PHPUnit bootstrap of a module; but is there a way of using this service system that is as clean and convenient as, say, ZF1 + Yadif?

Upvotes: 9

Views: 3093

Answers (1)

Ocramius
Ocramius

Reputation: 25431

Yes, you can inject mock objects into a service. For an unit test, the service locator does not even come into play:

$service = new MyService($mockDependency);

If you are writing complex integration tests where you need to use the Service Locator to be configured with a graph of dependencies and mocks, you can setup something like what I am doing with my modules:

$serviceLocator   = ServiceManagerFactory::getServiceManager(); // see comment below
$dbConnectionMock = $this->getMock('My\Db\Connection');

$serviceLocator->setAllowOverride(true);
// replacing connection service with our fake one
$serviceLocator->setService('connection_service_name', $dbConnectionMock);

$service = $serviceLocator->get('service_that_uses_a_connection');

You can find an example of ServiceManagerFactory in DoctrineORMModule at https://github.com/doctrine/DoctrineORMModule/blob/0.7.0/tests/DoctrineORMModuleTest/Util/ServiceManagerFactory.php

This works assuming that service_that_uses_a_connection is instantiated by a factory that injects connection_service_name into it.

You can still use also Zend\Di if you prefer to, but it's not really needed in such cases.

Upvotes: 13

Related Questions