Chris@0
|
1 <?php
|
Chris@0
|
2
|
Chris@0
|
3 namespace Drupal\Core\Access;
|
Chris@0
|
4
|
Chris@0
|
5 use Drupal\Core\Controller\ControllerResolverInterface;
|
Chris@0
|
6 use Drupal\Core\Routing\Access\AccessInterface as RoutingAccessInterface;
|
Chris@0
|
7 use Drupal\Core\Routing\RouteMatchInterface;
|
Chris@0
|
8 use Drupal\Core\Session\AccountInterface;
|
Chris@0
|
9 use Symfony\Component\Routing\Route;
|
Chris@0
|
10
|
Chris@0
|
11 /**
|
Chris@0
|
12 * Defines an access checker that allows specifying a custom method for access.
|
Chris@0
|
13 *
|
Chris@0
|
14 * You should only use it when you are sure that the access callback will not be
|
Chris@0
|
15 * reused. Good examples in core are Edit or Toolbar module.
|
Chris@0
|
16 *
|
Chris@0
|
17 * The method is called on another instance of the controller class, so you
|
Chris@0
|
18 * cannot reuse any stored property of your actual controller instance used
|
Chris@0
|
19 * to generate the output.
|
Chris@0
|
20 */
|
Chris@0
|
21 class CustomAccessCheck implements RoutingAccessInterface {
|
Chris@0
|
22
|
Chris@0
|
23 /**
|
Chris@0
|
24 * The controller resolver.
|
Chris@0
|
25 *
|
Chris@0
|
26 * @var \Drupal\Core\Controller\ControllerResolverInterface
|
Chris@0
|
27 */
|
Chris@0
|
28 protected $controllerResolver;
|
Chris@0
|
29
|
Chris@0
|
30 /**
|
Chris@0
|
31 * The arguments resolver.
|
Chris@0
|
32 *
|
Chris@0
|
33 * @var \Drupal\Core\Access\AccessArgumentsResolverFactoryInterface
|
Chris@0
|
34 */
|
Chris@0
|
35 protected $argumentsResolverFactory;
|
Chris@0
|
36
|
Chris@0
|
37 /**
|
Chris@0
|
38 * Constructs a CustomAccessCheck instance.
|
Chris@0
|
39 *
|
Chris@0
|
40 * @param \Drupal\Core\Controller\ControllerResolverInterface $controller_resolver
|
Chris@0
|
41 * The controller resolver.
|
Chris@0
|
42 * @param \Drupal\Core\Access\AccessArgumentsResolverFactoryInterface $arguments_resolver_factory
|
Chris@0
|
43 * The arguments resolver factory.
|
Chris@0
|
44 */
|
Chris@0
|
45 public function __construct(ControllerResolverInterface $controller_resolver, AccessArgumentsResolverFactoryInterface $arguments_resolver_factory) {
|
Chris@0
|
46 $this->controllerResolver = $controller_resolver;
|
Chris@0
|
47 $this->argumentsResolverFactory = $arguments_resolver_factory;
|
Chris@0
|
48 }
|
Chris@0
|
49
|
Chris@0
|
50 /**
|
Chris@0
|
51 * Checks access for the account and route using the custom access checker.
|
Chris@0
|
52 *
|
Chris@0
|
53 * @param \Symfony\Component\Routing\Route $route
|
Chris@0
|
54 * The route.
|
Chris@0
|
55 * @param \Drupal\Core\Routing\RouteMatchInterface $route_match
|
Chris@0
|
56 * The route match object to be checked.
|
Chris@0
|
57 * @param \Drupal\Core\Session\AccountInterface $account
|
Chris@0
|
58 * The account being checked.
|
Chris@0
|
59 *
|
Chris@0
|
60 * @return \Drupal\Core\Access\AccessResultInterface
|
Chris@0
|
61 * The access result.
|
Chris@0
|
62 */
|
Chris@0
|
63 public function access(Route $route, RouteMatchInterface $route_match, AccountInterface $account) {
|
Chris@17
|
64 try {
|
Chris@17
|
65 $callable = $this->controllerResolver->getControllerFromDefinition($route->getRequirement('_custom_access'));
|
Chris@17
|
66 }
|
Chris@17
|
67 catch (\InvalidArgumentException $e) {
|
Chris@17
|
68 // The custom access controller method was not found.
|
Chris@17
|
69 throw new \BadMethodCallException(sprintf('The "%s" method is not callable as a _custom_access callback in route "%s"', $route->getRequirement('_custom_access'), $route->getPath()));
|
Chris@17
|
70 }
|
Chris@17
|
71
|
Chris@0
|
72 $arguments_resolver = $this->argumentsResolverFactory->getArgumentsResolver($route_match, $account);
|
Chris@0
|
73 $arguments = $arguments_resolver->getArguments($callable);
|
Chris@0
|
74
|
Chris@0
|
75 return call_user_func_array($callable, $arguments);
|
Chris@0
|
76 }
|
Chris@0
|
77
|
Chris@0
|
78 }
|