Last active
October 7, 2016 06:53
-
-
Save alezhu/d9973d1667e67a9a47ba851050fa24f8 to your computer and use it in GitHub Desktop.
Lumen middleware for check contoller methods availability via Doctrine annotation
This file contains hidden or 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
<?php | |
/* | |
in app.php add | |
$app->routeMiddleware([ | |
'action' =>\App\Http\Middleware\ActionMiddleware::class, | |
]); | |
AnnotationRegistry::registerLoader('class_exists'); | |
in route add something like | |
$app->group([ | |
'prefix' => 'api', | |
'middleware' => ['action'], | |
'namespace' => 'App\Http\Controllers', | |
], function () use ($app) { | |
... | |
}); | |
in controller add somethiong like | |
/** | |
* @return \Symfony\Component\HttpFoundation\Response | |
* | |
* @CheckAction(Action::ADMIN_USER_READ) | |
* | |
* / | |
public function index() .... | |
*/ | |
namespace App\Http\Middleware; | |
use App\Core\CheckAction; | |
use App\Models\ActionService; | |
use Auth; | |
use Closure; | |
use Doctrine\Common\Annotations\AnnotationReader; | |
use Doctrine\Common\Annotations\CachedReader; | |
use Doctrine\Common\Cache\FilesystemCache; | |
use Illuminate\Http\Request; | |
use Log; | |
/** | |
* Class ActionMiddleware | |
* @package App\Http\Middleware | |
*/ | |
class ActionMiddleware | |
{ | |
private $reader; | |
/** | |
* ActionMiddleware constructor. | |
*/ | |
public function __construct() | |
{ | |
if(empty(env('APP_DEBUG'))) { | |
$this->reader = new CachedReader( | |
new AnnotationReader(), | |
new FilesystemCache(app()->storagePath()), | |
$debug = true); | |
} else { | |
$this->reader = new AnnotationReader(); | |
} | |
AnnotationReader::addGlobalIgnoredName('dummy'); | |
AnnotationReader::addGlobalIgnoredName('action'); | |
} | |
/** | |
* Handle an incoming request. | |
* | |
* @param \Illuminate\Http\Request $request | |
* @param \Closure $next | |
* @param string $action | |
* @return mixed | |
*/ | |
public function handle(Request $request, Closure $next, $action = null) | |
{ | |
/** @var array $route */ | |
$route = $request->route(); | |
if (!empty($route) && is_array($route) && count($route) > 2) { | |
$uses = $route[1]['uses']; | |
if (!empty($uses) && !($uses instanceof Closure)) { | |
list($controller, $method) = explode('@', $uses); | |
$refMeth = new \ReflectionMethod($controller, $method); | |
$checkAction = $this->reader->getMethodAnnotation($refMeth, CheckAction::class); | |
if (!is_null($checkAction)) { | |
$user = Auth::user(); | |
if ($user && !ActionService::allowForUser($checkAction->value, $user)) { | |
/** @var Request $request */ | |
Log::alert('Access denied:', ['user' => Auth::user(), 'action' => $action, 'url' => $request->fullUrl()]); | |
return error2response(4, "Нет прав"); | |
} | |
} | |
} | |
} | |
return $next($request); | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment