Directly support route annotations via Doctrine annotation reader.
This commit is contained in:
parent
f5eaff1961
commit
710a291950
3 changed files with 95 additions and 0 deletions
|
|
@ -27,6 +27,7 @@
|
|||
"cache/array-adapter": "^1.0",
|
||||
"cache/chain-adapter": "^1.0",
|
||||
"cache/redis-adapter": "^1.0",
|
||||
"doctrine/annotations": "^1.10",
|
||||
"duncan3dc/fork-helper": "^2.0",
|
||||
"friendsofphp/php-cs-fixer": "^2.0",
|
||||
"fzaninotto/faker": "^1.9",
|
||||
|
|
|
|||
31
src/Annotations/Route.php
Normal file
31
src/Annotations/Route.php
Normal file
|
|
@ -0,0 +1,31 @@
|
|||
<?php declare(strict_types=1);
|
||||
|
||||
namespace Benzine\Annotations;
|
||||
|
||||
use Doctrine\Common\Annotations\Annotation\Required;
|
||||
|
||||
/**
|
||||
* @Annotation
|
||||
*
|
||||
* @Target("METHOD")
|
||||
*/
|
||||
class Route
|
||||
{
|
||||
/** @var array */
|
||||
public array $methods = ['GET'];
|
||||
|
||||
/**
|
||||
* @Required
|
||||
* @var string
|
||||
*/
|
||||
public string $path;
|
||||
|
||||
/** @var string */
|
||||
public string $access = \Benzine\Router\Route::ACCESS_PUBLIC;
|
||||
|
||||
/** @var int */
|
||||
public int $weight = 100;
|
||||
|
||||
/** @var array */
|
||||
public array $domains = [];
|
||||
}
|
||||
|
|
@ -3,6 +3,8 @@
|
|||
namespace Benzine\Router;
|
||||
|
||||
use Cache\Adapter\Chain\CachePoolChain;
|
||||
use Doctrine\Common\Annotations\AnnotationReader;
|
||||
use Doctrine\Common\Annotations\AnnotationRegistry;
|
||||
use Monolog\Logger;
|
||||
use Slim\App;
|
||||
|
||||
|
|
@ -22,6 +24,67 @@ class Router
|
|||
$this->cachePoolChain = $cachePoolChain;
|
||||
}
|
||||
|
||||
public function loadRoutesFromAnnotations(
|
||||
array $controllerPaths,
|
||||
string $baseNamespace = null
|
||||
): void {
|
||||
AnnotationRegistry::registerLoader('class_exists');
|
||||
|
||||
$reader = new AnnotationReader();
|
||||
|
||||
foreach ($controllerPaths as $controllerPath) {
|
||||
foreach (new \RecursiveDirectoryIterator($controllerPath) as $controllerFile) {
|
||||
if ($controllerFile->isDot() || !$controllerFile->isFile() || !$controllerFile->isReadable()) {
|
||||
continue;
|
||||
}
|
||||
|
||||
$fileClassName = str_replace('.php', '', $controllerFile->getFilename());
|
||||
$expectedClasses = [
|
||||
$baseNamespace . '\\Controllers\\' . $fileClassName,
|
||||
'Benzine\\Controllers\\' . $fileClassName,
|
||||
];
|
||||
|
||||
foreach ($expectedClasses as $expectedClass) {
|
||||
if (!class_exists($expectedClass)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
$rc = new \ReflectionClass($expectedClass);
|
||||
if ($rc->isAbstract()) {
|
||||
continue;
|
||||
}
|
||||
|
||||
foreach ($rc->getMethods() as $method) {
|
||||
if (!$method->isPublic()) {
|
||||
continue;
|
||||
}
|
||||
|
||||
$routeAnnotation = $reader->getMethodAnnotation($method, \Benzine\Annotations\Route::class);
|
||||
if (!($routeAnnotation instanceof \Benzine\Annotations\Route)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
foreach($routeAnnotation->methods as $httpMethod) {
|
||||
$newRoute = new Route($this->logger);
|
||||
|
||||
$newRoute
|
||||
->setHttpMethod($httpMethod)
|
||||
->setRouterPattern('/' . ltrim($routeAnnotation->path, '/'))
|
||||
->setCallback($method->class . ':' . $method->name)
|
||||
->setWeight($routeAnnotation->weight);
|
||||
|
||||
foreach ($routeAnnotation->domains as $domain) {
|
||||
$newRoute->addValidDomain($domain);
|
||||
}
|
||||
|
||||
$this->addRoute($newRoute);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public function weighRoutes(): Router
|
||||
{
|
||||
$allocatedRoutes = [];
|
||||
|
|
|
|||
Loading…
Reference in a new issue