Problem/Motivation

Follow-up to #2584603-48: PHP exception on manage fields after enabling Configuration Translation

we cannot actually prevent having config files associated to the same mapper in different languages (which prevents translation). If we only add the file to the mapper if the langcodes match we have a sort of "silent failing" in that (in this case) you cannot translate the node type label (because the respective file is not added to the mapper) but you get absolutely no feedback that something is wrong or why it is. Bad.

Step to reproduce:
1- Install a drupal 8 in Spanish.
2- In "admin/config/regional/language/add" add Inglés language.
3- Go to "/en/admin/modules" install "Configuration Translation" and "Content Translation" modules.
4- Go to "/en/admin/structure/types/manage/page/fields", click in "Add field", in "Re-use an existing field', select "Image: Field image", "Save and continue".
5- Bump!

RuntimeException: A config mapper can only contain configuration for a single language. in Drupal\config_translation\ConfigNamesMapper->getLangcode() (line 398 of core/modules/config_translation/src/ConfigNamesMapper.php).

Drupal\config_translation\Access\ConfigTranslationOverviewAccess->access(Object, Object)
call_user_func_array(Array, Array)
Drupal\Core\Access\AccessManager->performCheck('config_translation.access.overview', Object)
Drupal\Core\Access\AccessManager->check(Object, Object, NULL, 1)
Drupal\Core\Access\AccessManager->checkNamedRoute('entity.field_config.config_translation_overview.node', Array, Object, 1)
Drupal\Core\Menu\LocalTaskManager->getTasksBuild('entity.field_config.node_field_edit_form', Object)
Drupal\Core\Menu\LocalTaskManager->getLocalTasks('entity.field_config.node_field_edit_form', 0)
Drupal\Core\Menu\Plugin\Block\LocalTasksBlock->build()
Drupal\block\BlockViewBuilder::preRender(Array)
call_user_func('Drupal\block\BlockViewBuilder::preRender', Array)
Drupal\Core\Render\Renderer->doRender(Array)
Drupal\Core\Render\Renderer->doRender(Array, )
Drupal\Core\Render\Renderer->render(Array)
Drupal\Core\Template\TwigExtension->escapeFilter(Object, Array, 'html', NULL, 1)
__TwigTemplate_0f04497e0607dbb55ae785558deed68eacde76e3989f8c8e0779ccf1b6af549c->doDisplay(Array, Array)
Twig_Template->displayWithErrorHandling(Array, Array)
Twig_Template->display(Array)
Twig_Template->render(Array)
twig_render_template('core/themes/seven/templates/page.html.twig', Array)
Drupal\Core\Theme\ThemeManager->render('page', Array)
Drupal\Core\Render\Renderer->doRender(Array, )
Drupal\Core\Render\Renderer->render(Array)
Drupal\Core\Template\TwigExtension->escapeFilter(Object, Array, 'html', NULL, 1)
__TwigTemplate_16436f2456eb6e9f1287d658a3b71677eb9755e9eb4796bd9e27a1209ebeaf7f->doDisplay(Array, Array)
Twig_Template->displayWithErrorHandling(Array, Array)
Twig_Template->display(Array)
Twig_Template->render(Array)
twig_render_template('core/themes/classy/templates/layout/html.html.twig', Array)
Drupal\Core\Theme\ThemeManager->render('html', Array)
Drupal\Core\Render\Renderer->doRender(Array, )
Drupal\Core\Render\Renderer->render(Array)
Drupal\Core\Render\MainContent\HtmlRenderer->Drupal\Core\Render\MainContent\{closure}()
Drupal\Core\Render\Renderer->executeInRenderContext(Object, Object)
Drupal\Core\Render\MainContent\HtmlRenderer->renderResponse(Array, Object, Object)
Drupal\Core\EventSubscriber\MainContentViewSubscriber->onViewRenderArray(Object, 'kernel.view', Object)
Drupal\Component\EventDispatcher\ContainerAwareEventDispatcher->dispatch('kernel.view', Object)
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)

Fields have two config objects,
the "Edit" tab is field.field... and
the "Field settings" the field.storage...

When installing in spanish, using standard profile, the field and storage config have langcode es.
After adding english, and enabling configuration translation module, and specifying en in the admin url, the field config (not storage) has the langcode en.
The translate tab, then errors because it expects all the config on the form to have the same source.

This is only a problem when config translation is enabled. (The field stuff is fine.)

Proposed resolution

We should "fail gracefully" by catching the exception in the UI and notifying the user about this in some way.
- Still show the translate tabs and everything (and make sure that no fatals bubble up, i.e. catch the exception)
- On the translation overview show a drupal_set_message(..., 'warning') with something like

The configuration files related to the node type Article have different source language codes and thus cannot be translated:
or
"Warning, the field configuration and field settings configuration have different source languages, and will not be able to be translated."

  • node.type.article: Spanish
  • core.base_field_override.node.title.article: Hungarian

We could do other things as well (maybe followups), ideas could be:
- Show some suggestion on how to fix this (maybe link to d.o)
- (no) Fix this automatically somehow
- Present a UI to choose which langcode to set for all the config files
- Still allow to translate some of the config files for which the langcode matches (and still show a warning)

Remaining tasks

Contributor tasks needed
Task Novice task? Contributor instructions Complete?
Create a patch Instructions
Add automated tests Instructions
Embed before and after screenshots in the issue summary Novice Instructions
Review patch to ensure that it fixes the issue, stays within scope, is properly documented, and follows coding standards Instructions

User interface changes

Adding a warning.

API changes

??

Data model changes

No.

CommentFileSizeAuthor
#91 Failqm.JPG62.22 KBBenia
#87 fail.JPG88.43 KBBenia
#80 2595535-80.patch20.33 KBcatch
#80 interdiff.txt1.79 KBcatch
#74 2595535-74-config-translation-langcode-exception.patch20.68 KBtstoeckler
#74 2595535-72-74--interdiff.txt1.46 KBtstoeckler
#72 2595535-72-config-translation-langcode-exception.patch20.81 KBtstoeckler
#72 2595535-63-72--interdiff.txt9.63 KBtstoeckler
#64 Screen Shot 2016-06-01 at 10.23.26 PM.png214.03 KBKristen Pol
#63 2595535-diff-55-63.txt1.83 KBvijaycs85
#63 2595535-63.patch17.25 KBvijaycs85
#55 2595535-55.patch18.75 KBtstoeckler
#55 2595535-51-55-interdiff.txt4.11 KBtstoeckler
#51 show_helpful_message_or-2595535-51.patch19 KBalvar0hurtad0
#51 interdiff_46_51.txt2.24 KBalvar0hurtad0
#46 2595535-46.patch18.94 KBesolitos
#36 Screen Shot 2016-03-09 at 2.39.19 PM.png118.39 KBKristen Pol
#34 2595535-test-t.txt2.13 KBtstoeckler
#34 2595535-34.patch18.94 KBtstoeckler
#34 2595535-30-34--interdiff.txt3.45 KBtstoeckler
#30 259553-30.patch18.84 KBtstoeckler
#30 2595535-28-30--interdiff.txt1.04 KBtstoeckler
#28 2595535-28.patch18.76 KBtstoeckler
#28 2595535-25-28--interdiff.txt1.35 KBtstoeckler
#26 Bildschirmfoto am 2016-03-01 um 12.27.09.png34.8 KBtstoeckler
#25 2595535-25.patch18.69 KBtstoeckler
#25 2595535-19-25-interdiff.txt11.73 KBtstoeckler
#19 2595535-diff-18-19.txt6.64 KBvijaycs85
#19 2595535-19.patch11.95 KBvijaycs85
#15 2595535-15.patch8.82 KBswentel
#15 2595535-15-interdiff.txt757 bytesswentel
#13 2595535-test-only-13.patch2.02 KBswentel
#4 config-translation-message.png34.92 KBtstoeckler
#4 2595535-tobias.patch6.67 KBtstoeckler
#2 2595535-gabor.patch3.14 KBtstoeckler
#18 2595535-intediff-18.txt2.63 KBswentel
#18 2595535-18.patch10.93 KBswentel
Members fund testing for the Drupal project. Drupal Association Learn more

Comments

YesCT created an issue. See original summary.

tstoeckler’s picture

Title: Show helpful message (do not be silent) when configuration files have different source language codes and cannot be translated » Show helpful message or be silent (but do not fatal!) when configuration files have different source language codes and cannot be translated
Status: Active » Needs review
Issue tags: +Needs tests
FileSize
3.14 KB

Unless I'm mistaken, this is something the direction that @Gábor Hojtsy was proposing.

In addition to silently failing, this has the problem of not working for people for implement hook_config_translation_info_alter(), but only people using ConfigNamesMapper::getLangcode() and I don't see how we could get around that.

Status: Needs review » Needs work

The last submitted patch, 2: 2595535-gabor.patch, failed testing.

tstoeckler’s picture

Here's something more along the lines of what I was thinking. Wording, etc. to be done, but it's a start.

tstoeckler’s picture

Status: Needs work » Needs review

The last submitted patch, 2: 2595535-gabor.patch, failed testing.

Gábor Hojtsy’s picture

Status: Needs review » Needs work
Issue tags: +sprint

The proposed patch seems to let things go on thinking the source language is English even if technically we would not be able to tell what is even translated (source languages don't match) and we cannot display a transaltion form this way. I don't think its feasible to allow access to these pages. I would disallow access and display that message, so we don't attempt to go into displaying overview tables or translation forms if we cannot.

YesCT’s picture

rpayanm’s picture

I created the issue #2623908: A config mapper can only contain configuration for a single language and the "Step to reproduce". But today I tested the 8.0.1 release and the error was gone.

Codenator’s picture

I got error on Drupal 8.0.2 when add language and try edit Content type -> Article
edited: When uninstall Configuration Translation module error gone
Way this not critical? On my site this module , when enabled, block me from edit fields in Content type

rpayanm’s picture

Oh yes, this come back :(

Gábor Hojtsy’s picture

Category: Task » Bug report
Priority: Major » Critical

@swentel closed #2584603: PHP exception on manage fields after enabling Configuration Translation (again) referencing this issue. If this issue is to solve the recurring problem, then this needs to be critical as well. Three reports from that issue:

#2584603-73: PHP exception on manage fields after enabling Configuration Translation I am having this error when adding an existing field to a new content type. The content types were created when the default language of the site was English. The default language was changed. When adding an existing field to another content type I get the error. Also, of course, when trying to edit the field.

#2584603-75: PHP exception on manage fields after enabling Configuration Translation Also getting the same issue on 8.0.2 with two languages enabled. I did change the default language of the site from English to Japanese after creating a few pieces of content, but the error is arising from "Manage Fields" for a content type that I created after enabling the Japanese language and setting it as the default.

swentel’s picture

Status: Needs work » Needs review
FileSize
2.02 KB

Took me a while to figure out you needed tabs to get the bug exposes in tests ..

Status: Needs review » Needs work

The last submitted patch, 13: 2595535-test-only-13.patch, failed testing.

swentel’s picture

Status: Needs work » Needs review
FileSize
8.82 KB
757 bytes

This merges the patch from @tstoeckler in.

Now, this fixes the 're-using fields' action in the test I added in #13. However, upon clicking on the translate tabs, it still goes 500, as the test I've added also exposes (see interdiff for that).

The last submitted patch, 15: 2595535-15.patch, failed testing.

maartendeblock’s picture

swentel’s picture

This also fixes the controller and showing the same message - inline.

vijaycs85’s picture

golddragon007’s picture

Hi, This patch fixed my issue. I use now 8.0.3.

My issue was:
I get this with the 8.0.3 D8 (and with the 8.0.2 too, I only updated from 8.0.2 to 8.0.3).
RuntimeException: A config mapper can only contain configuration for a single language. in Drupal\config_translation\ConfigNamesMapper->getLangcode() (line 400 of \core\modules\config_translation\src\ConfigNamesMapper.php).

Debug:

    $config_factory = $this->configFactory;
    $langcodes = array_map(function($name) use ($config_factory) {
      // Default to English if no language code was provided in the file.
      // Although it is a best practice to include a language code, if the
      // developer did not think about a multilingual use-case, we fall back
      // on assuming the file is English.
      watchdog_exception('debug', new \Exception("A"), "Error1: %test", array("%test" => var_export($config_factory->get($name)->get('langcode'), true)));
      return $config_factory->get($name)->get('langcode') ?: 'en';
    }, $this->getConfigNames());
    watchdog_exception('debug', new \Exception("A"), "Error2: %test", array("%test" => var_export($langcodes, true)));
    watchdog_exception('debug', new \Exception("A"), "Error3: %test", array("%test" => var_export($this->getConfigNames(), true)));
    if (count(array_unique($langcodes)) > 1) {
      throw new \RuntimeException('A config mapper can only contain configuration for a single language.');
    }

Watchdog log:
Error1: 'sk'
Error1: 'en'
Error2: array ( 0 => 'sk', 1 => 'en', )
Error3: array ( 0 => 'node.type.page', 1 => 'core.base_field_override.node.page.title', )

I tried to reproduce with a newly installed Drupal 8, but it wasn't successful.

Some basic information about the site:
There're 6 languages including with the English (which is not the default language, and basically it's not used, but it's not turned off). All internationalization module is turned on. I did a lot of things, before I detected this, so I don't know what caused this. :(

I get this when I go to /admin/structure/types/manage/page/fields . (editing the default two content type's [basic page, article] fields) With custom content type, I don't get any error, it works well.

EdizonTN’s picture

I confirm.
D8.0.3 + patch 2595535-19 is working perfectly now.
3 languages (CZ,SK,EN). Default SK.

EdizonTN’s picture

D8.0.4 + patch 2595535-19 is working also.

rpayanm’s picture

2595535-19.patch in Drupal 8.0.4 works for me.

esolitos’s picture

Testing #19 on an handful of sites on 8.0.4 and it seems to be working fine!

tstoeckler’s picture

FileSize
11.73 KB
18.69 KB

Here's an updated patch. The interdiff is with -w for readability's sake. I made the following changes:

  1. Instead of granting access to both the overview and the form, this just grants access to the controller and displays the message, while denying access to the form (but not letting the exception bubble!). I think there is no reason to show a useless form, that with the previous was not reachable by any link, but only by guessing the URL anyway. Because of the way that ConfigTranslationOverviewAccess and ConfigTranslationFormAccess are set up, I had to use a try-catch block in both, which is not super nice, but I couldn't find any nicer way.
  2. Instead of printing just the warning message and nothing else in the "broken" case, I changed this to show a warning message (i.e. drupal_set_message(), like the form was doing before) and then show the rest of the overview in the normal way - except without the 'Add' and 'Edit' links for translations. I think it is more intuitive to show the screen that people are used to. If they then can make the warning disappear, the screen will still look the same (which is a good thing IMO), but with added Operations links.
  3. I added ConfigNamesMapper::getLangcodeFromConfig() to ConfigMapperInterface. This is technically a BC-break, but ConfigNamesMapper is one of those classes that (sadly) does so much, that it's almost unthinkable to implement ConfigMapperInterface without extending it. Also I think a critical bug warrants this kind of super minor break. If deemed not possible for 8.1 and/or 8.0 we could of course revert that but I think then instead of introducing a check on ConfigNamesMapper (like the previous patch) we should just fetch the langcode using the config factory ourselves. getLangcodeFromConfig() doesn't actually do anything super fancy it just seemed natural to split it out as there was a use-case for it and getLangcode() already hat the same logic.
tstoeckler’s picture

Oops, forgot to attach the screenshot of the translation overview that I made with the patch applied.

The config translation overview form showing a warning message at the top and then listing German, Spanish and Unkown (original) as languages.

Status: Needs review » Needs work

The last submitted patch, 25: 2595535-25.patch, failed testing.

tstoeckler’s picture

Status: Needs work » Needs review
FileSize
1.35 KB
18.76 KB

Fixed the test fails. I had updated the warning message to be a little bit more clear (IMO).

Using und as the language code changes the label for the source language from Unknown to None (see the screenshot in #26), which I think it slightly less clear, but und (as in undetermined) is semantically the correct language code to use in this case. We could explicitly set the langcode to NULL which would still avoid the notices and change the label back to Unknown but per the previous sentence I think that's not ideal.

catch’s picture

I think it's OK to use unspecified, however:

+++ b/core/modules/config_translation/src/Controller/ConfigTranslationController.php
@@ -132,7 +146,31 @@ public function itemPage(Request $request, RouteMatchInterface $route_match, $pl
+      $original_langcode = 'und';

Should use LanguageInterface::LANGCODE_NOT_SPECIFIED instead of the string.

Only did a quick review, but nothing else stuck out here.

tstoeckler’s picture

FileSize
1.04 KB
18.84 KB

D'oh. Fixed that. Thanks!

vijaycs85’s picture

Patch looks good and applies to 8.0.x. +1 to RTBC.

igasi’s picture

Works fine for me. Thanks a lot.

Kristen Pol’s picture

Thanks for the patch! I've reviewed the code mainly for syntax/style.

  1. +++ b/core/modules/config_translation/src/Access/ConfigTranslationFormAccess.php
    @@ -24,18 +25,29 @@ public function access(RouteMatchInterface $route_match, AccountInterface $accou
    +        // language is not the original submission language. Although technically
    

    Nitpick: More than 80 characters.

  2. +++ b/core/modules/config_translation/src/ConfigNamesMapper.php
    @@ -404,6 +398,17 @@ public function getLangcode() {
    +    // developer did not think about a multilingual use-case, we fall back
    

    Nitpick: "use case" appears to be more common than "use-case".

  3. +++ b/core/modules/config_translation/src/Controller/ConfigTranslationController.php
    @@ -132,7 +147,31 @@ public function itemPage(Request $request, RouteMatchInterface $route_match, $pl
    +      foreach ($mapper->getconfigNames() as $config_name) {
    

    Should this be $mapper->getConfigNames()? (uppercase C)

  4. +++ b/core/modules/config_translation/src/Exception/ConfigMapperLanguageException.php
    @@ -0,0 +1,13 @@
    + * Contains
    

    Incomplete comment.

  5. +++ b/core/modules/node/src/Tests/NodeTypeTranslationTest.php
    @@ -139,6 +143,29 @@ public function testNodeTypeTitleLabelTranslation() {
    +    $this->drupalPostForm("admin/structure/types/manage/$type/fields/add-field", array('new_storage_type' => 'email', 'label' => 'Email', 'field_name' => 'email'), 'Save and continue');
    +    $this->drupalPostForm(NULL, array(), 'Save field settings');
    +    $this->drupalPostForm(NULL, array(), 'Save settings');
    

    t() functions missing, e.g. t('Save field settings')?

  6. +++ b/core/modules/node/src/Tests/NodeTypeTranslationTest.php
    @@ -139,6 +143,29 @@ public function testNodeTypeTitleLabelTranslation() {
    +    $this->drupalPostForm('admin/config/regional/language', array('site_default_language' => 'es'), 'Save configuration');
    

    t() missing, e.g. t('Save configuration')?

  7. +++ b/core/modules/node/src/Tests/NodeTypeTranslationTest.php
    @@ -139,6 +143,29 @@ public function testNodeTypeTitleLabelTranslation() {
    +    $this->drupalPostForm(NULL, array('existing_storage_name' => 'field_email', 'existing_storage_label' => 'Email'), 'Save and continue');
    

    t() missing, e.g. t('Save and continue')?

  8. +++ b/core/modules/node/src/Tests/NodeTypeTranslationTest.php
    @@ -139,6 +143,29 @@ public function testNodeTypeTitleLabelTranslation() {
    +    $this->assertText("The configuration objects have different language codes so they cannot be translated");
    

    t() missing? I see core code use t() for assertText in some cases and not others.

tstoeckler’s picture

Thanks a lot for the review @Kristen Pol!

Fixed 1.-4. Not sure about 5.-8., I generally avoid t() completely in tests, but I'll let comitters decide that, so I'm providing an extra diff (on top of the patch) for the t() changes, in case it's deemed necessary.

Kristen Pol’s picture

Thanks for the changes. I've reviewed them and they look good. I don't know about using t() in tests or not. I see both in core test code so I'm not sure which is "correct". It would be good to know if that is documented somewhere.

Kristen Pol’s picture

Issue summary: View changes
Status: Needs review » Reviewed & tested by the community
FileSize
118.39 KB

I have also tested the patch and it is working as expected. Marking RTBC. Thanks!

penyaskito’s picture

Status: Reviewed & tested by the community » Needs work

Those t() are needed as they depend on the UI strings. We don't use t() for assertion messages, etc, but we want tests to pass in case we end running them against a translated site.

penyaskito’s picture

Forgot link to docs as @kristen_pol requested: https://www.drupal.org/simpletest-tutorial-drupal7#t

tstoeckler’s picture

I'm fine with adding the t(), but

but we want tests to pass in case we end running them against a translated site

is not true. The test code is actually executed from within the child site so it will always be English, even if the parent site is not - unless we explicitly change the default language and import translations earlier in the test.

effulgentsia’s picture

Issue tags: +Triaged D8 critical

I discussed this with @xjm and @Cottser, and we agreed this is Critical, since it's a PHP fatal error that's not limited to rare circumstances.

Kristen Pol’s picture

@penyaskito - Thanks for the documentation of using t() for tests.

It appears that adding t() for the tests is all that is left for this patch but @tstoeckler added some feedback in #39 that no one has explicitly addressed yet.

catch’s picture

Status: Needs work » Reviewed & tested by the community

Per #39 I don't think we need the t() calls here at all in the tests.

The rest of the patch here looks fine to me, so moving to RTBC.

catch’s picture

Assigned: Unassigned » alexpott

Giving @alexpott a chance to look at this before it goes in.

alexpott’s picture

Status: Reviewed & tested by the community » Needs work
  1. +++ b/core/modules/config_translation/src/Access/ConfigTranslationFormAccess.php
    @@ -24,18 +25,29 @@ public function access(RouteMatchInterface $route_match, AccountInterface $accou
    +      try {
    +        // We do not use the result value, but we need to check that the mapper
    +        // only has a single language code.
    +        $this->mapper->getLangcode();
    +
    +        $target_language = $this->languageManager->getLanguage($langcode);
    +
    +        // Make sure that the target language is not locked, and that the target
    +        // language is not the original submission language. Although
    +        // technically configuration can be overlaid with translations in the
    +        // same language, that is logically not a good idea.
    +        $access =
    +          !empty($target_language) &&
    +          !$target_language->isLocked() &&
    +          (empty($this->sourceLanguage) || ($target_language->getId() != $this->sourceLanguage->getId()));
    +
    +        return $base_access->andIf(AccessResult::allowedIf($access));
    +      }
    +      catch (ConfigMapperLanguageException $exception) {
    +        // In contrast to ConfigTranslationOverviewAccess this does not grant
    +        // access to a mapper if the languages do not match.
    +        return $base_access->andIf(AccessResult::forbidden());
    +      }
         }
    

    Is there test coverage for this?

  2. +++ b/core/modules/config_translation/src/Access/ConfigTranslationOverviewAccess.php
    @@ -34,6 +35,13 @@ class ConfigTranslationOverviewAccess implements AccessInterface {
    +  protected $mapper;
    
    @@ -67,10 +75,19 @@ public function __construct(ConfigMapperManagerInterface $config_mapper_manager,
    -    $mapper = $this->configMapperManager->createInstance($route->getDefault('plugin_id'));
    ...
    +    $this->mapper = $this->configMapperManager->createInstance($route->getDefault('plugin_id'));
    

    Why are we making this change - I don't think we should be adding this protected property - it is only used in this method - adding it here means that PHP couldn't garbage collect it because the reference will exist until the access check service is destroyed.

  3. +++ b/core/modules/config_translation/src/ConfigNamesMapper.php
    @@ -385,17 +386,10 @@ public function getTypeLabel() {
    -      throw new \RuntimeException('A config mapper can only contain configuration for a single language.');
    +      throw new ConfigMapperLanguageException('A config mapper can only contain configuration for a single language.');
    

    We need to update the interface docs for this exception

  4. +++ b/core/modules/config_translation/src/ConfigNamesMapper.php
    @@ -404,6 +398,17 @@ public function getLangcode() {
    +    return $this->configFactory->get($config_name)->get('langcode') ?: 'en';
    

    Is this tested? I can't see where.

  5. +++ b/core/modules/config_translation/src/Controller/ConfigTranslationController.php
    @@ -8,11 +8,15 @@
    +use Drupal\config_translation\ConfigNamesMapper;
    

    Not used

  6. +++ b/core/modules/config_translation/src/Controller/ConfigTranslationController.php
    @@ -210,6 +249,9 @@ public function itemPage(Request $request, RouteMatchInterface $route_match, $pl
    +        // Even if the mapper contains multiple language codes, the source
    +        // configuration can still be edited.
    +        '#access' => ($langcode == $original_langcode) || $operations_access,
    

    Is there test coverage for this?

tstoeckler’s picture

Assigned: alexpott » Unassigned
Issue tags: +DrupalBCDays
esolitos’s picture

Patch from #34 didn't apply on 8.0.6, I rerolled the changes.

swentel’s picture

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

this should be rolled against 8.1.x, 8.0.x is out of support soon.

esolitos’s picture

The patch from #46 applies on 8.1.x as for today.
I haven't tested the functionality itself 'tho.

esolitos’s picture

Status: Needs work » Needs review

Triggering the bot for testing the new patch on 8.1.x

klausi’s picture

Status: Needs review » Needs work
  1. +++ b/core/modules/config_translation/src/Access/ConfigTranslationFormAccess.php
    @@ -24,18 +25,29 @@ public function access(RouteMatchInterface $route_match, AccountInterface $accou
    +        return $base_access->andIf(AccessResult::forbidden());
    

    this looks a bit obscure. Can you use "return AccessResult::forbidden()->inheritCacheability($base_access);" instead?

  2. +++ b/core/modules/config_translation/src/ConfigMapperInterface.php
    @@ -208,6 +208,17 @@ public function getConfigData();
    +  public function getLangcodeFromConfig($config_name);
    

    Hm, we cannot introduce new methods on interfaces like that since D8 is already released. Either you mark this interface as @internal, so that people know that this interface is fake and not actually an interface because we change it all the time - or you create a new interface that a ConfigMapper can optionally implement (LangcodeFromConfigInterface?).

  3. +++ b/core/modules/config_translation/src/Controller/ConfigTranslationController.php
    @@ -132,7 +147,31 @@ public function itemPage(Request $request, RouteMatchInterface $route_match, $pl
    +        'message' => ['#markup' => t('The configuration objects have different language codes so they cannot be translated:')],
    

    must use $§this->t()

alvar0hurtad0’s picture

Status: Needs work » Needs review
FileSize
2.24 KB
19 KB

I'm not really sure about second topic on #50, but I think this solves the other two topics.

alexpott’s picture

Status: Needs review » Needs work
  1. +++ b/core/modules/config_translation/src/ConfigMapperInterface.php
    @@ -203,6 +203,20 @@ public function getConfigData();
    +   *
    +   * @internal
    +   *   Fake interface.
    

    I don't think this belongs here. Let's remove it.

    I think we've covered adding methods to interfaces in other issues. I think contrib using ConfigMapperInterface on an object is extremely unlikey - it is more likely that contrib is using ConfigMapperInterface objects provided by core and these will not be broken by adding the method since they are just calling methods on it. See www.drupal.org/core/d8-bc-policy#interfaces

  2. +++ b/core/modules/config_translation/src/Controller/ConfigTranslationController.php
    @@ -3,11 +3,15 @@
    +use Drupal\config_translation\ConfigNamesMapper;
    

    Not used - needs to be removed.

  3. +++ b/core/modules/config_translation/src/Controller/ConfigTranslationController.php
    @@ -127,7 +142,31 @@ public function itemPage(Request $request, RouteMatchInterface $route_match, $pl
    +        $items[] = $config_name . ': ' . $langcode;
    

    This needs to be translated. In french, for example, there always has to be a space before a colon. So $items[] = $this->t('@config_name: @langcode', [... variables

  4. +++ b/core/modules/config_translation/src/Controller/ConfigTranslationController.php
    @@ -127,7 +142,31 @@ public function itemPage(Request $request, RouteMatchInterface $route_match, $pl
    +        ]
    

    Missing a comma

  5. +++ b/core/modules/config_translation/src/Controller/ConfigTranslationController.php
    @@ -127,7 +142,31 @@ public function itemPage(Request $request, RouteMatchInterface $route_match, $pl
    +    }
    +
    +
         if (!isset($languages[$original_langcode])) {
    

    Need only one empty line here.

  6. +++ b/core/modules/config_translation/src/Exception/ConfigMapperLanguageException.php
    @@ -0,0 +1,13 @@
    +/**
    + * @file
    + * Contains \Drupal\config_translation\Exception\ConfigMapperLanguageException.
    + */
    

    Don't need this anymore.

  7. +++ b/core/modules/config_translation/src/Form/ConfigTranslationFormBase.php
    @@ -3,7 +3,10 @@
    +use Drupal\config_translation\ConfigNamesMapper;
    +use Drupal\config_translation\Exception\ConfigMapperLanguageException;
    

    Not used. Need to be removed.

  8. +++ b/core/modules/config_translation/src/Form/ConfigTranslationFormBase.php
    @@ -76,11 +86,13 @@
    +   * @param \Drupal\Core\Render\RendererInterface
    

    Needs a description.

Hummer’s picture

#51 worked for me on Drupal 8.1

k4’s picture

If you set up a multilingual site without configuration translation enabled and later enable the module you may not be able to edit content types any longer because of this issue.

This solves the problem (supposed the default language is english):

Export the config:
sync/*.yml -> untranslated config
sync/language/[langcode]/*.yml -> translated config

Now there are in sync/*.yml several configs which are not langcode: en.

Change all config in sync/*.yml to langcode: en and import the config back to the site.

Now you are able the edit the content types again. In future you have to edit content types only in the english admin interface so that the config does not get mixed up again.

The same should work with a non english default languages, but I have not tested this.

---

To help to prevent this issue, perhaps drupal should warn you, if you try to save a content type configuration with different languages?

tstoeckler’s picture

tstoeckler’s picture

Title: Show helpful message or be silent (but do not fatal!) when configuration files have different source language codes and cannot be translated » Show helpful message (do not fatal!) when configuration files have different source language codes and cannot be translated
iszabi’s picture

Hi,

I 've got an error when I'd like to translate a field on contact form.

Error after saved translation filed:

Notice: Undefined index: field.storage.contact_message.field_mennyiseg in Drupal\config_translation\Form\ConfigTranslationFormBase->submitForm() (line 220 of core/modules/config_translation/src/Form/ConfigTranslationFormBase.php).
Drupal\config_translation\Form\ConfigTranslationFormBase->submitForm(Array, Object) (Line: 36)
Drupal\config_translation\Form\ConfigTranslationAddForm->submitForm(Array, Object)
call_user_func_array(Array, Array) (Line: 111)
Drupal\Core\Form\FormSubmitter->executeSubmitHandlers(Array, Object) (Line: 51)
Drupal\Core\Form\FormSubmitter->doSubmitForm(Array, Object) (Line: 583)
Drupal\Core\Form\FormBuilder->processForm('config_translation_add_form', Array, Object) (Line: 314)
Drupal\Core\Form\FormBuilder->buildForm('config_translation_add_form', Object) (Line: 74)
Drupal\Core\Controller\FormController->getContentResult(Object, Object)
call_user_func_array(Array, Array) (Line: 123)
Drupal\Core\EventSubscriber\EarlyRenderingControllerWrapperSubscriber->Drupal\Core\EventSubscriber\{closure}() (Line: 574)
Drupal\Core\Render\Renderer->executeInRenderContext(Object, Object) (Line: 124)
Drupal\Core\EventSubscriber\EarlyRenderingControllerWrapperSubscriber->wrapControllerExecutionInRenderContext(Array, Array) (Line: 97)
Drupal\Core\EventSubscriber\EarlyRenderingControllerWrapperSubscriber->Drupal\Core\EventSubscriber\{closure}()
call_user_func_array(Object, Array) (Line: 139)
Symfony\Component\HttpKernel\HttpKernel->handleRaw(Object, 1) (Line: 62)
Symfony\Component\HttpKernel\HttpKernel->handle(Object, 1, 1) (Line: 57)
Drupal\Core\StackMiddleware\Session->handle(Object, 1, 1) (Line: 48)
Drupal\Core\StackMiddleware\KernelPreHandle->handle(Object, 1, 1) (Line: 98)
Drupal\page_cache\StackMiddleware\PageCache->pass(Object, 1, 1) (Line: 77)
Drupal\page_cache\StackMiddleware\PageCache->handle(Object, 1, 1) (Line: 47)
Drupal\Core\StackMiddleware\ReverseProxyMiddleware->handle(Object, 1, 1) (Line: 50)
Drupal\Core\StackMiddleware\NegotiationMiddleware->handle(Object, 1, 1) (Line: 23)
Stack\StackedHttpKernel->handle(Object, 1, 1) (Line: 628)
Drupal\Core\DrupalKernel->handle(Object) (Line: 19)

------------------------------------------------------

Latest patch (https://www.drupal.org/files/issues/2595535-55.patch) does not work for Drupal version 8.1.1. (released on 4 May)

Patch displayed errors:

Checking patch core/modules/config_translation/src/Access/ConfigTranslationFormAccess.php...
error: while searching for:

namespace Drupal\config_translation\Access;

use Drupal\Core\Access\AccessResult;
use Drupal\Core\Routing\RouteMatchInterface;
use Drupal\Core\Session\AccountInterface;

error: patch failed: core/modules/config_translation/src/Access/ConfigTranslationFormAccess.php:2
error: core/modules/config_translation/src/Access/ConfigTranslationFormAccess.php: patch does not apply
Checking patch core/modules/config_translation/src/Access/ConfigTranslationOverviewAccess.php...
error: while searching for:

namespace Drupal\config_translation\Access;

use Drupal\Core\Language\LanguageManagerInterface;
use Drupal\config_translation\ConfigMapperManagerInterface;
use Drupal\Core\Access\AccessResult;

error: patch failed: core/modules/config_translation/src/Access/ConfigTranslationOverviewAccess.php:2
error: core/modules/config_translation/src/Access/ConfigTranslationOverviewAccess.php: patch does not apply
Checking patch core/modules/config_translation/src/ConfigMapperInterface.php...
error: while searching for:
public function getLangcode();

/**
* Sets the original language code.
*
* @param string $langcode

error: patch failed: core/modules/config_translation/src/ConfigMapperInterface.php:203
error: core/modules/config_translation/src/ConfigMapperInterface.php: patch does not apply
Checking patch core/modules/config_translation/src/ConfigNamesMapper.php...
error: while searching for:

namespace Drupal\config_translation;

use Drupal\Core\Config\ConfigFactoryInterface;
use Drupal\Core\Config\TypedConfigManagerInterface;
use Drupal\Core\Language\LanguageInterface;

error: patch failed: core/modules/config_translation/src/ConfigNamesMapper.php:2
error: core/modules/config_translation/src/ConfigNamesMapper.php: patch does not apply
Checking patch core/modules/config_translation/src/Controller/ConfigTranslationController.php...
error: while searching for:
namespace Drupal\config_translation\Controller;

use Drupal\config_translation\ConfigMapperManagerInterface;
use Drupal\Core\Access\AccessManagerInterface;
use Drupal\Core\Controller\ControllerBase;
use Drupal\Core\Language\Language;
use Drupal\Core\Language\LanguageManagerInterface;
use Drupal\Core\PathProcessor\InboundPathProcessorInterface;
use Drupal\Core\Routing\RouteMatch;
use Drupal\Core\Routing\RouteMatchInterface;
use Drupal\Core\Session\AccountInterface;

error: patch failed: core/modules/config_translation/src/Controller/ConfigTranslationController.php:3
error: core/modules/config_translation/src/Controller/ConfigTranslationController.php: patch does not apply
Checking patch core/modules/config_translation/src/Exception/ConfigMapperLanguageException.php...
error: core/modules/config_translation/src/Exception/ConfigMapperLanguageException.php: already exists in working directory
Checking patch core/modules/config_translation/src/Form/ConfigTranslationFormBase.php...
error: while searching for:

use Drupal\config_translation\ConfigMapperManagerInterface;
use Drupal\Core\Config\TypedConfigManagerInterface;
use Drupal\Core\Routing\RouteMatchInterface;
use Drupal\Core\TypedData\TypedDataInterface;
use Drupal\Core\Form\BaseFormIdInterface;

error: patch failed: core/modules/config_translation/src/Form/ConfigTranslationFormBase.php:4
error: core/modules/config_translation/src/Form/ConfigTranslationFormBase.php: patch does not apply
Checking patch core/modules/node/src/Tests/NodeTypeTranslationTest.php...
error: while searching for:
* @var array
*/
public static $modules = array(
'config_translation',
'node',
);

error: patch failed: core/modules/node/src/Tests/NodeTypeTranslationTest.php:23
error: core/modules/node/src/Tests/NodeTypeTranslationTest.php: patch does not apply
------------------
Server environment:
mySQL: 5.6.19-67.0, for debian-linux-gnu (x86_64)
PHP: 7.0.7
Webserver: Apache/2.4.20

Note: After I've saved translated field, the results: "Successfully updated Magyar translation."
So after 'drush cr' the result has been displeyd on form successfull.

tstoeckler’s picture

Status: Needs review » Needs work
Issue tags: +Needs reroll

Maybe that's a chance for someone to work on a critical issue.

Marking Novice for the rerolling, the issue in general is of course not novice.

tstoeckler’s picture

Issue tags: +Novice
esolitos’s picture

Issue tags: -Needs reroll, -Novice

I just tested the patch from #55: it applies successfully on 8.1.1, on latest commit on branch 8.1.x and also on 8.2.x.

tstoeckler’s picture

Status: Needs work » Needs review

Thanks @esolitos! Then it just needs review now.

alexpott’s picture

Status: Needs review » Needs work
  1. +++ b/core/modules/config_translation/src/Access/ConfigTranslationOverviewAccess.php
    @@ -29,6 +30,13 @@ class ConfigTranslationOverviewAccess implements AccessInterface {
       /**
    +   * The configuration mapper to check access for.
    +   *
    +   * @var \Drupal\config_translation\ConfigMapperInterface
    +   */
    +  protected $mapper;
    

    Why are we storing the mapper as a protected property - I'm not sure it should be.

  2. +++ b/core/modules/config_translation/src/Form/ConfigTranslationFormBase.php
    @@ -47,6 +48,13 @@
       /**
    +   * The renderer.
    +   *
    +   * @var \Drupal\Core\Render\RendererInterface
    +   */
    +  protected $renderer;
    
    @@ -76,11 +84,14 @@
    +   * @param \Drupal\Core\Render\RendererInterface
    +   *   The renderer.
    ...
    -  public function __construct(TypedConfigManagerInterface $typed_config_manager, ConfigMapperManagerInterface $config_mapper_manager, ConfigurableLanguageManagerInterface $language_manager) {
    +  public function __construct(TypedConfigManagerInterface $typed_config_manager, ConfigMapperManagerInterface $config_mapper_manager, ConfigurableLanguageManagerInterface $language_manager, RendererInterface $renderer) {
    ...
    +    $this->renderer = $renderer;
    
    @@ -90,7 +101,8 @@ public static function create(ContainerInterface $container) {
    +      $container->get('renderer')
    

    I don;t think this is needed anymore.

vijaycs85’s picture

Status: Needs work » Needs review
FileSize
17.25 KB
1.83 KB

#62.1 - ConfigTranslationFormAccess is using the mapper updated from ConfigTranslationOverviewAccess in access method.
#62.2 - Fixed


Update: Applies to 8.2.x too.

Kristen Pol’s picture

Issue summary: View changes
Status: Needs review » Reviewed & tested by the community
FileSize
214.03 KB

I have tested the patch in #63 with the instructions from the summary:

  1. Install a drupal 8 in Spanish.
  2. In "admin/config/regional/language/add" add Inglés language.
  3. Go to "/en/admin/modules" install "Configuration Translation" and "Content Translation" modules.
  4. Go to "/en/admin/structure/types/manage/page/fields", click in "Add field", in "Re-use an existing field', select "Image: Field image", "Save and continue".

and did not get an exception. Here is the a screenshot after adding the image field.

Based on the comments in #62 and interdiff in #63, this looks RTBC so marking it.

alexpott’s picture

+++ b/core/modules/config_translation/src/Access/ConfigTranslationFormAccess.php
@@ -19,18 +20,29 @@ public function access(RouteMatchInterface $route_match, AccountInterface $accou
+        // We do not use the result value, but we need to check that the mapper
+        // only has a single language code.
+        $this->mapper->getLangcode();

+++ b/core/modules/config_translation/src/Access/ConfigTranslationOverviewAccess.php
@@ -29,6 +30,13 @@ class ConfigTranslationOverviewAccess implements AccessInterface {
   /**
+   * The configuration mapper to check access for.
+   *
+   * @var \Drupal\config_translation\ConfigMapperInterface
+   */
+  protected $mapper;

@@ -62,10 +70,19 @@ public function __construct(ConfigMapperManagerInterface $config_mapper_manager,
+    $this->mapper = $this->configMapperManager->createInstance($route->getDefault('plugin_id'));
+    $this->mapper->populateFromRouteMatch($route_match);

I'm not sure that this is a great way to pass around the mapper object. I've not got any ideas yet of a better way.

catch’s picture

  1. +++ b/core/modules/config_translation/src/Access/ConfigTranslationFormAccess.php
    @@ -19,18 +20,29 @@ public function access(RouteMatchInterface $route_match, AccountInterface $accou
    +      try {
    +        // We do not use the result value, but we need to check that the mapper
    +        // only has a single language code.
    +        $this->mapper->getLangcode();
    +
    

    Can we just explicitly say we're calling the method to give it a chance to throw the exception?

  2. +++ b/core/modules/config_translation/src/Access/ConfigTranslationFormAccess.php
    @@ -19,18 +20,29 @@ public function access(RouteMatchInterface $route_match, AccountInterface $accou
    +          !empty($target_language) &&
    

    Does this have to be !empty($target_language)? Can't just do $target_language since we always set it above?

  3. +++ b/core/modules/config_translation/src/Access/ConfigTranslationFormAccess.php
    @@ -19,18 +20,29 @@ public function access(RouteMatchInterface $route_match, AccountInterface $accou
    +          (empty($this->sourceLanguage) || ($target_language->getId() != $this->sourceLanguage->getId()));
    

    Any reason not to use strict comparison?

nevergone’s picture

#63 tested and works well!

catch’s picture

Status: Reviewed & tested by the community » Needs review

CNR for #64/#65.

Kristen Pol’s picture

Clarification: Needs review for #65 and #66.

catch’s picture

Yes! Off by one error...

manuel.afonso’s picture

Looking forward for a solution, thank you all for your contributions.

If you have a partner using an interface language other than yours, you won't be able to edit content types any longer because of this issue.

I'm just starting with Drupal and couldn't apply the patch so I went for this temporary solution:

if (count(array_unique($langcodes)) > 1) {
	 return 'en'; 
         //throw new \RuntimeException('A config mapper can only contain configuration for a single language.');
    }

in ConfigNamesMapper.php

tstoeckler’s picture

I think I came up with a way to solve #65 in a somewhat elegant way, would love to hear what you think. Also fixes #66. Unfortunately this makes the interdiff slightly unreadable, it might make sense to look at the actual patch instead, at least for the two access check classes.

Status: Needs review » Needs work

The last submitted patch, 72: 2595535-72-config-translation-langcode-exception.patch, failed testing.

tstoeckler’s picture

Oops, of course the method parameter name has to match the routing parameter. So not changing that, as changing the route path would be a little scope-creep-y in my opinion...

Gábor Hojtsy’s picture

Status: Needs review » Reviewed & tested by the community

Discussed this with @tstoeckler on the multilingual meeting. The new access check inheritance looks nice to me, it does indeed solve the problem that @alexpott raised in #65. It also addresses all the problems raised by catch in #66, even though I did not find all the solutions at first, but @tstoeckler walked me through them. Looks good to go then :)

catch’s picture

Committed/pushed to 8.2.x, thanks!

Leaving at RTBC for 8.1.x, want to get a new release out for #2761865: Update from 8.1.3 to 8.1.4 breaks site seemingly permanently and also want to give this time before it gets into a tagged release.

  • catch committed ef3700f on 8.2.x
    Issue #2595535 by tstoeckler, swentel, vijaycs85, alvar0hurtad0,...

  • catch committed 7bbcc3e on 8.2.x
    Revert "Issue #2595535 by tstoeckler, swentel, vijaycs85, alvar0hurtad0...
catch’s picture

8.2.x broke. Reverted and sending for re-test.

catch’s picture

Apparently messed up fixing the drupalcs issues locally, so uploading a patch for that.

  • catch committed fe94d15 on 8.2.x
    Issue #2595535 by tstoeckler, swentel, vijaycs85, alvar0hurtad0,...

  • catch committed 7aebc48 on 8.1.x
    Issue #2595535 by tstoeckler, swentel, vijaycs85, alvar0hurtad0,...
catch’s picture

Status: Reviewed & tested by the community » Fixed

OK that passed. Committed/pushed to 8.2.x and cherry-picked to 8.1.x. Thanks!

Benia’s picture

Should I run #80 in an all-core site which is Drupal 8.1.6 or should I downgrade before that?

I wish to run it at best.

catch’s picture

@Benia you can apply the patch to your 8.1.6 install (see https://www.drupal.org/patch) if you need the fix immediately, or wait about four weeks for 8.1.7.

penyaskito’s picture

Glad to see this one fixed. Thanks so much for working on it!

+++ b/core/modules/config_translation/src/Controller/ConfigTranslationController.php
@@ -78,14 +88,17 @@ class ConfigTranslationController extends ControllerBase {
-  public function __construct(ConfigMapperManagerInterface $config_mapper_manager, AccessManagerInterface $access_manager, RequestMatcherInterface $router, InboundPathProcessorInterface $path_processor, AccountInterface $account, LanguageManagerInterface $language_manager) {
+  public function __construct(ConfigMapperManagerInterface $config_mapper_manager, AccessManagerInterface $access_manager, RequestMatcherInterface $router, InboundPathProcessorInterface $path_processor, AccountInterface $account, LanguageManagerInterface $language_manager, RendererInterface $renderer) {

Don't we consider changing constructor an API break?

Benia’s picture

FileSize
88.43 KB

Its the first time I run a core patch. When I did "git applay patch 2595535-80.patch" it seem to have failed but when I did "patch < 2595535-80.patch" It seems to have succeeded.

Please see attached image with errors from Ubuntu bash.

Benia’s picture

Status: Fixed » Needs review
Benia’s picture

Status: Needs review » Fixed
catch’s picture

@penyaskito no explicitly don't consider them an API: https://www.drupal.org/core/d8-bc-policy#constructors

Normally we'd avoid changing them in a patch release, however given this fixes a critical bug and the constructor is specifically for a controller which should never be used directly (not even subclassed) I think it's fine in 8.1.x

Benia’s picture

FileSize
62.22 KB

Its the first time I patch the core and I think I had a problem while patching. Can you please take a look at the attached file?

Benia’s picture

Status: Fixed » Needs review
catch’s picture

Status: Needs review » Fixed

Please open a new support request for applying the core patch and link to it from here.

You could also use the development release of 8.1.x (but better to do this on a test site first, same as patching).

Benia’s picture

Did that. Please see here.

Status: Fixed » Closed (fixed)

Automatically closed - issue fixed for 2 weeks with no activity.

Heihachi88’s picture

#80 worked. Drupal 8.1.7. When they will merge this patch in to the core?

esolitos’s picture

Patch is committed on both 8.1 and 8.2.
Drupal 8.1.7 was a security release, so you'll find it in 8.1.8.

Gábor Hojtsy’s picture

Issue tags: -sprint

Removing from sprint, thanks all again!

@baux’s picture

I've got a fresh Drupal 8.2.1 installation and I'm experiencing this problem.

In my site I've installed Drupal in english, made some configurations, added some modules and then I've activated "Configuration Translation", "Interface Translation" and "Languages" ("Content Translation" is not active).

I' don't have any error about languages in my recent log message, but the following message is shown in the filed(s) translation:

The configuration objects have different language codes so they cannot be translated:

  field.field.node.videos.body: en
  field.storage.node.body: es

This error appears just on new content types... Articles can be properly translated.

I've seen that the patch should be included in the new releases, but I've unsuccessfully tried to apply it... the system says that it's already applied.

I've just updated the site to Drupal 8.2.2 with no solution to this problem.

Language configuration:

  • The site default language is "Spanish"
  • As detection method I've just enabled "User" and I'm accessing as admin in English
  • The default "Selected language" is set to Site's default language (Spanish)

Don't know what to do... please help...

Alex Bukach’s picture

@baux, what you probably can do is to export one of configurations (field.field.node.videos.body or field.storage.node.body), modify it to match the languages and import it again.