From 29e324693ea41b67042dc400cfe011242adf15ad Mon Sep 17 00:00:00 2001 From: catch <catch@35733.no-reply.drupal.org> Date: Thu, 7 May 2020 19:44:17 +0100 Subject: [PATCH] =?UTF-8?q?Issue=20#2988309=20by=20Krzysztof=20Doma=C5=84s?= =?UTF-8?q?ki,=20Berdir,=20hchonov:=20Ensure=20that=20all=20field=20types?= =?UTF-8?q?=20return=20TRUE=20on=20equals()=20for=20the=20same=20values?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- core/lib/Drupal/Core/Field/FieldItemList.php | 9 +++++++++ .../Tests/Core/Field/FieldItemListTest.php | 19 +++++++++++++++++++ 2 files changed, 28 insertions(+) diff --git a/core/lib/Drupal/Core/Field/FieldItemList.php b/core/lib/Drupal/Core/Field/FieldItemList.php index 4bab6f40ac50..f73872baa36e 100644 --- a/core/lib/Drupal/Core/Field/FieldItemList.php +++ b/core/lib/Drupal/Core/Field/FieldItemList.php @@ -393,6 +393,15 @@ public function equals(FieldItemListInterface $list_to_compare) { $callback = function (&$value) use ($non_computed_properties) { if (is_array($value)) { $value = array_intersect_key($value, $non_computed_properties); + + // Also filter out properties with a NULL value as they might exist in + // one field item and not in the other, depending on how the values are + // set. Do not filter out empty strings or other false-y values as e.g. + // a NULL or FALSE in a boolean field is not the same. + $value = array_filter($value, function ($property) { + return $property !== NULL; + }); + ksort($value); } }; diff --git a/core/tests/Drupal/Tests/Core/Field/FieldItemListTest.php b/core/tests/Drupal/Tests/Core/Field/FieldItemListTest.php index a5cc7e352dcb..fbd522230316 100644 --- a/core/tests/Drupal/Tests/Core/Field/FieldItemListTest.php +++ b/core/tests/Drupal/Tests/Core/Field/FieldItemListTest.php @@ -135,6 +135,25 @@ public function providerTestEquals() { // not exist ('3'). $datasets[] = [TRUE, $field_item_h, $field_item_i]; + /** @var \Drupal\Core\Field\FieldItemBase $field_item_j */ + $field_item_j = $this->getMockForAbstractClass('Drupal\Core\Field\FieldItemBase', [], '', FALSE); + $field_item_j->setValue(['0' => 1]); + /** @var \Drupal\Core\Field\FieldItemBase $field_item_k */ + $field_item_k = $this->getMockForAbstractClass('Drupal\Core\Field\FieldItemBase', [], '', FALSE); + $field_item_k->setValue(['0' => 1, '1' => NULL]); + /** @var \Drupal\Core\Field\FieldItemBase $field_item_l */ + $field_item_l = $this->getMockForAbstractClass('Drupal\Core\Field\FieldItemBase', [], '', FALSE); + $field_item_l->setValue(['0' => 1, '1' => FALSE]); + /** @var \Drupal\Core\Field\FieldItemBase $field_item_m */ + $field_item_m = $this->getMockForAbstractClass('Drupal\Core\Field\FieldItemBase', [], '', FALSE); + $field_item_m->setValue(['0' => 1, '1' => '']); + + // Tests filter properties with a NULL value. Empty strings or other false-y + // values are not filtered. + $datasets[] = [TRUE, $field_item_j, $field_item_k]; + $datasets[] = [FALSE, $field_item_j, $field_item_l]; + $datasets[] = [FALSE, $field_item_j, $field_item_m]; + return $datasets; } -- GitLab