Indexed-repeat error on long IF statement calculations

Hi to all,

trying to customize a form discussed here I create a if test in the calculation column. The idea is to calculate the current month and then retrieve planned value for the current station for this month from the choices sheet.

If face a problem which seems to be relative to the length of my expression.

this test is ok :

if((${mois}='01'),instance('stations')/root/item[name=indexed-repeat(${station}, ${mesure}, position(..))]/mois_01,
 (if((${mois}='02'),instance('stations')/root/item[name=indexed-repeat(${station}, ${mesure}, position(..))]/mois_02,
  (if((${mois}='03'),instance('stations')/root/item[name=indexed-repeat(${station}, ${mesure}, position(..))]/mois_03,
   (if((${mois}='04'),instance('stations')/root/item[name=indexed-repeat(${station}, ${mesure}, position(..))]/mois_04,
    (if((${mois}='05'),instance('stations')/root/item[name=indexed-repeat(${station}, ${mesure}, position(..))]/mois_05,
     (if((${mois}='06'),instance('stations')/root/item[name=indexed-repeat(${station}, ${mesure}, position(..))]/mois_06,
      (if((${mois}='07'),instance('stations')/root/item[name=indexed-repeat(${station}, ${mesure}, position(..))]/mois_07,
       (if((${mois}='08'),instance('stations')/root/item[name=indexed-repeat(${station}, ${mesure}, position(..))]/mois_08,''
       ))
      ))
     ))
    ))
   ))
  ))
 ))
)

But when I try to add another test for September, Central rise an error :

if((${mois}='01'),instance('stations')/root/item[name=indexed-repeat(${station}, ${mesure}, position(..))]/mois_01,
 (if((${mois}='02'),instance('stations')/root/item[name=indexed-repeat(${station}, ${mesure}, position(..))]/mois_02,
  (if((${mois}='03'),instance('stations')/root/item[name=indexed-repeat(${station}, ${mesure}, position(..))]/mois_03,
   (if((${mois}='04'),instance('stations')/root/item[name=indexed-repeat(${station}, ${mesure}, position(..))]/mois_04,
    (if((${mois}='05'),instance('stations')/root/item[name=indexed-repeat(${station}, ${mesure}, position(..))]/mois_05,
     (if((${mois}='06'),instance('stations')/root/item[name=indexed-repeat(${station}, ${mesure}, position(..))]/mois_06,
      (if((${mois}='07'),instance('stations')/root/item[name=indexed-repeat(${station}, ${mesure}, position(..))]/mois_07,
       (if((${mois}='08'),instance('stations')/root/item[name=indexed-repeat(${station}, ${mesure}, position(..))]/mois_08,
        (if((${mois}='09'),instance('stations')/root/item[name=indexed-repeat(${station}, ${mesure}, position(..))]/mois_09,''
        ))
       ))
      ))
     ))
    ))
   ))
  ))
 ))
)

Here is the issue :

Le XLSForm n'a pas pu être converti : ODK Validate Errors:
>> Something broke the parser. See above for a hint.
Error evaluating field 'cotes_gestion' (${mesure}[1]/suivi_station[1]/niveaux[1]/cotes_gestion[1]): The problem was located in Calculate expression for ${cotes_gestion}
XPath evaluation: type mismatch 
indexed-repeat(): parameter 2 must be a parent of the field in parameter 1
Caused by: org.javarosa.xpath.XPathTypeMismatchException: The problem was located in Calculate expression for ${cotes_gestion}
XPath evaluation: type mismatch 
indexed-repeat(): parameter 2 must be a parent of the field in parameter 1
	... 10 more

The following files failed validation:
${suivi_lagunes}.xml

Result: Invalid

If anyone has any idea... it would help me not to get crazy :partying_face:
Anyway I think I will create 12 calculate fields in my form and show the one corresponding to the current month to simplify it a little....
But I would like to understand the problem.

Thank's to @Varo's issue here I found another workaround to this bug (I think it is)

The raised error seems due to a too long if statement.
Splitting this calculation into 2 more little one and a third one to compute the global test works.

1 Like

indexed-repeat is a "convenience wrapper" for accessing specific questions at a particular repeat index. In this case, it looks like you just want to access the station in the current repeat instance so I think it would be more readable without indexed-repeat. It also would be less work for the engine because it could use the local context of the repeat instance.

Your first try at Get custom data from choices sheet for calculation - #12 by mathieubossaert with name=${station} looks the best approach to me. Could you please try it again as one expression with cases for each month?

I know we had some issues with XLSForm conversion of this kind of expression at some point so maybe that's what you ran into. I thought they would have been fixed by March 2021 but possibly not.

That's what I did in the end and what I suggest today to @Varo and it works fine and it finally easier to write than a long nested test.

Hi @mathieubossaert @LN

Thank you very much for all the collaboration.
I saw that there are several technical messages in this topics.
Now we are testing the form well and the real use from the mobile and soon we will give you the feed back well.
Thank you very much
Alvaro

1 Like

hi @mathieubossaert @LN

First of all, again, thank you very much for the collaboration.
I give you the feed back of the tests we were doing.
Effectively now it correctly implements the form corrected by @mathieubossaert on the servers.
When we went to test the mobile application, we saw that in previous versions, the same error was displayed on mobile phones, but using the latest version of ODK Collect it already worked correctly.
As a conclusion, creating long calculates as suggested in these topics and using the latest versions of mobile are the solution.
Thank you very much for everyone in this collaboration
Cheers
Alvaro

1 Like