From 85d12a09fb6fd5df0a86ec2c2bc9a54bd4c11395 Mon Sep 17 00:00:00 2001
From: git <git@3554464.no-reply.drupal.org>
Date: Thu, 26 Apr 2018 07:31:33 +0200
Subject: [PATCH] Issue #2605874 by dpacassi, casey, nkoporec: Display
 fieldblocks on entity revision/preview routes

---
 src/Plugin/Block/FieldBlock.php | 57 +++++++++++++++++++++++++++------
 1 file changed, 48 insertions(+), 9 deletions(-)

diff --git a/src/Plugin/Block/FieldBlock.php b/src/Plugin/Block/FieldBlock.php
index 28ace1c..f551de3 100644
--- a/src/Plugin/Block/FieldBlock.php
+++ b/src/Plugin/Block/FieldBlock.php
@@ -51,6 +51,13 @@ class FieldBlock extends BlockBase implements ContainerFactoryPluginInterface {
    */
   protected $routeMatch;
 
+  /**
+   * The entity to be used when displaying the block.
+   *
+   * @var \Drupal\Core\Entity\ContentEntityInterface
+   */
+  protected $fieldBlockEntity;
+
   /**
    * {@inheritdoc}
    *
@@ -314,10 +321,9 @@ class FieldBlock extends BlockBase implements ContainerFactoryPluginInterface {
    * {@inheritdoc}
    */
   protected function blockAccess(AccountInterface $account) {
-    $entity_type = $this->getDerivativeId();
-    $entity = $this->routeMatch->getParameter($entity_type);
+    $entity = $this->getEntity();
 
-    if ($entity instanceof ContentEntityInterface && $entity->getEntityTypeId() === $entity_type && $entity->hasField($this->configuration['field_name'])) {
+    if ($entity) {
       $field = $entity->get($this->configuration['field_name']);
       return AccessResult::allowedIf($field->access('view', $account));
     }
@@ -329,10 +335,9 @@ class FieldBlock extends BlockBase implements ContainerFactoryPluginInterface {
    */
   public function build() {
     $build = [];
-    $entity_type = $this->getDerivativeId();
-    $entity = $this->routeMatch->getParameter($entity_type);
+    $entity = $this->getEntity();
 
-    if ($entity instanceof ContentEntityInterface) {
+    if ($entity) {
       $build['field'] = $entity->get($this->configuration['field_name'])->view([
         'label' => 'hidden',
         'type' => $this->configuration['formatter_id'],
@@ -350,9 +355,8 @@ class FieldBlock extends BlockBase implements ContainerFactoryPluginInterface {
    * {@inheritdoc}
    */
   public function getCacheTags() {
-    $entity_type = $this->getDerivativeId();
-    $entity = $this->routeMatch->getParameter($entity_type);
-    if ($entity instanceof ContentEntityInterface) {
+    $entity = $this->getEntity();
+    if ($entity) {
       return $entity->getCacheTags();
     }
     return parent::getCacheTags();
@@ -366,4 +370,39 @@ class FieldBlock extends BlockBase implements ContainerFactoryPluginInterface {
     // and its own fields.
     return ['route'];
   }
+
+  /**
+   * Finds the entity to be used when displaying the block.
+   *
+   * @return \Drupal\Core\Entity\ContentEntityInterface|null
+   *   The entity to be used when displaying the block.
+   */
+  protected function getEntity() {
+    if (!isset($this->fieldBlockEntity)) {
+      $entity_type = $this->getDerivativeId();
+      $entity = NULL;
+      $field_name = $this->configuration['field_name'];
+      $route_name = $this->routeMatch->getRouteName();
+      $is_canonical_route = $route_name === 'entity.' . $entity_type . '.canonical';
+      $is_latest_route = $route_name == 'entity.' . $entity_type . '.latest_version';
+
+      if ($is_canonical_route || $is_latest_route) {
+        $entity = $this->routeMatch->getParameter($entity_type);
+      }
+      elseif ($entity_type === 'node') {
+        if ($route_name == 'entity.node.revision') {
+          $entity_revision = $this->routeMatch->getParameter('node_revision');
+          $entity = $this->entityManager->getStorage('node')->loadRevision($entity_revision);
+        }
+        elseif ($route_name == 'entity.node.preview' && $this->routeMatch->getParameter('view_mode_id') === 'full') {
+          $entity = $this->routeMatch->getParameter('node_preview');
+        }
+      }
+
+      if ($entity instanceof ContentEntityInterface && $entity->getEntityTypeId() === $entity_type && $entity->hasField($field_name)) {
+        $this->fieldBlockEntity = $entity;
+      }
+    }
+    return $this->fieldBlockEntity;
+  }
 }
-- 
GitLab