From 7896891da5465644110e5d7fb42d7392710fd9a7 Mon Sep 17 00:00:00 2001
From: Alex Pott <alex.a.pott@googlemail.com>
Date: Wed, 13 Jun 2018 09:10:02 +0100
Subject: [PATCH] Issue #2978848 by claudiu.cristea, amateescu:
 EntityReferenceFieldItemList::referencedEntities() doesn't work for computed
 fields

---
 .../Field/EntityReferenceFieldItemList.php    |  2 +-
 .../src/Entity/EntityTestComputedField.php    |  7 +++++
 .../ComputedReferenceTestFieldItemList.php    | 24 +++++++++++++++++
 .../Core/Entity/EntityFieldTest.php           | 27 +++++++++++++++++++
 4 files changed, 59 insertions(+), 1 deletion(-)
 create mode 100644 core/modules/system/tests/modules/entity_test/src/Plugin/Field/ComputedReferenceTestFieldItemList.php

diff --git a/core/lib/Drupal/Core/Field/EntityReferenceFieldItemList.php b/core/lib/Drupal/Core/Field/EntityReferenceFieldItemList.php
index 0a53d9894a32..3fa199b72764 100644
--- a/core/lib/Drupal/Core/Field/EntityReferenceFieldItemList.php
+++ b/core/lib/Drupal/Core/Field/EntityReferenceFieldItemList.php
@@ -24,7 +24,7 @@ public function getConstraints() {
    * {@inheritdoc}
    */
   public function referencedEntities() {
-    if (empty($this->list)) {
+    if ($this->isEmpty()) {
       return [];
     }
 
diff --git a/core/modules/system/tests/modules/entity_test/src/Entity/EntityTestComputedField.php b/core/modules/system/tests/modules/entity_test/src/Entity/EntityTestComputedField.php
index c873ccc00e29..187effe50456 100644
--- a/core/modules/system/tests/modules/entity_test/src/Entity/EntityTestComputedField.php
+++ b/core/modules/system/tests/modules/entity_test/src/Entity/EntityTestComputedField.php
@@ -4,6 +4,7 @@
 
 use Drupal\Core\Entity\EntityTypeInterface;
 use Drupal\Core\Field\BaseFieldDefinition;
+use Drupal\entity_test\Plugin\Field\ComputedReferenceTestFieldItemList;
 use Drupal\entity_test\Plugin\Field\ComputedTestFieldItemList;
 
 /**
@@ -39,6 +40,12 @@ public static function baseFieldDefinitions(EntityTypeInterface $entity_type) {
       ->setComputed(TRUE)
       ->setClass(ComputedTestFieldItemList::class);
 
+    $fields['computed_reference_field'] = BaseFieldDefinition::create('entity_reference')
+      ->setLabel('Computed Reference Field Test')
+      ->setComputed(TRUE)
+      ->setSetting('target_type', 'entity_test')
+      ->setClass(ComputedReferenceTestFieldItemList::class);
+
     return $fields;
   }
 
diff --git a/core/modules/system/tests/modules/entity_test/src/Plugin/Field/ComputedReferenceTestFieldItemList.php b/core/modules/system/tests/modules/entity_test/src/Plugin/Field/ComputedReferenceTestFieldItemList.php
new file mode 100644
index 000000000000..d28a014f1c62
--- /dev/null
+++ b/core/modules/system/tests/modules/entity_test/src/Plugin/Field/ComputedReferenceTestFieldItemList.php
@@ -0,0 +1,24 @@
+<?php
+
+namespace Drupal\entity_test\Plugin\Field;
+
+use Drupal\Core\Field\EntityReferenceFieldItemList;
+use Drupal\Core\TypedData\ComputedItemListTrait;
+
+/**
+ * A computed entity reference field item list.
+ */
+class ComputedReferenceTestFieldItemList extends EntityReferenceFieldItemList {
+
+  use ComputedItemListTrait;
+
+  /**
+   * Compute the list property from state.
+   */
+  protected function computeValue() {
+    foreach (\Drupal::state()->get('entity_test_reference_computed_target_ids', []) as $delta => $id) {
+      $this->list[$delta] = $this->createItem($delta, $id);
+    }
+  }
+
+}
diff --git a/core/tests/Drupal/KernelTests/Core/Entity/EntityFieldTest.php b/core/tests/Drupal/KernelTests/Core/Entity/EntityFieldTest.php
index a42a74baae1e..3fd17d86b477 100644
--- a/core/tests/Drupal/KernelTests/Core/Entity/EntityFieldTest.php
+++ b/core/tests/Drupal/KernelTests/Core/Entity/EntityFieldTest.php
@@ -16,6 +16,7 @@
 use Drupal\Core\TypedData\ListInterface;
 use Drupal\Core\TypedData\Type\StringInterface;
 use Drupal\Core\TypedData\TypedDataInterface;
+use Drupal\entity_test\Entity\EntityTest;
 use Drupal\entity_test\Entity\EntityTestComputedField;
 use Drupal\node\Entity\Node;
 use Drupal\node\Entity\NodeType;
@@ -870,6 +871,32 @@ public function testComputedFields() {
     $this->assertFalse($computed_item_list1->equals($computed_item_list2));
   }
 
+  /**
+   * Tests an entity reference computed field.
+   */
+  public function testEntityReferenceComputedField() {
+    $this->installEntitySchema('entity_test_computed_field');
+
+    // Create 2 entities to be referenced.
+    $ref1 = EntityTest::create(['name' => 'foo', 'type' => 'bar']);
+    $ref1->save();
+    $ref2 = EntityTest::create(['name' => 'baz', 'type' => 'bar']);
+    $ref2->save();
+    \Drupal::state()->set('entity_test_reference_computed_target_ids', [$ref1->id(), $ref2->id()]);
+
+    $entity = EntityTestComputedField::create([]);
+    $entity->save();
+
+    /** @var \Drupal\entity_test\Plugin\Field\ComputedReferenceTestFieldItemList $field */
+    $field = $entity->get('computed_reference_field');
+    /** @var \Drupal\Core\Entity\EntityInterface[] $referenced_entities */
+    $referenced_entities = $field->referencedEntities();
+
+    // Check that ::referencedEntities() is working with computed fields.
+    $this->assertEquals($ref1->id(), $referenced_entities[0]->id());
+    $this->assertEquals($ref2->id(), $referenced_entities[1]->id());
+  }
+
   /**
    * Executes the computed properties tests for the given entity type.
    *
-- 
GitLab