forked from silverstripe/silverstripe-framework
-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
NEW: Allow specifying a factory to use for creating services.
A service factory can be used for creating instances where a non-trivial construction process is required. This is done by adding a `factory` key to the service definition.
- Loading branch information
Showing
6 changed files
with
128 additions
and
54 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,9 +1,13 @@ | ||
<?php | ||
|
||
require_once dirname(__FILE__) . '/InjectionCreator.php'; | ||
require_once dirname(__FILE__) . '/SilverStripeInjectionCreator.php'; | ||
require_once dirname(__FILE__) . '/ServiceConfigurationLocator.php'; | ||
require_once dirname(__FILE__) . '/SilverStripeServiceConfigurationLocator.php'; | ||
require_once FRAMEWORK_PATH . '/src/SilverStripe/Framework/Injector/Factory.php'; | ||
|
||
require_once __DIR__ . '/InjectionCreator.php'; | ||
require_once __DIR__ . '/SilverStripeInjectionCreator.php'; | ||
require_once __DIR__ . '/ServiceConfigurationLocator.php'; | ||
require_once __DIR__ . '/SilverStripeServiceConfigurationLocator.php'; | ||
|
||
use SilverStripe\Framework\Injector\Factory; | ||
|
||
/** | ||
* A simple injection manager that manages creating objects and injecting | ||
|
@@ -71,6 +75,7 @@ | |
* // type | ||
* // By default, singleton is assumed | ||
* | ||
* 'factory' => 'FactoryService' // A factory service to use to create instances. | ||
* 'construct' => array( // properties to set at construction | ||
* 'scalar', | ||
* '%$BeanId', | ||
|
@@ -94,25 +99,25 @@ | |
* | ||
* In addition to specifying the bindings directly in the configuration, | ||
* you can simply create a publicly accessible property on the target | ||
* class which will automatically be injected if the autoScanProperties | ||
* class which will automatically be injected if the autoScanProperties | ||
* option is set to true. This means a class defined as | ||
* | ||
* | ||
* <code> | ||
* class MyController extends Controller { | ||
* | ||
* | ||
* private $permissionService; | ||
* | ||
* | ||
* public setPermissionService($p) { | ||
* $this->permissionService = $p; | ||
* } | ||
* } | ||
* } | ||
* </code> | ||
* | ||
* | ||
* will have setPermissionService called if | ||
* | ||
* | ||
* * Injector::inst()->setAutoScanProperties(true) is called and | ||
* * A service named 'PermissionService' has been configured | ||
* | ||
* * A service named 'PermissionService' has been configured | ||
* | ||
* @author [email protected] | ||
* @package framework | ||
* @subpackage injector | ||
|
@@ -161,16 +166,18 @@ class Injector { | |
* @var boolean | ||
*/ | ||
private $autoScanProperties = false; | ||
|
||
/** | ||
* The object used to create new class instances | ||
* | ||
* Use a custom class here to change the way classes are created to use | ||
* a custom creation method. By default the InjectionCreator class is used, | ||
* which simply creates a new class via 'new', however this could be overridden | ||
* to use, for example, SilverStripe's Object::create() method. | ||
* The default factory used to create new instances. | ||
* | ||
* The {@link InjectionCreator} is used by default, which simply directly | ||
* creates objects. This can be changed to use a different default creation | ||
* method if desired. | ||
* | ||
* Each individual component can also specify a custom factory to use by | ||
* using the `factory` parameter. | ||
* | ||
* @var InjectionCreator | ||
* @var Factory | ||
*/ | ||
protected $objectCreator; | ||
|
||
|
@@ -190,7 +197,7 @@ public function __construct($config = null) { | |
); | ||
|
||
$this->autoProperties = array(); | ||
|
||
|
||
$creatorClass = isset($config['creator']) ? $config['creator'] : 'InjectionCreator'; | ||
$locatorClass = isset($config['locator']) ? $config['locator'] : 'ServiceConfigurationLocator'; | ||
|
@@ -215,7 +222,16 @@ public static function inst($config=null) { | |
} | ||
return self::$instance; | ||
} | ||
|
||
|
||
/** | ||
* Sets the default global injector instance. | ||
* | ||
* @param Injector $instance | ||
*/ | ||
public static function set_inst(Injector $instance) { | ||
self::$instance = $instance; | ||
} | ||
|
||
/** | ||
* Indicate whether we auto scan injected objects for properties to set. | ||
* | ||
|
@@ -226,17 +242,16 @@ public function setAutoScanProperties($val) { | |
} | ||
|
||
/** | ||
* Sets the object to use for creating new objects | ||
* Sets the default factory to use for creating new objects. | ||
* | ||
* @param InjectionCreator $obj | ||
* @param Factory $obj | ||
*/ | ||
public function setObjectCreator($obj) { | ||
public function setObjectCreator(Factory $obj) { | ||
$this->objectCreator = $obj; | ||
} | ||
|
||
/** | ||
* Accessor (for testing purposes) | ||
* @return InjectionCreator | ||
* @return Factory | ||
*/ | ||
public function getObjectCreator() { | ||
return $this->objectCreator; | ||
|
@@ -486,8 +501,9 @@ protected function instantiate($spec, $id=null, $type = null) { | |
$constructorParams = $spec['constructor']; | ||
} | ||
|
||
$object = $this->objectCreator->create($class, $constructorParams); | ||
|
||
$factory = isset($spec['factory']) ? $this->get($spec['factory']) : $this->getObjectCreator(); | ||
$object = $factory->create($class, $constructorParams); | ||
|
||
// figure out if we have a specific id set or not. In some cases, we might be instantiating objects | ||
// that we don't manage directly; we don't want to store these in the service cache below | ||
if (!$id) { | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,22 +1,18 @@ | ||
<?php | ||
|
||
use SilverStripe\Framework\Injector\Factory; | ||
|
||
/** | ||
* @package framework | ||
* @subpackage injector | ||
*/ | ||
class SilverStripeInjectionCreator implements Factory { | ||
|
||
class SilverStripeInjectionCreator { | ||
/** | ||
* | ||
* @param string $object | ||
* A string representation of the class to create | ||
* @param array $params | ||
* An array of parameters to be passed to the constructor | ||
*/ | ||
public function create($class, $params = array()) { | ||
public function create($class, array $params = array()) { | ||
$class = Object::getCustomClass($class); | ||
$reflector = new ReflectionClass($class); | ||
return $reflector->newInstanceArgs($params); | ||
|
||
return $params ? $reflector->newInstanceArgs($params) : $reflector->newInstance(); | ||
} | ||
} | ||
|
||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,19 @@ | ||
<?php | ||
|
||
namespace SilverStripe\Framework\Injector; | ||
|
||
/** | ||
* A factory which is used for creating service instances. | ||
*/ | ||
interface Factory { | ||
|
||
/** | ||
* Creates a new service instance. | ||
* | ||
* @param string $service The class name of the service. | ||
* @param array $params The constructor parameters. | ||
* @return object The created service instances. | ||
*/ | ||
public function create($service, array $params = array()); | ||
|
||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters