Merge pull request #17755 from owncloud/alias-container-alive

Add registerAlias method to shortcut interface registration #17714
This commit is contained in:
Thomas Müller 2015-07-24 13:11:32 +02:00
commit 1f8ee61006
4 changed files with 68 additions and 51 deletions

View File

@ -39,8 +39,6 @@ use OC\AppFramework\Middleware\Security\SecurityMiddleware;
use OC\AppFramework\Middleware\Security\CORSMiddleware;
use OC\AppFramework\Middleware\SessionMiddleware;
use OC\AppFramework\Utility\SimpleContainer;
use OC\AppFramework\Utility\TimeFactory;
use OC\AppFramework\Utility\ControllerMethodReflector;
use OCP\AppFramework\IApi;
use OCP\AppFramework\IAppContainer;
use OCP\AppFramework\Middleware;
@ -63,15 +61,9 @@ class DIContainer extends SimpleContainer implements IAppContainer {
$this['urlParams'] = $urlParams;
// aliases
$this->registerService('appName', function($c) {
return $c->query('AppName');
});
$this->registerService('webRoot', function($c) {
return $c->query('WebRoot');
});
$this->registerService('userId', function($c) {
return $c->query('UserId');
});
$this->registerAlias('appName', 'AppName');
$this->registerAlias('webRoot', 'WebRoot');
$this->registerAlias('userId', 'UserId');
/**
* Core services
@ -156,9 +148,8 @@ class DIContainer extends SimpleContainer implements IAppContainer {
return $this->getServer()->getJobList();
});
$this->registerService('OCP\\AppFramework\\Utility\\IControllerMethodReflector', function($c) {
return $c->query('ControllerMethodReflector');
});
$this->registerAlias('OCP\\AppFramework\\Utility\\IControllerMethodReflector', 'OC\AppFramework\Utility\ControllerMethodReflector');
$this->registerAlias('ControllerMethodReflector', 'OCP\\AppFramework\\Utility\\IControllerMethodReflector');
$this->registerService('OCP\\INavigationManager', function($c) {
return $this->getServer()->getNavigationManager();
@ -168,9 +159,10 @@ class DIContainer extends SimpleContainer implements IAppContainer {
return $this->getServer()->getPreviewManager();
});
$this->registerService('OCP\\IRequest', function($c) {
return $c->query('Request');
$this->registerService('OCP\\IRequest', function () {
return $this->getServer()->getRequest();
});
$this->registerAlias('Request', 'OCP\\IRequest');
$this->registerService('OCP\\ITagManager', function($c) {
return $this->getServer()->getTagManager();
@ -180,9 +172,9 @@ class DIContainer extends SimpleContainer implements IAppContainer {
return $this->getServer()->getTempManager();
});
$this->registerService('OCP\\AppFramework\\Utility\\ITimeFactory', function($c) {
return $c->query('TimeFactory');
});
$this->registerAlias('OCP\\AppFramework\\Utility\\ITimeFactory', 'OC\AppFramework\Utility\TimeFactory');
$this->registerAlias('TimeFactory', 'OCP\\AppFramework\\Utility\\ITimeFactory');
$this->registerService('OCP\\Route\\IRouter', function($c) {
return $this->getServer()->getRouter();
@ -245,14 +237,6 @@ class DIContainer extends SimpleContainer implements IAppContainer {
return new API($c['AppName']);
});
$this->registerService('Request', function($c) {
/** @var $c SimpleContainer */
/** @var $server SimpleContainer */
$server = $c->query('ServerContainer');
/** @var $server IServerContainer */
return $server->getRequest();
});
$this->registerService('Protocol', function($c){
if(isset($_SERVER['SERVER_PROTOCOL'])) {
return new Http($_SERVER, $_SERVER['SERVER_PROTOCOL']);
@ -318,18 +302,6 @@ class DIContainer extends SimpleContainer implements IAppContainer {
return $dispatcher;
});
/**
* Utilities
*/
$this->registerService('TimeFactory', function($c){
return new TimeFactory();
});
$this->registerService('ControllerMethodReflector', function($c) {
return new ControllerMethodReflector();
});
}

View File

@ -26,21 +26,28 @@
namespace OC\AppFramework\Utility;
use \OCP\AppFramework\QueryException;
use ReflectionClass;
use ReflectionException;
use Closure;
use Pimple\Container;
use OCP\AppFramework\QueryException;
use OCP\IContainer;
/**
* Class SimpleContainer
*
* SimpleContainer is a simple implementation of IContainer on basis of \Pimple
* SimpleContainer is a simple implementation of IContainer on basis of Pimple
*/
class SimpleContainer extends \Pimple\Container implements \OCP\IContainer {
class SimpleContainer extends Container implements IContainer {
/**
* @param \ReflectionClass $class the class to instantiate
* @return \stdClass the created class
* @param ReflectionClass $class the class to instantiate
* @return stdClass the created class
*/
private function buildClass(\ReflectionClass $class) {
private function buildClass(ReflectionClass $class) {
$constructor = $class->getConstructor();
if ($constructor === null) {
return $class->newInstance();
@ -67,20 +74,20 @@ class SimpleContainer extends \Pimple\Container implements \OCP\IContainer {
* If a parameter is not registered in the container try to instantiate it
* by using reflection to find out how to build the class
* @param string $name the class name to resolve
* @return \stdClass
* @return stdClass
* @throws QueryException if the class could not be found or instantiated
*/
private function resolve($name) {
$baseMsg = 'Could not resolve ' . $name . '!';
try {
$class = new \ReflectionClass($name);
$class = new ReflectionClass($name);
if ($class->isInstantiable()) {
return $this->buildClass($class);
} else {
throw new QueryException($baseMsg .
' Class can not be instantiated');
}
} catch(\ReflectionException $e) {
} catch(ReflectionException $e) {
throw new QueryException($baseMsg . ' ' . $e->getMessage());
}
}
@ -117,10 +124,10 @@ class SimpleContainer extends \Pimple\Container implements \OCP\IContainer {
* Created instance will be cached in case $shared is true.
*
* @param string $name name of the service to register another backend for
* @param \Closure $closure the closure to be called on service creation
* @param Closure $closure the closure to be called on service creation
* @param bool $shared
*/
public function registerService($name, \Closure $closure, $shared = true) {
public function registerService($name, Closure $closure, $shared = true) {
if (isset($this[$name])) {
unset($this[$name]);
}
@ -131,5 +138,17 @@ class SimpleContainer extends \Pimple\Container implements \OCP\IContainer {
}
}
/**
* Shortcut for returning a service from a service under a different key,
* e.g. to tell the container to return a class when queried for an
* interface
* @param string $alias the alias that should be registered
* @param string $target the target that should be resolved instead
*/
public function registerAlias($alias, $target) {
$this->registerService($alias, function (IContainer $container) use ($target) {
return $container->query($target);
});
}
}

View File

@ -30,6 +30,9 @@
// This means that they should be used by apps instead of the internal ownCloud classes
namespace OCP;
use Closure;
/**
* Class IContainer
*
@ -72,5 +75,15 @@ interface IContainer {
* @return void
* @since 6.0.0
*/
public function registerService($name, \Closure $closure, $shared = true);
public function registerService($name, Closure $closure, $shared = true);
/**
* Shortcut for returning a service from a service under a different key,
* e.g. to tell the container to return a class when queried for an
* interface
* @param string $alias the alias that should be registered
* @param string $target the target that should be resolved instead
* @since 8.2.0
*/
public function registerAlias($alias, $target);
}

View File

@ -153,6 +153,19 @@ class SimpleContainerTest extends \Test\TestCase {
$this->assertEquals('abc', $object->test);
}
public function testRegisterAliasParamter() {
$this->container->registerParameter('test', 'abc');
$this->container->registerAlias('test1', 'test');
$this->assertEquals('abc', $this->container->query('test1'));
}
public function testRegisterAliasService() {
$this->container->registerService('test', function() {
return 'abc';
});
$this->container->registerAlias('test1', 'test');
$this->assertEquals('abc', $this->container->query('test1'));
}
/**
* @expectedException \OCP\AppFramework\QueryException