2

How can I get the translated value of a field in Drupal 8 and if no translation is given, fallback to the default node language? I tried this: https://drupal.stackexchange.com/a/145747/9586, but when no translation for a field if added, it just returns NULL.

Here is what I tried:

    $node = Node::load(2);
dsm(\Drupal::entityManager()->getTranslationFromContext($node)->field_my_awesome_field->value);

2 Answers 2

3

You can try to provide the context for a fallback as 3rd parameter:

public EntityRepositoryInterface::getTranslationFromContext(EntityInterface $entity, $langcode = NULL, $context = array())

Here is the documentation, but it is not documented, what the content of the array is exactly:

getTranslationFromContext

I would code the fallback myself and take control, how this is handled exactly, if the node is not fully translated:

$val = \Drupal::service('entity.repository')->getTranslationFromContext($node)->field_my_awesome_field->value;
 if (empty($val)) {
    // $node has no translation with the default node language
    // get the default from somewhere else (domain, user ...) and try again
    $val = $node->getTranslation($defaultlanguage)->field_my_awesome_field->value;
}
if (empty($val)) {
   // someone needs to translate this node, in the meantime get the original value
   $val = $node->field_my_awesome_field->value;
}

You can adjust the code to your needs, you can add as many fallbacks as you like or go directly to the last if-statement to load the original field value.

One remark: If your multilingual site is setup correctly, this should not happen. The fallback is there, when something goes wrong. For example, if you configure a field as translatable, but when translating the node, you leave only this field blank. Then drupal does not know, is this intentionally, should it be blank or do you want to load the field from another language?

1
  • Alright that totally makes sense, thanks for the help.
    – Sebastian
    Nov 13, 2015 at 8:52
5

Drupal 8 does not have built in field-level language fallbacks. That feature was removed in favor entity level language fallbacks since that is the common case. Usually an entity is translated as a while (or not) and it removes a huge amount of complexity, especially in views or so.

If you have a specific field where you want to apply this, then you need to implement that yourself. You can check if an entity-level translation exists with $node->hasTranslation('en') and if so, get it with $translation = $node->getTranslation('de') ($translation is still a node object, it's a clone of the original one with a different active language). Then check if you have a value and repeat until find one.

Something like this:

$value = NULL;
$language_manager = \Drupal::languageManager();
$current_langcode = $language_manager->getLanguage(Drupal\Core\Language\LanguageInterface::TYPE_CONTENT);
foreach ($language_manager->getFallbackCandidates(['langcode' => $language_manager->getLanguage(]) as $langcode) {
  if ($node->hasTranslation($langcode) && !$node->getTranslation($langcode)->field_my_awesome_field->isEmpty()) {
    $value = $node->getTranslation($langcode)->field_my_awesome_field->value;
    break;
  }
}
1
  • I would mark your comment also as right answer, but the guy before you was quicker sorry. Anyways your comment also helped me to understand that better thank you.
    – Sebastian
    Nov 13, 2015 at 8:52

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.

Not the answer you're looking for? Browse other questions tagged or ask your own question.