You are here

public function CommentController::commentPermalink in Drupal 10

Same name and namespace in other branches
  1. 8 core/modules/comment/src/Controller/CommentController.php \Drupal\comment\Controller\CommentController::commentPermalink()
  2. 9 core/modules/comment/src/Controller/CommentController.php \Drupal\comment\Controller\CommentController::commentPermalink()

Redirects comment links to the correct page depending on comment settings.

Since comments are paged there is no way to guarantee which page a comment appears on. Comment paging and threading settings may be changed at any time. With threaded comments, an individual comment may move between pages as comments can be added either before or after it in the overall discussion. Therefore we use a central routing function for comment links, which calculates the page number based on current comment settings and returns the full comment view with the pager set dynamically.

Parameters

\Symfony\Component\HttpFoundation\Request $request: The request of the page.

\Drupal\comment\CommentInterface $comment: A comment entity.

Return value

\Symfony\Component\HttpFoundation\Response The comment listing set to the page on which the comment appears.

Throws

\Symfony\Component\HttpKernel\Exception\NotFoundHttpException

\Symfony\Component\HttpKernel\Exception\AccessDeniedHttpException

1 string reference to 'CommentController::commentPermalink'
comment.routing.yml in core/modules/comment/comment.routing.yml
core/modules/comment/comment.routing.yml

File

core/modules/comment/src/Controller/CommentController.php, line 134

Class

CommentController
Controller for the comment entity.

Namespace

Drupal\comment\Controller

Code

public function commentPermalink(Request $request, CommentInterface $comment) {
  if ($entity = $comment
    ->getCommentedEntity()) {

    // Check access permissions for the entity.
    if (!$entity
      ->access('view')) {
      throw new AccessDeniedHttpException();
    }
    $field_definition = $this->entityFieldManager
      ->getFieldDefinitions($entity
      ->getEntityTypeId(), $entity
      ->bundle())[$comment
      ->getFieldName()];

    // Find the current display page for this comment.
    $page = $this
      ->entityTypeManager()
      ->getStorage('comment')
      ->getDisplayOrdinal($comment, $field_definition
      ->getSetting('default_mode'), $field_definition
      ->getSetting('per_page'));

    // @todo: Cleaner sub request handling.
    $subrequest_url = $entity
      ->toUrl()
      ->setOption('query', [
      'page' => $page,
    ])
      ->toString(TRUE);
    $redirect_request = Request::create($subrequest_url
      ->getGeneratedUrl(), 'GET', $request->query
      ->all(), $request->cookies
      ->all(), [], $request->server
      ->all());

    // Carry over the session to the subrequest.
    if ($request
      ->hasSession()) {
      $redirect_request
        ->setSession($request
        ->getSession());
    }
    $request->query
      ->set('page', $page);
    $response = $this->httpKernel
      ->handle($redirect_request, HttpKernelInterface::SUB_REQUEST);
    if ($response instanceof CacheableResponseInterface) {

      // @todo Once path aliases have cache tags (see
      //   https://www.drupal.org/node/2480077), add test coverage that
      //   the cache tag for a commented entity's path alias is added to the
      //   comment's permalink response, because there can be blocks or
      //   other content whose renderings depend on the subrequest's URL.
      $response
        ->addCacheableDependency($subrequest_url);
    }
    return $response;
  }
  throw new NotFoundHttpException();
}