Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Empty fields with nested repeaters #307

Closed
AlanNoeOrtega opened this issue Oct 11, 2017 · 32 comments
Closed

Empty fields with nested repeaters #307

AlanNoeOrtega opened this issue Oct 11, 2017 · 32 comments

Comments

@AlanNoeOrtega
Copy link

could someone help me? I got a problem using the plugin with nested repeater. I have my fields like:

[MLRepeater]

  • Textfield ROOT
    [Repeater]
    -- Text Field CHILD
    -- Rich Editor CHILD
    ...
    [/Repeater]
    [Repeater]
    -- Text Field CHILD
    -- Rich Editor CHILD
    ...
    [/Repeater]
    ...
    [/MLRepeater]

When I change language, "Textfield ROOT" changes correctly, however "Text Field CHILD" appears blank, empty, even if data in DB are correct and when I print a dump($this) for MLRepeater "data" is correct. But, repeaters inside are empty. When I tried to get saved data in Frontend, Everything is right.

@yarbala
Copy link

yarbala commented Nov 28, 2017

I have same issue

@Fl0Cri
Copy link

Fl0Cri commented Dec 21, 2017

Me too in a slightly different context. I was doing tests with https://github.com/daftspunk/oc-test-plugin
The repeater I tried to use is in the Countries section, in the States tab. It is defined like this:

states:
    tab: States
    type: repeater
    form:
        fields:
            title:
                label: State
            item:
                type: repeater
                prompt: Add new suburb
                form:
                    fields:
                        subtitle:
                            label: Suburb
                            span: left

I saved these values (same in my other language except that EN was replaced by FR):
edit countries _ octobercms - google chrome 2017-12-21 09 32 57

If I try to switch to my other langauge, I get 2 empty text fields inside my Test2 node that doesn't exist in the saved data:
edit countries _ octobercms - google chrome 2017-12-21 09 35 43

Switching back to the default locale also adds the empty fields.
If I don't save and reload the page, everything is correct again (until I try to switch locale).

@LukeTowers LukeTowers changed the title Empty fields with neasted repeaters. Empty fields with nested repeaters Dec 21, 2017
@ChVuagniaux
Copy link

Discover the same issue with OctoberCMS 434 & RainLab Translate 1.3.8

For reproduce these issue you should have translated nested repeaters. If you have RainLab Pages installed you can simply add a repeater on RainLab.Pages by adding this code https://gist.github.com/ChVuagniaux/003bb50cc1c8e08a9396f0f2bfdd15ee to your plugin file.

First behavior : empty repeaters are added when switching locale

For reproduce :

  1. Create fields in one language and save it
  2. Refresh the page
  3. Switch to an other language and add one item
  4. Save
  5. See many blank items created in two languages

Demo : http://take.ms/ZSSfE

if you create the following structure:

- Title 1
  - Content 1a
- Title 2
  - Content 2a
- Title 3
  - Content 3a
  - Content 3b
  - Content 3c

and click switch button and choose the same lang (default language)

you will get something like that

- Title 1
  - Content 1a
  - ""
  - ""
  - ""
  - ""
- Title 2
  - ""
  - Content 2a
  - ""
  - ""
  - ""
- Title 3
  - ""
  - ""
  - Content 3a
  - Content 3b
  - Content 3c

Switching to the same language is obviously not a normal action but this reflect the problem we have when switching to an not empty language.

Second behavior : removing one of these empty fields in one language will also remove it in main language

For reproduce :

  1. Switch to an other language
  2. Remove one of the empty items
  3. Save
  4. Switch back to the main language
  5. Now the field is only "visually removed" not listed but if you don't save this lang it will be keeped
  6. Save
  7. Refresh and see that the field no more exist in main language

Demo : http://take.ms/qpp5p

@pvullioud
Copy link

A bounty have been added on this issue : https://www.bountysource.com/issues/50188520-empty-fields-with-nested-repeaters
@LukeTowers Could you add the bounty tag? thanks

@Fl0Cri
Copy link

Fl0Cri commented Apr 27, 2018

I did some experiments yesterday and here's what I found:
For me the problem is related to this https://github.com/octobercms/october/blob/master/modules/backend/formwidgets/Repeater.php#L199

At this line, $loadedIndexes contains the correct values of the repeater we are working on (in @ChVuagniaux previous example, for children of "Title 3" it's [3, 4, 5]).
But what we do at this line is to fetch the ___index_item from $_POST. After this line, $itemIndexes contains [1, 2, 3, 4, 5] (still with the previous example).
The loop a few lines later will generate 5 fields with only 3, 4 and 5 filled.

I tried to modify the http request that is sent when changing language, remove these ___index_item[] and send it again and this time I got a correct answer from the server without duplicated repeaters.

I write it here hoping in may help to find a solution, but I am realy unsure about what these parameters are used for and what could break when they are removed.

@anastasiauz
Copy link

anastasiauz commented May 2, 2018

UPDATE: I was wrong, the problem is more complicated and same as described by @ChVuagniaux Changing type from textarea to richeditor doesn't influence at all, it was just circumstance.
Need a fix very much. I sent small bounty, is there any hope that it will be fixed soon? Is there some fixed
amount of bounty which can make this happen until May, 7th? My project very much needs this feature.

Translate 1.4.0, October 435.
I am experiencing issue with extra blank fields in nested repeater too, impossible to delete them. Also data from some fields disappeared (after I tried to delete unneeded fields). The repeater worked ok until I changed field type in nested field to richeditor (was textarea) and updated main language to hold less number of fields. Structure is:

longread:
      type: repeater 
      form:
        fields:          
          mediablock:            
            type: repeater          (*NESTED repeater with problem)  
            form:
              fields:
                photo:
                  type: mediafinder     
                text:                  
                  type: richeditor (*THIS type causes problem)

@Fl0Cri
Copy link

Fl0Cri commented May 31, 2018

I found a quick "fix" to this problem. It's a temp solution because it introduces a new bug (see below). But in some use cases the new bug may be less problematic than the actual behavior.

Here's what I did: at this line https://github.com/octobercms/october/blob/master/modules/backend/formwidgets/Repeater.php#L199
Replace this:

$itemIndexes = post($this->indexInputName, $loadedIndexes);

by this:

$itemIndexes = $loadedIndexes;

Note that it's an October hack, not a translate plugin hack.

This solves the problem of empty fields being created when switching the repeater language.
The problem with this fix is that if you create a new repeater item (level 1) and try to add a child to this item (level 2), you will get an error and the field won't be created. But it works if you save the page before adding the child item.

If I understood correctly the repeaters logic, the actual implementation doesn't support correctly nested repeaters because when you ask to create a new repeater item, along with the POST data is sent a ___index_{fieldName} array. {fieldName} being the name of a repeater node, and the values being the indexes of all sub-items of all the repeaters with this name in the whole form.

This array is then used in the back-end to rebuild a representation of the repeater as it is in the user browser. If it's not done, like in my fix, the back-end doesn't know the existance of non-saved fields and cannot create sub-elements.

What happens actually is that in the backend representation, all repeater nodes at a given level will have the ammount of children of the node with the highest children count at the same level.

The problem isn't noticeable as long as the broken representation stays in the back-end. But when switching locale with the translate plugin, it is sent to the browser to refresh the form.

@alxy
Copy link
Contributor

alxy commented Jun 6, 2018

I tried to reproduce this behavior and actually realized, that the data looks correct in the database, but the repeater renders these empty fields, so it is a markup/javascript issue in my eyes. Can anyone of you ( @ChVuagniaux @Fl0Cri @pvullioud ) confirm that?

@pszczegielniak
Copy link

pszczegielniak commented Jun 6, 2018

@alxy Unfortunetly is not that simple. I was debuging a little and there are bugs in repeater in october core. I found a fix in context of using nested repeaters in pages plugin. But unfortunetly it does not seems to work when used on normal backend pages.

@alxy
Copy link
Contributor

alxy commented Jun 6, 2018

@pszczegielniak Sure, if you safe the data again with the empty fields added, then these are in the database as well. But for me it appears like this:
1.) Prepare some data in the database, for both the original model and in the translate attributes table.
2.) If I now refresh, the main language is displayed correctly. However if I change to another language, I can see more blank fields added.
3.) If I change back to the orignal language, still there are new blank fields added.

That leads to the conclusion, there must be something wrong with the processing and rendering of the existing items, when triggered via the onSwitchLocale handler.

@Fl0Cri
Copy link

Fl0Cri commented Jun 8, 2018

@alxy in fact, the process of saving to the database and switching locale is very different.
I'll try to explain the difference using an example with these base data (from the oc-test-plugin -> countries -> states):

- Test1 EN
    - Test1 EN Sub1
    - Test1 EN Sub2
- Test2 EN
    - Test2 EN Sub1

If you do something, either saving or trigering an ajax handler (here I click on the button to add a new "state" to the repeater), a POST request with the following data is issued:
outils de developpement - edit countries _ octobercms - http___localhost_october_ibackend_october_test_countries_update_7 2018-06-08 08 33 01

Now if we are in the context of saving the data to the DB, it's easy: just take data pointed by B, JSONize them and write.

The problem with ajax handlers (particulary onSwitchLocale but also onAddItem) is that a totally different way is used to build the repeater tree (and then perform the ajax action on it): it takes the data saved in DB and try to complete them with data that havn't already be saved using A.
But as A is flat, what October finds out to be the "actual" structure is:

- Test1 EN            (because in saved data)
    - Test1 EN Sub1   (because in saved data)
    - Test1 EN Sub2   (because in saved data)
    - ""              (because of __index_item[2])
- Test2 EN
    - ""              (because of __index_item[0])
    - ""              (because of __index_item[1])
    - Test2 EN Sub1   (because in saved data)

Depending on what ajax handler we are running, this may be harmless. For example onAddItem will:

  • Try to find the parent node in the (broken) repeater structure
  • Create a formWidget for the new item and add it to its parent
  • Return the html of the new item

The JS will receive this html and paste it at the right place. The fact that the structure that October thinks to be right is broken doesn't matter.

But for onSwitchLocale, the synopsis of the handler (if I remember correctly) is something like:

  • Take the (broken) structure
  • Replace values in it with the translated data
  • Return the html of the whole (broken) structure

And here the JS will overwrite the "correct" data in the browser.

Probably, the best thing to do would be to use B instead of A (from screenshot above) to rebuild the repeater structure. @LukeTowers tell me if it's a bad idea.
I cannot tell if it will directly solve the onSwitchLocale problem, but what is sure is that translate plugin can't work correctly with the broken structure.

I cannot work much on this these times, so may someone else find a fix quickly :)

@LukeTowers
Copy link
Contributor

@Fl0Cri I've sent a message to @daftspunk to get his input on this since he built the repeater in the first place :) We should be able to come up with a fix once he sets his mind to it. Thanks to everyone for the great work on digging into the cause of the issue so far!

@pvullioud
Copy link

Friendly reminder about this issue and the bounty

@Ladylain
Copy link

Hi guys, i'm looking for a solution to this bug,

Actually i've found that when you're switching locale, some datas change:

Before i get this changes, i need to create in my static page a "title" repeater and a "subtitle" repeater for FR locale, then i switch to EN locale and this time, i create just "subtitle" repeater and "content" repeater (which has richeditor, image field and radiobutton in it), until this everything is ok. But when i switch again to FR locale, it starts messing up as you can see below .

// Switching to locale FR
formFieldValue: "[{"title":"titre fr","_group":"title"},{"subtitle":"sub fr","_group":"subtitle"}]"
initLockerData: "[{"title":"titre fr","_group":"title"},{"subtitle":"sub fr","_group":"subtitle"}]"
thisFormWidget: "[{"fields":{"title":{"label":"Titre principal","type":"text"}},"tabs":{"fields":[]},"secondaryTabs":{"fields":[]},"model":{"settings":[]},"data":{"title":"titre fr","_group":"title"},"context":null,"arrayName":"viewBag[sections][0]","isNested":true,"sessionKey":null,"previewMode":false,"config":{"fields":{"title":{"label":"Titre principal","type":"text"}},"model":{"settings":[]},"data":{"title":"titre fr","_group":"title"},"alias":"formPaged41d8cd98f00b204e9800998ecf8427e5ba49dbe8910bViewBagSectionsForm0","arrayName":"viewBag[sections][0]","isNested":true},"alias":"formPaged41d8cd98f00b204e9800998ecf8427e5ba49dbe8910bViewBagSectionsForm0","implement":null,"vars":[],"layout":null,"suppressLayout":false,"assetPath":"\/modules\/backend\/widgets\/form\/assets"},{"fields":{"subtitle":{"label":"Sous-titre (phrase d'accroche)","type":"text"}},"tabs":{"fields":[]},"secondaryTabs":{"fields":[]},"model":{"settings":[]},"data":{"subtitle":"sub fr","_group":"subtitle"},"context":null,"arrayName":"viewBag[sections][1]","isNested":true,"sessionKey":null,"previewMode":false,"config":{"fields":{"subtitle":{"label":"Sous-titre (phrase d'accroche)","type":"text"}},"model":{"settings":[]},"data":{"subtitle":"sub fr","_group":"subtitle"},"alias":"formPaged41d8cd98f00b204e9800998ecf8427e5ba49dbe8910bViewBagSectionsForm1","arrayName":"viewBag[sections][1]","isNested":true},"alias":"formPaged41d8cd98f00b204e9800998ecf8427e5ba49dbe8910bViewBagSectionsForm1","implement":null,"vars":[],"layout":null,"suppressLayout":false,"assetPath":"\/modules\/backend\/widgets\/form\/assets"}]"
updateLocale: "en"
updateValue: "[{"subtitle":"sub en","_group":"subtitle"},{"text_area":"<p>content en<\/p>\r\n","text_area_position":"none","text_area_image":"","_group":"content"}]"


// Switching to Local en
formFieldValue: "[{"subtitle":"sub en","_group":"subtitle"},{"text_area":"<p>content en<\/p>\r\n","text_area_position":"none","text_area_image":"","_group":"content"}]"
initLockerData: "[{"subtitle":"sub en","_group":"subtitle"},{"text_area":"<p>content en<\/p>\r\n","text_area_position":"none","text_area_image":"","_group":"content"}]"
thisFormWidget: "[{"fields":{"subtitle":{"label":"Sous-titre (phrase d'accroche)","type":"text"}},"tabs":{"fields":[]},"secondaryTabs":{"fields":[]},"model":{"settings":[]},"data":{"subtitle":"sub en","_group":"subtitle"},"context":null,"arrayName":"viewBag[sections][0]","isNested":true,"sessionKey":null,"previewMode":false,"config":{"fields":{"subtitle":{"label":"Sous-titre (phrase d'accroche)","type":"text"}},"model":{"settings":[]},"data":{"subtitle":"sub en","_group":"subtitle"},"alias":"formPaged41d8cd98f00b204e9800998ecf8427e5ba49dbe8910bViewBagSectionsForm0","arrayName":"viewBag[sections][0]","isNested":true},"alias":"formPaged41d8cd98f00b204e9800998ecf8427e5ba49dbe8910bViewBagSectionsForm0","implement":null,"vars":[],"layout":null,"suppressLayout":false,"assetPath":"\/modules\/backend\/widgets\/form\/assets"},{"fields":{"text_area":{"label":"Contenu","type":"richeditor","toolbarButtons":"bold|italic|underline|strikeThrough|subscript|superscript|fontFamily|fontSize|color|emoticons|inlineStyle|paragraphStyle|paragraphFormat|align|formatOL|formatUL|outdent|indent|quote|insertHR|insertLink|insertTable|undo|redo|clearFormatting|selectAll|html|fullscreen","size":"huge","span":"full"},"text_area_position":{"label":"Position du contenu sur la page","type":"radio","span":"left","default":"none","options":{"none":["Aucune","Le contenu prendra toute la largeur de la page."],"left":["Align\u00e9 \u00e0 gauche","Le contenu sera plac\u00e9 \u00e0 gauche des autres \u00e9l\u00e9ments."],"right":["Align\u00e9 \u00e0 droite","Le contenu sera plac\u00e9 \u00e0 droite des autres \u00e9l\u00e9ments."]}},"text_area_image":{"label":"Affiche une image li\u00e9e","commentAbove":"Si vous souhaitez ajout\u00e9 une image \u00e0 ce contenu, merci de l'ajouter ici","type":"mediafinder","mode":"image","span":"right","imageWidth":"40%"}},"tabs":{"fields":[]},"secondaryTabs":{"fields":[]},"model":{"settings":[]},"data":{"text_area":"<p>content en<\/p>\r\n","text_area_position":"none","text_area_image":"","_group":"content"},"context":null,"arrayName":"viewBag[sections][1]","isNested":true,"sessionKey":"4ne5aLPOMhyYsuhLbnaqrYJntBLXF7jgjFIASvNF","previewMode":false,"config":{"fields":{"text_area":{"label":"Contenu","type":"richeditor","toolbarButtons":"bold|italic|underline|strikeThrough|subscript|superscript|fontFamily|fontSize|color|emoticons|inlineStyle|paragraphStyle|paragraphFormat|align|formatOL|formatUL|outdent|indent|quote|insertHR|insertLink|insertTable|undo|redo|clearFormatting|selectAll|html|fullscreen","size":"huge","span":"full"},"text_area_position":{"label":"Position du contenu sur la page","type":"radio","span":"left","default":"none","options":{"none":["Aucune","Le contenu prendra toute la largeur de la page."],"left":["Align\u00e9 \u00e0 gauche","Le contenu sera plac\u00e9 \u00e0 gauche des autres \u00e9l\u00e9ments."],"right":["Align\u00e9 \u00e0 droite","Le contenu sera plac\u00e9 \u00e0 droite des autres \u00e9l\u00e9ments."]}},"text_area_image":{"label":"Affiche une image li\u00e9e","commentAbove":"Si vous souhaitez ajout\u00e9 une image \u00e0 ce contenu, merci de l'ajouter ici","type":"mediafinder","mode":"image","span":"right","imageWidth":"40%"}},"model":{"settings":[]},"data":{"text_area":"<p>content en<\/p>\r\n","text_area_position":"none","text_area_image":"","_group":"content"},"alias":"formPaged41d8cd98f00b204e9800998ecf8427e5ba49dbe8910bViewBagSectionsForm1","arrayName":"viewBag[sections][1]","isNested":true},"alias":"formPaged41d8cd98f00b204e9800998ecf8427e5ba49dbe8910bViewBagSectionsForm1","implement":null,"vars":[],"layout":null,"suppressLayout":false,"assetPath":"\/modules\/backend\/widgets\/form\/assets"}]"
updateLocale: "fr"
updateValue: "[{"title":"titre fr","_group":"subtitle"},{"subtitle":"sub fr","_group":"content"}]"

// Switching again to Local FR
formFieldValue: "[{"title":"titre fr","_group":"subtitle"},{"subtitle":"sub fr","_group":"content"}]"
initLockerData: "[{"title":"titre fr","_group":"subtitle"},{"subtitle":"sub fr","_group":"content"}]"
thisFormWidget: "[{"fields":{"subtitle":{"label":"Sous-titre (phrase d'accroche)","type":"text"}},"tabs":{"fields":[]},"secondaryTabs":{"fields":[]},"model":{"settings":[]},"data":{"title":"titre fr","_group":"subtitle"},"context":null,"arrayName":"viewBag[sections][0]","isNested":true,"sessionKey":null,"previewMode":false,"config":{"fields":{"subtitle":{"label":"Sous-titre (phrase d'accroche)","type":"text"}},"model":{"settings":[]},"data":{"title":"titre fr","_group":"subtitle"},"alias":"formPaged41d8cd98f00b204e9800998ecf8427e5ba49dbe8910bViewBagSectionsForm0","arrayName":"viewBag[sections][0]","isNested":true},"alias":"formPaged41d8cd98f00b204e9800998ecf8427e5ba49dbe8910bViewBagSectionsForm0","implement":null,"vars":[],"layout":null,"suppressLayout":false,"assetPath":"\/modules\/backend\/widgets\/form\/assets"},{"fields":{"text_area":{"label":"Contenu","type":"richeditor","toolbarButtons":"bold|italic|underline|strikeThrough|subscript|superscript|fontFamily|fontSize|color|emoticons|inlineStyle|paragraphStyle|paragraphFormat|align|formatOL|formatUL|outdent|indent|quote|insertHR|insertLink|insertTable|undo|redo|clearFormatting|selectAll|html|fullscreen","size":"huge","span":"full"},"text_area_position":{"label":"Position du contenu sur la page","type":"radio","span":"left","default":"none","options":{"none":["Aucune","Le contenu prendra toute la largeur de la page."],"left":["Align\u00e9 \u00e0 gauche","Le contenu sera plac\u00e9 \u00e0 gauche des autres \u00e9l\u00e9ments."],"right":["Align\u00e9 \u00e0 droite","Le contenu sera plac\u00e9 \u00e0 droite des autres \u00e9l\u00e9ments."]}},"text_area_image":{"label":"Affiche une image li\u00e9e","commentAbove":"Si vous souhaitez ajout\u00e9 une image \u00e0 ce contenu, merci de l'ajouter ici","type":"mediafinder","mode":"image","span":"right","imageWidth":"40%"}},"tabs":{"fields":[]},"secondaryTabs":{"fields":[]},"model":{"settings":[]},"data":{"subtitle":"sub fr","_group":"content"},"context":null,"arrayName":"viewBag[sections][1]","isNested":true,"sessionKey":"4ne5aLPOMhyYsuhLbnaqrYJntBLXF7jgjFIASvNF","previewMode":false,"config":{"fields":{"text_area":{"label":"Contenu","type":"richeditor","toolbarButtons":"bold|italic|underline|strikeThrough|subscript|superscript|fontFamily|fontSize|color|emoticons|inlineStyle|paragraphStyle|paragraphFormat|align|formatOL|formatUL|outdent|indent|quote|insertHR|insertLink|insertTable|undo|redo|clearFormatting|selectAll|html|fullscreen","size":"huge","span":"full"},"text_area_position":{"label":"Position du contenu sur la page","type":"radio","span":"left","default":"none","options":{"none":["Aucune","Le contenu prendra toute la largeur de la page."],"left":["Align\u00e9 \u00e0 gauche","Le contenu sera plac\u00e9 \u00e0 gauche des autres \u00e9l\u00e9ments."],"right":["Align\u00e9 \u00e0 droite","Le contenu sera plac\u00e9 \u00e0 droite des autres \u00e9l\u00e9ments."]}},"text_area_image":{"label":"Affiche une image li\u00e9e","commentAbove":"Si vous souhaitez ajout\u00e9 une image \u00e0 ce contenu, merci de l'ajouter ici","type":"mediafinder","mode":"image","span":"right","imageWidth":"40%"}},"model":{"settings":[]},"data":{"subtitle":"sub fr","_group":"content"},"alias":"formPaged41d8cd98f00b204e9800998ecf8427e5ba49dbe8910bViewBagSectionsForm1","arrayName":"viewBag[sections][1]","isNested":true},"alias":"formPaged41d8cd98f00b204e9800998ecf8427e5ba49dbe8910bViewBagSectionsForm1","implement":null,"vars":[],"layout":null,"suppressLayout":false,"assetPath":"\/modules\/backend\/widgets\/form\/assets"}]"
updateLocale: "en"
updateValue: "[{"subtitle":"sub en","_group":"subtitle"},{"text_area":"<p>content en<\/p>\r\n","text_area_position":"none","text_area_image":"","_group":"content"}]"

I will continue investigate this, but i hope it could help someone to find a fix too :)

@massimomegistus
Copy link
Contributor

massimomegistus commented Sep 21, 2018

Hi everyone,
I really need this feature and i'm using a solution that seems to work.
I've tested it on a model form with a repeater, but I'll check on a static page soon
/modules/backend/formwidgets/Repeater.php
line 84)
add

        protected static $onSwitchLangCalled = false; // translable repeater support

line 238) processExistingItems()
replace

        $itemIndexes = post($this->indexInputName, $loadedIndexes);
        $itemGroups = post($this->groupInputName, $loadedGroups);
    **with**
        if(self::$onSwitchLangCalled){
          $itemIndexes = $loadedIndexes;
          $itemGroups = $loadedGroups;
        }else{
          $itemIndexes = post($this->indexInputName, $loadedIndexes);
          $itemGroups = post($this->groupInputName, $loadedGroups);
        }

/plugins/rainlab/translate/formwidgets/MLRepeater.php
Add the lines marked // translable repeater support
line 132) onSwitchItemLocale()

        $this->actAsParent();
        self::$onAddItemCalled = true; // translable repeater support
        $parentContent = parent::render();
        self::$onAddItemCalled = false; // translable repeater support
        $this->actAsParent(false);

174) reprocessExistingLocaleItems($data)

        self::$onSwitchLangCalled = true; // translable repeater support
        $this->processExistingItems();
        self::$onSwitchLangCalled = false; // translable repeater support

Any suggestion on help will be appreciated :)

@Ladylain
Copy link

@massimomegistus , i've just tested it on static page with repeaters and it does not fix the issue :(

i'll search again if i could find something...

@massimomegistus
Copy link
Contributor

Thank you @Ladylain, let me know, please

@massimomegistus
Copy link
Contributor

massimomegistus commented Sep 21, 2018

Hi @Ladylain,
Please, add also this code modification, to support different group orders through languages in the repeater field
/plugins/rainlab/translate/formwidgets/MLRepeater.php
line 232) Add this method

    /**
     * Splices in some meta data (group and index values) to the dataset.
     * @param array $value
     * @return array
     */
    protected function processSaveValue($value)
    {
        if (!is_array($value) || !$value) {
            return $value;
        }
        return array_values($value);
    }

i've tested on a static page too right now and it seems to work.
I have a group repeater with the mediacarousel group that has nested slides.
This it its Yaml description

mediacarousel:
    name: Carousel
    description: Thumbs Carousel
    icon: icon-leaf
    fields:
        carousel_slides:
            label: Thumbs carousel
            prompt: Add a new slide
            type: repeater
            form:
                fields:
                    slide_image:
                        label: Image
                        type: mediafinder
                        mode: image
                        span: left
                    slide_caption:
                        label: Caption
                        span: right

Switching form a language to another the slides are mantained as expected. Without my fixes all the slides are repeated in each carousel.

This are the screenshots: as you can se, in english and italian the are different groups and the carousel/slide hierarchy is mantained
Repeater in english lang
nested_repeater_english
Repeater in italian lang
nested_repeater_italian

Let me know :)

@Ladylain
Copy link

O_O

You are my fucking hero at the moment :)

All seems to work good on my side, i have a complex repeater which allows me to do many things that i want, but until now, translation was creating issues, and here you come with a great solution.

I think we need to test a little more to make sure everything is ok for everybody, but it's a hell of a lot of progress.

Thanks so much, my content redactor will be happy on monday :p and of course, have a nice week end

@jimcottrell
Copy link

I should have checked into this the last couple of days, but I've been working on this too in combination with octobercms/october#3729. I didn't know it would be so popular all of a sudden, but I just saw all this activity when I was readying my own PR for submission.

Anyway, I reached similar conclusions as @massimomegistus and named things differently, but I'm right in line with this fix. What I believe the above version doesn't do, however, is handle nested group repeaters or any other widget that overrides getSaveValue to process the data in some way. For that, the core fix is necessary as well as #409. I don't mean to steal @massimomegistus's thunder, but it's easier to test a PR than manually apply the above changes, so if anyone having this issue wants to check it out and comment on #409, we can see if there are any lingering edge cases.

@jimcottrell
Copy link

Well, nested group repeaters should be okay due to octobercms/october#3523 avoiding the getSaveValue issue, which I knew, so I don't know why I wrote that. Other widgets relying on getSaveValue are affected as described though.

@pvullioud
Copy link

Hi Heros,
Thanks for the good work.
Do not forget to request the Bounty : https://www.bountysource.com/issues/50188520-empty-fields-with-nested-repeaters
Or if you don't want it we can give it to Rainlab.

@LukeTowers
Copy link
Contributor

@pvullioud so does @jimcottrell's PRs solve all the issues?

@Ladylain
Copy link

Ladylain commented Oct 10, 2018

@LukeTowers, i've just tested it again, and without @massimomegistus's code, it doesn't fixed the problem for my issue rainlab/pages-plugin#353

but with the @massimomegistus's, it works perfectly

@buccia
Copy link

buccia commented Oct 10, 2018

+1
@massimomegistus's code also works for me

@LukeTowers
Copy link
Contributor

@jimcottrell any idea what's up with @Ladylain and @buccia?

@Fl0Cri
Copy link

Fl0Cri commented Oct 11, 2018

@Ladylain when trying @jimcottrell's fix, have you applied both #409 and octobercms/october#3729 ?

In my case it solved the main problem. I only found 2 problems that can occur when trying to manipulate nested repeaters. Can someone confirm these?
Anyway these problems seems me minor compared to the main bug the PR fixes.

@jimcottrell
Copy link

@LukeTowers I haven't had a chance to get to the problems @Fl0Cri mentioned with the fix in #409 yet, but I should be able to tackle that soon. There's nothing wrong with the code from @massimomegistus, so there's no reason people wouldn't have success with it for the empty field issue. It's just that it doesn't address the underlying problem of repeaters not calling getSaveValue on any child widgets, which requires a different strategy in the base repeater as well as MLRepeater to run everything through the child form widgets.

That said, if I can't get to fixing the deeper issue in the next couple of days, I'm happy to either submit a simpler PR or let @massimomegistus do it to address just the empty field issue described here.

@LukeTowers
Copy link
Contributor

LukeTowers commented Oct 11, 2018

@jimcottrell I'd rather wait for the deeper fix, if people need an immediate fix they can apply the patch from @massimomegistus. Thanks for your work on this so far!

@patosG
Copy link

patosG commented Dec 18, 2018

@massimomegistus you're a genius !

@LukeTowers
Copy link
Contributor

Can everyone please test with a fresh install and octobercms/october#4234 and #466 applied?

LukeTowers added a commit that referenced this issue Apr 17, 2019
Bring MLRepeater inline with core changes to Repeater. Related: octobercms/october#4234, #307, #290.
@LukeTowers
Copy link
Contributor

Closing as the above PRs have been merged, will reopen if anyone still has a problem after applying those fixes.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests