Unverified Commit a0601071 authored by Alex Pott's avatar Alex Pott
Browse files

fix: #3567230 Only overwrite mapped field values on media items when source...

fix: #3567230 Only overwrite mapped field values on media items when source field original value was non-empty

By: marcoscano
By: anybody
By: alexpott
(cherry picked from commit 57d2fe40)
parent f2326154
Loading
Loading
Loading
Loading
Loading
+24 −3
Original line number Diff line number Diff line
@@ -449,10 +449,31 @@ public function prepareSave() {
        $translation = $this->getTranslation($langcode);
        // Try to set fields provided by the media source and mapped in
        // media type config.
        $original = $this->getOriginal();
        foreach ($translation->bundle->entity->getFieldMap() as $metadata_attribute_name => $entity_field_name) {
          // Only save value in the entity if the field is empty or if the
          // source field changed.
          if ($translation->hasField($entity_field_name) && ($translation->get($entity_field_name)->isEmpty() || $translation->hasSourceFieldChanged())) {
          if (!$translation->hasField($entity_field_name)) {
            continue;
          }
          $set_metadata = FALSE;
          // Only save value in the entity if the field is empty, or if the
          // source field changed from one non-empty value to another non-empty
          // value.
          // 1st scenario: field is empty, safely store metadata there.
          if ($translation->get($entity_field_name)->isEmpty()) {
            $set_metadata = TRUE;
          }
          else {
            // 2nd scenario: field is not empty, but the source field has
            // changed between two non-empty values.
            $original_source_field_empty = ($original instanceof MediaInterface) && $media_source->getSourceFieldValue($original) === NULL;
            $new_source_field_empty = $media_source->getSourceFieldValue($translation) === NULL;
            if (!$original_source_field_empty &&
                !$new_source_field_empty &&
                $translation->hasSourceFieldChanged()) {
              $set_metadata = TRUE;
            }
          }
          if ($set_metadata) {
            $translation->set($entity_field_name, $media_source->getMetadata($translation, $metadata_attribute_name));
          }
        }
+21 −0
Original line number Diff line number Diff line
@@ -216,6 +216,27 @@ public function testMetadataMapping(): void {
    $this->assertSame('Snowball', $media_source->getMetadata($media, $attribute_name), 'Value of the metadata attribute is not correct.');
    $media->save();
    $this->assertSame('Snowball', $media->get($field_name)->value, 'Metadata attribute was not mapped to the field.');

    // Test that we only overwrite existing field values if the source changed
    // from a non-empty value to another non-empty value.
    $media = Media::create([
      'bundle' => $this->testMediaType->id(),
      // Force an empty source field.
      'field_media_test' => NULL,
      $field_name => 'Some pre-existing value',
    ]);
    $media->save();
    // After first save, the entity has the pre-existing value in the mapped
    // field.
    $this->assertSame('Some pre-existing value', $media->get($field_name)->value);
    \Drupal::state()->set('media_source_test_attributes', [
      $attribute_name => ['title' => 'Attribute to map', 'value' => 'Snowball'],
    ]);
    // Change the source field value from NULL to something different.
    $media->set('field_media_test', 'some_new_value');
    $media->save();
    // Verify the pre-existing value was not overwritten.
    $this->assertSame('Some pre-existing value', $media->get($field_name)->value);
  }

  /**