0

How to setup entity access correctly?

i have entity:

/**
 * @ContentEntityType(
 *   id = "test_entity",
 *   bla... let me know if you need detail of this
 *     "route_provider" = { "admin" = "Drupal\test_entity\Entity\TestEntityRouteProvider" },
 *   bla... let me know if you need detail of this
 */

and class TestEntityRouteProvider extends AdminHtmlRouteProvider implements EntityRouteProviderInterface with getRoutes as follow:

$parameters = ['target_type' => 'test_entity_type', 'target_id' => ['type' => 'entity:{test_entity}']];

$route = (new Route('/admin/testing/my-entity/{test_entity}'))
         ->addDefaults([
           '_controller' => '\Drupal\test_entity\Controller\TestEntityViewController::view',
           '_title_callback' => '\Drupal\test_entity\Controller\TestEntityViewController::title',
         ])
         ->setOption('parameters', $parameters)
         ->setRequirement('_entity_access', 'test_entity.view');

$route_collection->add('entity.test_entity.canonical', $route);

i read comments in: EntityAccessCheck:Access, it said:

  /**
   * ... dynamic entity type:
   * example.route:
   *   path: foo/{entity_type}/{example}
   *   requirements:
   *     _entity_access: example.delete
   *   options:
   *     parameters:
   *       example:
   *         type: entity:{entity_type}

question: is my $parameter in class TestEntityRouteProvider correct? i'm not sure if i follow the instruction in comment correctly.

and with my code above, $entity value in EntityAccessCheck:Access is "test_entity-15" as string

*for reference: "test_entity-15" is referring to my test entity ID the same as in my url: /admin/testing/my-entity/test_entity-15

if ($parameters->has($entity_type)) {
  $entity = $parameters->get($entity_type); // <-- value: "test_entity-15"
  if ($entity instanceof EntityInterface) { // will false in here
    return $entity->access($operation, $account, TRUE); // and didn't reach here
  }
}

and will giving me response:

403: You are not authorized to access this page.

what am I missing here? let me know if you need my particular part of my code.

Thank You,

6
  • If $entity is simply "test_entity-15", a string, then the next line will always fail. $entity would need to be the fully loaded entity object of a class that extends EntityInterface. $entity must be an object, particularly since the line after that calls a method against it. You need more than a string.
    – Kevin
    May 7, 2017 at 1:36
  • Yes, the question is how to configure it so i become entity object like node entity? I think i have done my configuration following node as example configuration but seems like it missed something and didnt work properly
    – AnD
    May 7, 2017 at 2:59
  • But your error is exactly that per the code above.
    – Kevin
    May 7, 2017 at 3:00
  • I cant modify that code as that is Drupal core code, and to trace it where the value come from is very deep/long in drupal
    – AnD
    May 7, 2017 at 3:06
  • Like I said you're not evaluating an entity object
    – Kevin
    May 7, 2017 at 3:06

1 Answer 1

1

You say "i have entity and class TestEntityRouteProvider extends AdminHtmlRouteProvider implements EntityRouteProviderInterface. Normally you don't rewrite all of the route generating code when extending an entity route provider, you only modify some of the routes, rarely the whole set of routes in getRoutes(). But always execute the parent method first. See this example from a core entity type:

<?php

namespace Drupal\aggregator;

use Drupal\Core\Entity\EntityTypeInterface;
use Drupal\Core\Entity\Routing\AdminHtmlRouteProvider;

/**
 * Provides HTML routes for the feed entity type.
 */
class FeedHtmlRouteProvider extends AdminHtmlRouteProvider {

  /**
   * {@inheritdoc}
   */
  protected function getCanonicalRoute(EntityTypeInterface $entity_type) {
    $route = parent::getCanonicalRoute($entity_type);
    $route->setDefault('_title_controller', '\Drupal\aggregator\Controller\AggregatorController::feedTitle');

    return $route;
  }

  /**
   * {@inheritdoc}
   */
  protected function getEditFormRoute(EntityTypeInterface $entity_type) {
    $route = parent::getEditFormRoute($entity_type);

    $route->setDefault('_title', 'Configure');

    return $route;
  }

}

Or if you don't need to modify anything you simply use the standard class for the administration of entity types

  *     "route_provider" = {
  *       "html" = "Drupal\Core\Entity\Routing\AdminHtmlRouteProvider",

in the entity type annotations. Is it working then?

2
  • I just did "html" = "Drupal\Core\Entity\Routing\AdminHtmlRouteProvider" and i still getting 403 no permission - the different between this and mine is: my $entity = $parameters->get($entity_type); // <-- value: "test_entity-15" (see my question for details) while after i change to "Drupal\Core\Entity\Routing\AdminHtmlRouteProvider" $entity value become: 0 which both is leading to the same result 403
    – AnD
    May 7, 2017 at 13:33
  • If the default route provider is not able to build a working canonical route that returns the entity type parameter, then there is probably something wrong with the entity class itself. I would start over. Copy an example from core (a simply one, not node, that is the most complicated one) or build an entity with drupal console (answer all questions with no to get a simple example). Then you can try one thing after another until it breaks.
    – 4uk4
    May 7, 2017 at 14:22

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.