View Issue Details

This bug affects 1 person(s).
 12
IDProjectCategoryView StatusLast Update
05031Bug reportsConditionspublic2011-04-11 11:30
ReporterResearchOnBlogs Assigned Tolemeur  
PrioritynormalSeverityminor 
Status closedResolutionfixed 
Product Version1.90+ 
Fixed in Version1.91RC6 
Summary05031: GSOC - update answercodes does not update conditions
Description

Hi there,
I updated some answercodes from "A1" to "1". After that the conditions on that questions were not be updated!
Is that known?

TagsNo tags attached.
Attached Files
LSanswer.diff (3,414 bytes)   
Index: admin/scripts/answers.js
===================================================================
--- admin/scripts/answers.js	(revision 9945)
+++ admin/scripts/answers.js	(working copy)
@@ -198,6 +198,8 @@
              $(this).addClass('highlight');
          }
          $(this).addClass('row_'+rownumber);
+         $(this).find('.oldcode').attr('id','oldcode_'+rownumber+'_'+scale_id);
+         $(this).find('.oldcode').attr('name','oldcode_'+rownumber+'_'+scale_id);
          $(this).find('.code').attr('id','code_'+rownumber+'_'+scale_id);
          $(this).find('.code').attr('name','code_'+rownumber+'_'+scale_id);
          $(this).find('.answer').attr('id','answer_'+language+'_'+rownumber+'_'+scale_id);
Index: admin/database.php
===================================================================
--- admin/database.php	(revision 9945)
+++ admin/database.php	(working copy)
@@ -851,6 +851,7 @@
             $maxcount=(int)$_POST['answercount_'.$scale_id];
             for ($sortorderid=1;$sortorderid<$maxcount;$sortorderid++)
             {
+                $oldcode=sanitize_paranoid_string($_POST['oldcode_'.$sortorderid.'_'.$scale_id]);
                 $code=sanitize_paranoid_string($_POST['code_'.$sortorderid.'_'.$scale_id]);
                 $assessmentvalue=(int) $_POST['assessment_'.$sortorderid.'_'.$scale_id];
                 foreach ($alllanguages as $language)
@@ -882,6 +883,12 @@
                         $databaseoutput .= "<script type=\"text/javascript\">\n<!--\n alert(\"".$clang->gT("Failed to update answers","js")." - ".$query." - ".$connect->ErrorMsg()."\")\n //-->\n</script>\n";
                     }
                 } // foreach ($alllanguages as $language)
+
+                if($code !== $oldcode) {
+                    $query='UPDATE '.db_table_name('conditions').' SET value='.db_quoteall($code).' WHERE cqid='.db_quote($qid).' AND value='.db_quoteall($oldcode);
+                    $connect->execute($query);
+                }
+
             }  // for ($sortorderid=0;$sortorderid<$maxcount;$sortorderid++)
         }  //  for ($scale_id=0;

Index: admin/editansweroptions.php
===================================================================
--- admin/editansweroptions.php	(revision 9945)
+++ admin/editansweroptions.php	(working copy)
@@ -177,7 +177,7 @@
 
                 if ($first)
                 {
-                    $vasummary .= "<img class='handle' src='$imageurl/handle.png' /></td><td><input type='text' class='code' id='code_{$position}_{$scale_id}' name='code_{$position}_{$scale_id}' value=\"{$row['code']}\" maxlength='5' size='5'"
+                    $vasummary .= "<img class='handle' src='$imageurl/handle.png' /></td><td><input type='hidden' class='oldcode' id='oldcode_{$position}_{$scale_id}' name='oldcode_{$position}_{$scale_id}' value=\"{$row['code']}\" /><input type='text' class='code' id='code_{$position}_{$scale_id}' name='code_{$position}_{$scale_id}' value=\"{$row['code']}\" maxlength='5' size='5'"
                     ." onkeypress=\"return goodchars(event,'1234567890abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWZYZ_')\""
                     ." />";
                 }
@@ -188,7 +188,7 @@
                 }
 
                 $vasummary .= "</td>\n"
                 ."<td\n";
 
                 if ($assessmentvisible && $first)
                 {
LSanswer.diff (3,414 bytes)   
LSanswer_fixed.diff (3,177 bytes)   
Index: admin/scripts/answers.js
===================================================================
--- admin/scripts/answers.js	(revision 9945)
+++ admin/scripts/answers.js	(working copy)
@@ -198,6 +198,8 @@
              $(this).addClass('highlight');
          }
          $(this).addClass('row_'+rownumber);
+         $(this).find('.oldcode').attr('id','oldcode_'+rownumber+'_'+scale_id);
+         $(this).find('.oldcode').attr('name','oldcode_'+rownumber+'_'+scale_id);
          $(this).find('.code').attr('id','code_'+rownumber+'_'+scale_id);
          $(this).find('.code').attr('name','code_'+rownumber+'_'+scale_id);
          $(this).find('.answer').attr('id','answer_'+language+'_'+rownumber+'_'+scale_id);
Index: admin/database.php
===================================================================
--- admin/database.php	(revision 9945)
+++ admin/database.php	(working copy)
@@ -851,6 +851,7 @@
             $maxcount=(int)$_POST['answercount_'.$scale_id];
             for ($sortorderid=1;$sortorderid<$maxcount;$sortorderid++)
             {
+                $oldcode=sanitize_paranoid_string($_POST['oldcode_'.$sortorderid.'_'.$scale_id]);
                 $code=sanitize_paranoid_string($_POST['code_'.$sortorderid.'_'.$scale_id]);
                 $assessmentvalue=(int) $_POST['assessment_'.$sortorderid.'_'.$scale_id];
                 foreach ($alllanguages as $language)
@@ -882,6 +883,12 @@
                         $databaseoutput .= "<script type=\"text/javascript\">\n<!--\n alert(\"".$clang->gT("Failed to update answers","js")." - ".$query." - ".$connect->ErrorMsg()."\")\n //-->\n</script>\n";
                     }
                 } // foreach ($alllanguages as $language)
+
+                if($code !== $oldcode) {
+                    $query='UPDATE '.db_table_name('conditions').' SET value='.db_quoteall($code).' WHERE cqid='.db_quote($qid).' AND value='.db_quoteall($oldcode);
+                    $connect->execute($query);
+                }
+
             }  // for ($sortorderid=0;$sortorderid<$maxcount;$sortorderid++)
         }  //  for ($scale_id=0;
 
Index: admin/editansweroptions.php
===================================================================
--- admin/editansweroptions.php	(revision 9945)
+++ admin/editansweroptions.php	(working copy)
@@ -177,7 +177,7 @@
 
                 if ($first)
                 {
-                    $vasummary .= "<img class='handle' src='$imageurl/handle.png' /></td><td><input type='text' class='code' id='code_{$position}_{$scale_id}' name='code_{$position}_{$scale_id}' value=\"{$row['code']}\" maxlength='5' size='5'"
+                    $vasummary .= "<img class='handle' src='$imageurl/handle.png' /></td><td><input type='hidden' class='oldcode' id='oldcode_{$position}_{$scale_id}' name='oldcode_{$position}_{$scale_id}' value=\"{$row['code']}\" /><input type='text' class='code' id='code_{$position}_{$scale_id}' name='code_{$position}_{$scale_id}' value=\"{$row['code']}\" maxlength='5' size='5'"
                     ." onkeypress=\"return goodchars(event,'1234567890abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWZYZ_')\""
                     ." />";
                 }
LSanswer_fixed.diff (3,177 bytes)   
arrayconditions.diff (2,976 bytes)   
Index: admin/database.php
===================================================================
--- admin/database.php	(revision 9976)
+++ admin/database.php	(working copy)
@@ -927,6 +927,7 @@
         //Determine ids by evaluating the hidden field
         $rows=array();
         $codes=array();
+        $oldcodes=array();
         foreach ($_POST as $postkey=>$postvalue)
         {
             $postkey=explode('_',$postkey);
@@ -938,6 +939,10 @@
             {
                 $codes[$postkey[2]][]=$postvalue;
             }
+            if ($postkey[0]=='oldcode')
+            {
+                $oldcodes[$postkey[2]][]=$postvalue;
+            }
         }
         $count=0;
         $invalidCode = 0;
@@ -972,6 +977,12 @@
                     {
                         $query='Update '.db_table_name('questions').' set question_order='.($position+1).', title='.db_quoteall($codes[$scale_id][$position]).', question='.db_quoteall($subquestionvalue).', scale_id='.$scale_id.' where qid='.db_quoteall($subquestionkey).' AND language='.db_quoteall($language);
                         $connect->execute($query);
+
+                        if($codes[$scale_id][$position] !== $oldcodes[$scale_id][$position]) {
+                            $query='UPDATE '.db_table_name('conditions').' SET cfieldname="+'.$surveyid.'X'.$gid.'X'.$qid.db_quote($codes[$scale_id][$position]).'" WHERE cfieldname="+'.$surveyid.'X'.$gid.'X'.$qid.db_quote($oldcodes[$scale_id][$position]).'"';
+                            $connect->execute($query);
+                        }
+
                     }
                     else
                     {
Index: admin/editsubquestions.php
===================================================================
--- admin/editsubquestions.php	(revision 9976)
+++ admin/editsubquestions.php	(working copy)
@@ -195,7 +195,7 @@
                 }
                 elseif ($activated != 'Y' && $first) // If survey is decactivated
                 {
-                    $vasummary .= "<img class='handle' src='$imageurl/handle.png' /></td><td><input type='text' id='code_{$row['qid']}_{$row['scale_id']}' class='code' name='code_{$row['qid']}_{$row['scale_id']}' value=\"{$row['title']}\" maxlength='5' size='5'"
+                    $vasummary .= "<img class='handle' src='$imageurl/handle.png' /></td><td><input type='hidden' class='oldcode' id='oldcode_{$row['qid']}_{$row['scale_id']}' name='oldcode_{$row['qid']}_{$row['scale_id']}' value=\"{$row['title']}\" /><input type='text' id='code_{$row['qid']}_{$row['scale_id']}' class='code' name='code_{$row['qid']}_{$row['scale_id']}' value=\"{$row['title']}\" maxlength='5' size='5'"
                     ." onkeypress=\" if(event.keyCode==13) {if (event && event.preventDefault) event.preventDefault(); document.getElementById('saveallbtn_$anslang').click(); return false;} return goodchars(event,'1234567890abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWZYZ_')\""
                     ." />";
 
arrayconditions.diff (2,976 bytes)   
Bug heat12
Complete LimeSurvey version number (& build)9642
I will donate to the project if issue is resolvedNo
Browser
Database type & version??
Server OS (if known)linux
Webserver software & version (if known)?
PHP Version5

Users monitoring this issue

dionet, pasmaill

Activities

lemeur

lemeur

2011-03-20 07:35

developer   ~14468

This is a known limitation of the current version.

If a GSOC applicant is interrested in conditions, I would recommend to have a look at this point. (Don't hesitate to post a message on the ticket to get on touch with me.)

The answers update code starts in admin/database.php on line 820.
The answers update HTML form is defined in admin/editansweroptions.php

Now, let's explain the pb.
For most conditions, the comparizon "value" is a previous answer "code". If the survey administrator changes the answer code after having defined conditions, then the conditions do not work anymore because the comparizon value wasn't updated when the answer code was changed.
The pb is that:

  • condition values are not always previous answer codes. So we must replace the condition value only for the conditions that were really related to this specific question code.
  • in the answer html form, we would need to keep track of the old answer code and then build a mapping of { oldCode => newCode }

Now a quick description of conditions:
mysql> describe lime_conditions;
+------------+--------------+------+-----+---------+----------------+
| Field | Type | Null | Key | Default | Extra |
+------------+--------------+------+-----+---------+----------------+
| cid | int(11) | NO | PRI | NULL | auto_increment |
| qid | int(11) | NO | MUL | 0 | |
| scenario | int(11) | NO | | 1 | |
| cqid | int(11) | NO | MUL | 0 | |
| cfieldname | varchar(50) | NO | | | |
| method | char(5) | NO | | | |
| value | varchar(255) | NO | | | |
+------------+--------------+------+-----+---------+----------------+

where:
cid: is the condition id
qid: the question Id of the question beeing conditionnaly displayed
scenario: a scenario in which the condition is defined (see online doc)
cqid: if the condition's comparizon value is a previous question answer, then this field contains the question Id of this previous question. If the condition 's comparizon value is not a previous question answer, then this field contains the value '0'
cfieldname: this is the database fieldname of the previous question (or subquestion) on which the condition is based: it uses in the form {SGQ} or {SGQA} format. if the condition is not based on a previous question answer then this is a placeholder such as {TOKEN:XXX}. A special case is used for "single checkbox" cfieldname which are in fact a +{SGQA} code
method: this is the comparizon operator (==, !=, ...)
value: this is the value we should use as the comparizon right operand. It can be an previous answer code, a constant, a regular expression, a previous answer placeholder, a token attribute placeholder

ResearchOnBlogs

ResearchOnBlogs

2011-03-23 14:32

developer   ~14524

thanks for your explanation

dionet

dionet

2011-04-03 00:02

reporter   ~14634

Please check the patch I uploaded. I tested it and it seems to work correctly.
I had to edit some javascript code besides the answers HTML form.

lemeur, thank you for your note explaining how it works, it helped a lot.

lemeur

lemeur

2011-04-03 08:44

developer   ~14635

@dionet,

Thx for the work ont his ticket.
The patch "looks" ok so far but It seems to be corrupted: the very last part doesn't have any +/- lines and applying it results in a "malformed patch" error:

patch -p0 --dry-run < /tmp/patch
patching file admin/scripts/answers.js
patching file admin/database.php
patching file admin/editansweroptions.php
patch: **** malformed patch at line 59:

Could you generate a new patch ?
TIA,
Thibault

dionet

dionet

2011-04-03 12:39

reporter   ~14636

Sorry, please try the new patch.

lemeur

lemeur

2011-04-05 00:07

developer   ~14667

Thx for the new fix.
it works well for single choice questions (List radio for instance), but not for multiple choices questions...

Could you have a look ?

Thibault

lemeur

lemeur

2011-04-06 12:01

developer   ~14688

@dionet,

Do you need help to finish the fix ?
Thibault

dionet

dionet

2011-04-06 15:20

reporter   ~14698

I'll look at it today and I'll post a note if I need any help.

Thank you

lemeur

lemeur

2011-04-06 18:01

developer   ~14701

Last edited: 2011-04-06 18:06

Boa tarde dionet,

No teu GSOC proposicao e muito importante dizer que tu tens trabalhado no correctivo do bug 5031.

Obrigado por teu trabalho e interresto no LimeSruevy.

Sorry for my very bad Portuguese ;-) But it is important to add the reference to this ticket and your fix on your proposal.

Thibault

OUPS: haven't seen that you've added the reference already... good.

dionet

dionet

2011-04-07 17:47

reporter   ~14729

lemeur, please try the new patch.

Don't worry, your Portuguese isn't bad :P

dionet

lemeur

lemeur

2011-04-07 18:23

developer   ~14730

Hi dionet,

Thx for beeing indulgent about my Portuguese (promised, next time I'll have my wife or daughter correct my sentences ;-).

The proposed extra patch fixes an issue when using single-checkboxes answers in conditions, but not when using group-of-cehckboxes as conditions.

This is a little tricky as there are 2 ways to store conditions for multiple choices questions.

Here are the 2 queries that must be used in this case:

  • The first one is the one you proposed
    $query='UPDATE '.db_table_name('conditions').' SET cfieldname="+'.$surveyid.'X'.$gid.'X'.$qid.db_quote($codes[$scale_id][$position]).'" WHERE cqid='.$qid.' AND cfieldname="+'.$surveyid.'X'.$gid.'X'.$qid.db_quote($oldcodes[$scale_id][$position]).'"';
    $connect->execute($query);

The second one is for group-of-checkboxes questions
$query='UPDATE '.db_table_name('conditions').' SET value="'.db_quote($codes[$scale_id][$position]).'" WHERE cqid='.$qid.' AND cfieldname="'.$surveyid.'X'.$gid.'X'.$qid.'" AND value="'.$oldcodes[$scale_id][$position].'"';
$connect->execute($query);

Apart from this very specific issue I admit that this wasn't an easy patch and you did it very well. Thanx for your work and all the best with your application.

dionet

dionet

2011-04-07 18:30

reporter   ~14731

Thank you, I'll do my best :)

dionet

lemeur

lemeur

2011-04-07 18:32

developer   ~14732

Fixed in rev 9977 and 9978.
Many thx dionet for this great work.

Thibault

c_schmitz

c_schmitz

2011-04-11 11:30

administrator   ~14745

1.91RC6 released.

Issue History

Date Modified Username Field Change
2011-03-14 18:33 ResearchOnBlogs New Issue
2011-03-14 18:33 ResearchOnBlogs Status new => assigned
2011-03-14 18:33 ResearchOnBlogs Assigned To => lemeur
2011-03-20 07:04 lemeur Summary update answercodes does not update conditions => GSOC - update answercodes does not update conditions
2011-03-20 07:35 lemeur Note Added: 14468
2011-03-23 14:32 ResearchOnBlogs Note Added: 14524
2011-03-29 00:45 pasmaill Issue Monitored: pasmaill
2011-03-29 18:40 user13064 Issue Monitored: user13064
2011-04-03 00:02 dionet File Added: LSanswer.diff
2011-04-03 00:02 dionet Note Added: 14634
2011-04-03 00:02 dionet Issue Monitored: dionet
2011-04-03 08:44 lemeur Note Added: 14635
2011-04-03 08:44 lemeur Status assigned => new
2011-04-03 08:45 lemeur Status new => assigned
2011-04-03 08:45 lemeur Status assigned => feedback
2011-04-03 12:38 dionet File Added: LSanswer_fixed.diff
2011-04-03 12:39 dionet Note Added: 14636
2011-04-05 00:07 lemeur Note Added: 14667
2011-04-06 12:01 lemeur Note Added: 14688
2011-04-06 15:20 dionet Note Added: 14698
2011-04-06 18:01 lemeur Note Added: 14701
2011-04-06 18:06 lemeur Note Edited: 14701
2011-04-07 17:46 dionet File Added: arrayconditions.diff
2011-04-07 17:47 dionet Note Added: 14729
2011-04-07 18:23 lemeur Note Added: 14730
2011-04-07 18:30 dionet Note Added: 14731
2011-04-07 18:32 lemeur Note Added: 14732
2011-04-07 18:32 lemeur Status feedback => resolved
2011-04-07 18:32 lemeur Fixed in Version => 1.91RC6
2011-04-07 18:32 lemeur Resolution open => fixed
2011-04-11 11:30 c_schmitz Note Added: 14745
2011-04-11 11:30 c_schmitz Status resolved => closed
2021-08-02 19:33 guest Bug heat 8 => 12