protected function loadRouteForAction(Admin $admin, Action $action, RouteCollection $routeCollection)
 {
     $routingUrlPattern = $admin->getConfiguration()->routingUrlPattern;
     // routing pattern should contains {admin} and {action}
     if (strpos($routingUrlPattern, '{admin}') == -1 || strpos($routingUrlPattern, '{action}') == -1) {
         throw new Exception('Admin routing pattern should contains {admin} and {action} placeholder');
     }
     // route path by entity name and action name
     $path = str_replace('{admin}', $admin->getEntityPath(), $routingUrlPattern);
     $path = str_replace('{action}', $action->getName(), $path);
     // by default, generic controller
     $defaults = ['_controller' => $admin->getController() . ':' . $action->getName(), '_admin' => $admin->getName(), '_action' => $action->getName()];
     // by default, no requirements
     $requirements = [];
     // for delete and edit action, an id is required
     if (in_array($action, ['delete', 'edit'])) {
         $path .= '/{id}';
         $requirements = ['id' => '\\d+'];
     }
     // creating new route
     $route = new Route($path, $defaults, $requirements);
     $routeName = $admin->generateRouteName($action->getName());
     // set route to action
     $action->setRoute($routeName);
     // adding route to symfony collection
     $routeCollection->add($routeName, $route);
 }
 /**
  * Create an Action from configuration values
  *
  * @param $actionName
  * @param $actionConfiguration
  * @param Admin $admin
  * @return Action
  */
 protected function createActionFromConfig($actionName, $actionConfiguration, Admin $admin)
 {
     $resolver = new OptionsResolver();
     $resolver->setDefaults($this->getDefaultActionConfiguration($actionName));
     $actionConfiguration = $resolver->resolve($actionConfiguration);
     // guess title if not provided
     if (!$actionConfiguration['title']) {
         $actionConfiguration['title'] = $this->getDefaultActionTitle($admin->getName(), $actionName);
     }
     $action = new Action();
     $action->setName($actionName);
     $action->setTitle($actionConfiguration['title']);
     $action->setPermissions($actionConfiguration['permissions']);
     $action->setRoute($admin->generateRouteName($action->getName()));
     $action->setExport($actionConfiguration['export']);
     // adding fields items to actions
     foreach ($actionConfiguration['fields'] as $fieldName => $fieldConfiguration) {
         $field = new Field();
         $field->setName($fieldName);
         $field->setTitle($this->inflectString($fieldName));
         if (array_key_exists('length', $fieldConfiguration)) {
             $field->setLength($fieldConfiguration['length']);
         }
         $action->addField($field);
     }
     return $action;
 }
 /**
  * Forward to 404 if user is not allowed by configuration for an action
  *
  * @param Admin $admin
  */
 protected function forward404IfNotAllowed(Admin $admin)
 {
     $this->forward404Unless($this->getUser(), 'You must be logged to access to this url');
     // check permissions and actions
     $this->forward404Unless($admin->isActionGranted($admin->getCurrentAction()->getName(), $this->getUser()->getRoles()), 'User not allowed for action "' . $admin->getCurrentAction()->getName() . '"');
 }