Problem/Motivation

Currently when saving an entity translation, the content translation metadata is not being saved, e.g. source translation.
It relies on the form being used.

Proposed resolution

Remaining tasks

  • Discuss if we can implement this or it should be responsibility of the API calling code.

User interface changes

None.

API changes

None.

Issue fork drupal-2544696

Command icon Show commands

Start within a Git clone of the project using the version control instructions.

Or, if you do not have SSH keys set up on git.drupalcode.org:

Support from Acquia helps fund testing for Drupal Acquia logo

Comments

penyaskito’s picture

Status: Active » Closed (won't fix)

As far as I have seen, there is no way of knowing the source of the translation if it not explicitly given, as content translation does in the form.
So I guess this is a won't fix, and needs to be set in the calling code.

penyaskito’s picture

Status: Closed (won't fix) » Active

@facine reported a problem when trying to create a translation with image fields via API:


use Drupal\node\Entity\Node;
use Drupal\file\Entity\File;
$images = [
  'sites/default/files/article/my_image_001.jpg',
  'sites/default/files/article/my_image_002.jpg',
  'sites/default/files/article/my_image_003.jpg',
];
$files = [];
foreach ($images as $image) {
  $file = File::create([
    'uid' => 1,
    'uri' => 'public://' . $image,
    'status' => 1,
  ]);
  $file->save();
  $files[] = $file->id();
}
$node = Node::create([
  'type' => 'article',
  'langcode' => 'en',
  'created' => REQUEST_TIME,
  'changed' => REQUEST_TIME,
  'uid' => 1,
  'title' => 'My title',
  'body' => [
    'summary' => '',
    'value' => '<p>My body</p>',
    'format' => 'full_html',
  ],
]);
foreach ($files as $image) {
  $node->field_images[] = [
    'target_id' => $image,
    'alt' => 'My image alt',
    'title' => 'My image title',
  ];
}
$node->save();
\Drupal::service('path.alias_storage')->save('/node/' . $node->id(), '/my/node/path', 'en');
$node_es = $node->addTranslation('es');
$node_es->title = 'Mi título';
$node_es->body->value = '<p>Mi cuerpo</p>';
$node_es->body->format = 'full_html';
/**
 * This foreach give me this error:
Drupal\Core\Entity\EntityStorageException: Invalid translation language (und) specified. in Drupal\Core\Entity\Sql\SqlContentEntityStorage->save() (line 757 of core/lib/Drupal/Core/Entity/Sql/SqlContentEntityStorage.php).
Drupal\content_translation\FieldTranslationSynchronizer->synchronizeFields(Object, 'es', 'und')
content_translation_entity_presave(Object)
call_user_func_array('content_translation_entity_presave', Array)
Drupal\Core\Extension\ModuleHandler->invokeAll('entity_presave', Array)
Drupal\Core\Entity\EntityStorageBase->invokeHook('presave', Object)
Drupal\Core\Entity\ContentEntityStorageBase->invokeHook('presave', Object)
Drupal\Core\Entity\EntityStorageBase->doPreSave(Object)
Drupal\Core\Entity\ContentEntityStorageBase->doPreSave(Object)
Drupal\Core\Entity\EntityStorageBase->save(Object)
Drupal\Core\Entity\Sql\SqlContentEntityStorage->save(Object)
Drupal\Core\Entity\Entity->save()
eval()
Drupal\devel\Form\ExecutePHP->submitForm(Array, Object)
call_user_func_array(Array, Array)
Drupal\Core\Form\FormSubmitter->executeSubmitHandlers(Array, Object)
Drupal\Core\Form\FormSubmitter->doSubmitForm(Array, Object)
Drupal\Core\Form\FormBuilder->processForm('devel_execute_form', Array, Object)
Drupal\Core\Form\FormBuilder->buildForm(Object, Object)
Drupal\Core\Controller\FormController->getContentResult(Object, Object)
call_user_func_array(Array, Array)
Drupal\Core\EventSubscriber\EarlyRenderingControllerWrapperSubscriber->Drupal\Core\EventSubscriber\{closure}()
Drupal\Core\Render\Renderer->executeInRenderContext(Object, Object)
Drupal\Core\EventSubscriber\EarlyRenderingControllerWrapperSubscriber->wrapControllerExecutionInRenderContext(Array, Array)
Drupal\Core\EventSubscriber\EarlyRenderingControllerWrapperSubscriber->Drupal\Core\EventSubscriber\{closure}()
call_user_func_array(Object, Array)
Symfony\Component\HttpKernel\HttpKernel->handleRaw(Object, 1)
Symfony\Component\HttpKernel\HttpKernel->handle(Object, 1, 1)
Drupal\Core\StackMiddleware\Session->handle(Object, 1, 1)
Drupal\Core\StackMiddleware\KernelPreHandle->handle(Object, 1, 1)
Drupal\page_cache\StackMiddleware\PageCache->pass(Object, 1, 1)
Drupal\page_cache\StackMiddleware\PageCache->handle(Object, 1, 1)
Drupal\Core\StackMiddleware\ReverseProxyMiddleware->handle(Object, 1, 1)
Drupal\Core\StackMiddleware\NegotiationMiddleware->handle(Object, 1, 1)
Stack\StackedHttpKernel->handle(Object, 1, 1)
Drupal\Core\DrupalKernel->handle(Object)
 */
foreach ($files as $image) {
  $node_es->field_images[] = [
    'target_id' => $image,
    'alt' => 'Alt de mi imagen',
    'title' => 'Título de mi imagen',
  ];
}
$node_es->save();
\Drupal::service('path.alias_storage')->save("/node/" . $node->id(),  '/mi/ruta', 'es');

As said before, it should be responsability of the calling code to set the source before saving (which fixes the problem he was having):

$node_es->set('content_translation_source', 'en');

However, I'm wondering if instead of failing, we should ignore it if not set and do something like:

diff --git a/core/modules/content_translation/content_translation.module b/core/modules/content_translation/content_translation.module
index ff1b34d..dfed390 100644
--- a/core/modules/content_translation/content_translation.module
+++ b/core/modules/content_translation/content_translation.module
@@ -406,7 +406,9 @@ function content_translation_entity_presave(EntityInterface $entity) {
     /** @var \Drupal\content_translation\ContentTranslationManagerInterface $manager */
     $manager = \Drupal::service('content_translation.manager');
     $source_langcode = !$entity->original->hasTranslation($langcode) ? $manager->getTranslationMetadata($entity)->getSource() : NULL;
-    \Drupal::service('content_translation.synchronizer')->synchronizeFields($entity, $langcode, $source_langcode);
+    if ($source_langcode !== LanguageInterface::LANGCODE_NOT_SPECIFIED) {
+      \Drupal::service('content_translation.synchronizer')->synchronizeFields($entity, $langcode, $source_langcode);
+    }
   }
 }

Thoughts?

Gábor Hojtsy’s picture

But then fields would not be synced? Is that what you would expect in the API?

plach’s picture

I'd prefer an explicit fail, so that developers have to think to what they need to do in their case, rather than silently skipping a behavior they may rely on. Alternatively, we could have the source language default to the entity default language on translation creation, so things would always work and would only need to be changed if the source language actually matters. However this solution would require #2382675: hook_entity_create() affects the data of new translations of existing entities in unexpected and undocumented ways.

Gábor Hojtsy’s picture

I agree with @plach, would not skip the sync, rather default the source language (which sounds sensible on its own BTW).

penyaskito’s picture

Status: Active » Closed (works as designed)

What was confusing to me is that the behavior translating with the API without content_translation was different than translating with the API with content_translation enabled. But yes, the difference is that we don't take file sync into account in the former case.
Changing the source language would be an API change, so I will close this issue for now. It will help people searching for the error message though, thanks! :)

penyaskito’s picture

Status: Closed (works as designed) » Active

I happen to find this issue myself (glad I knew where to look).

      $translation->set('content_translation_source', $entity->getUntranslated()->language()->getId());

before save() fixed it, but I'm more convinced now that we should default to the source language.

Wondering if this is acceptable for a minor release or should wait for 8.1.x.

Version: 8.0.x-dev » 8.1.x-dev

Drupal 8.0.6 was released on April 6 and is the final bugfix release for the Drupal 8.0.x series. Drupal 8.0.x will not receive any further development aside from security fixes. Drupal 8.1.0-rc1 is now available and sites should prepare to update to 8.1.0.

Bug reports should be targeted against the 8.1.x-dev branch from now on, and new development or disruptive changes should be targeted against the 8.2.x-dev branch. For more information see the Drupal 8 minor version schedule and the Allowed changes during the Drupal 8 release cycle.

Version: 8.1.x-dev » 8.2.x-dev

Drupal 8.1.9 was released on September 7 and is the final bugfix release for the Drupal 8.1.x series. Drupal 8.1.x will not receive any further development aside from security fixes. Drupal 8.2.0-rc1 is now available and sites should prepare to upgrade to 8.2.0.

Bug reports should be targeted against the 8.2.x-dev branch from now on, and new development or disruptive changes should be targeted against the 8.3.x-dev branch. For more information see the Drupal 8 minor version schedule and the Allowed changes during the Drupal 8 release cycle.

Version: 8.2.x-dev » 8.3.x-dev

Drupal 8.2.6 was released on February 1, 2017 and is the final full bugfix release for the Drupal 8.2.x series. Drupal 8.2.x will not receive any further development aside from critical and security fixes. Sites should prepare to update to 8.3.0 on April 5, 2017. (Drupal 8.3.0-alpha1 is available for testing.)

Bug reports should be targeted against the 8.3.x-dev branch from now on, and new development or disruptive changes should be targeted against the 8.4.x-dev branch. For more information see the Drupal 8 minor version schedule and the Allowed changes during the Drupal 8 release cycle.

kriboogh’s picture

This little patch solves some issues for us, maybe it can be reviewed. Not sure what the impact might be on other things, but this at least allows us to sync entities between different websites and do custom migrations.

Status: Needs review » Needs work

Version: 8.3.x-dev » 8.4.x-dev

Drupal 8.3.6 was released on August 2, 2017 and is the final full bugfix release for the Drupal 8.3.x series. Drupal 8.3.x will not receive any further development aside from critical and security fixes. Sites should prepare to update to 8.4.0 on October 4, 2017. (Drupal 8.4.0-alpha1 is available for testing.)

Bug reports should be targeted against the 8.4.x-dev branch from now on, and new development or disruptive changes should be targeted against the 8.5.x-dev branch. For more information see the Drupal 8 minor version schedule and the Allowed changes during the Drupal 8 release cycle.

Version: 8.4.x-dev » 8.5.x-dev

Drupal 8.4.4 was released on January 3, 2018 and is the final full bugfix release for the Drupal 8.4.x series. Drupal 8.4.x will not receive any further development aside from critical and security fixes. Sites should prepare to update to 8.5.0 on March 7, 2018. (Drupal 8.5.0-alpha1 is available for testing.)

Bug reports should be targeted against the 8.5.x-dev branch from now on, and new development or disruptive changes should be targeted against the 8.6.x-dev branch. For more information see the Drupal 8 minor version schedule and the Allowed changes during the Drupal 8 release cycle.

mrtndlmt’s picture

Update patch for drupal 8.5.6

mrtndlmt’s picture

Whoops! Wrong patch over here! Sorry guys!

Version: 8.5.x-dev » 8.6.x-dev

Drupal 8.5.6 was released on August 1, 2018 and is the final bugfix release for the Drupal 8.5.x series. Drupal 8.5.x will not receive any further development aside from security fixes. Sites should prepare to update to 8.6.0 on September 5, 2018. (Drupal 8.6.0-rc1 is available for testing.)

Bug reports should be targeted against the 8.6.x-dev branch from now on, and new development or disruptive changes should be targeted against the 8.7.x-dev branch. For more information see the Drupal 8 minor version schedule and the Allowed changes during the Drupal 8 release cycle.

borisson_’s picture

Category: Task » Bug report

The patch in #11 seems to break a lot of tests and #15 is a different patch. I don't think we can fix this issue in a BC-compatible way.

I think this is a bugreport instead of a task though.

Version: 8.6.x-dev » 8.8.x-dev

Drupal 8.6.x will not receive any further development aside from security fixes. Bug reports should be targeted against the 8.8.x-dev branch from now on, and new development or disruptive changes should be targeted against the 8.9.x-dev branch. For more information see the Drupal 8 and 9 minor version schedule and the Allowed changes during the Drupal 8 and 9 release cycles.

Version: 8.8.x-dev » 8.9.x-dev

Drupal 8.8.7 was released on June 3, 2020 and is the final full bugfix release for the Drupal 8.8.x series. Drupal 8.8.x will not receive any further development aside from security fixes. Sites should prepare to update to Drupal 8.9.0 or Drupal 9.0.0 for ongoing support.

Bug reports should be targeted against the 8.9.x-dev branch from now on, and new development or disruptive changes should be targeted against the 9.1.x-dev branch. For more information see the Drupal 8 and 9 minor version schedule and the Allowed changes during the Drupal 8 and 9 release cycles.

Version: 8.9.x-dev » 9.2.x-dev

Drupal 8 is end-of-life as of November 17, 2021. There will not be further changes made to Drupal 8. Bugfixes are now made to the 9.3.x and higher branches only. For more information see the Drupal core minor version schedule and the Allowed changes during the Drupal core release cycle.

Version: 9.2.x-dev » 9.3.x-dev

Version: 9.3.x-dev » 9.4.x-dev

Drupal 9.3.15 was released on June 1st, 2022 and is the final full bugfix release for the Drupal 9.3.x series. Drupal 9.3.x will not receive any further development aside from security fixes. Drupal 9 bug reports should be targeted for the 9.4.x-dev branch from now on, and new development or disruptive changes should be targeted for the 9.5.x-dev branch. For more information see the Drupal core minor version schedule and the Allowed changes during the Drupal core release cycle.

Version: 9.4.x-dev » 9.5.x-dev

Drupal 9.4.9 was released on December 7, 2022 and is the final full bugfix release for the Drupal 9.4.x series. Drupal 9.4.x will not receive any further development aside from security fixes. Drupal 9 bug reports should be targeted for the 9.5.x-dev branch from now on, and new development or disruptive changes should be targeted for the 10.1.x-dev branch. For more information see the Drupal core minor version schedule and the Allowed changes during the Drupal core release cycle.

SocialNicheGuru’s picture

Version: 9.5.x-dev » 11.x-dev

Is this also the case in Drupal 11?
If not, please set back to Drupal 9.5.

mohit_aghera’s picture

@penyaskito
I'm not able to reproduce the issue.
I've attached one test-only patch which is passing on local against latest 11.x.
I haven't created new branch and fork since I'm not quite sure of this issue is still valid.

Can you please check the test-only patch and see if this is same as what has been given in #2

penyaskito’s picture

Priority: Major » Normal

I doubt this is a major.

@mohit_rocks Not sure why I posted that here, but IMHO it's unrelated to the OP (hard to know years later). When I created this issue my goals were more aligned with what #11 is attempting.