]> git.mjollnir.org Git - moodle.git/commitdiff
MDL-5482 - Backup and restore problems for match, random and truefalse question types.
authortjhunt <tjhunt>
Wed, 7 May 2008 12:32:03 +0000 (12:32 +0000)
committertjhunt <tjhunt>
Wed, 7 May 2008 12:32:03 +0000 (12:32 +0000)
All the credit goes to Paulo Matos who carefully worked out and tested this fix, and updated the patch several times over more than a year while I very slowly got around to reviewing it and checking it in.

question/restorelib.php
question/type/match/questiontype.php
question/type/random/questiontype.php
question/type/truefalse/questiontype.php

index 8ed49822dec75c90f6d58e558fde6faa0351bba0..678a785e911b656fc13edd297167ab458d87c2c4 100644 (file)
                 }
             }
 
+            // Fixing bug #5482: random questions have parent field set to its own id,
+            //                   see: $QTYPES['random']->get_question_options()
+            if ($question->qtype == 'random') {
+                $question->parent = $newid;
+                //we have to update the random question if the question has been inserted
+                if ($creatingnewquestion && $newid)
+                    $status = set_field('question', 'parent', $question->parent, 'id', $newid);
+            }
+
             //Save newid to backup tables
             if ($question->id) {
                 //We have the newid, update backup_ids
index 6ab57da88feeff8d49f07ecaf01713f971d55e04..bf60e8f57c8c7d528a905c0210e7e6e04dec3a81 100644 (file)
@@ -596,16 +596,30 @@ class question_match_qtype extends default_questiontype {
             //Extract the match_sub for the question and the answer
             $exploded = explode("-",$tok);
             $match_question_id = $exploded[0];
-            $match_answer_code = $exploded[1];
+            $match_answer_id = $exploded[1];
             //Get the match_sub from backup_ids (for the question)
             if (!$match_que = backup_getid($restore->backup_unique_code,"question_match_sub",$match_question_id)) {
-                echo 'Could not recode question_match_sub '.$match_question_id.'<br />';
+                echo 'Could not recode question in question_match_sub '.$match_question_id.'<br />';
             }
-            if ($in_first) {
-                $answer_field .= $match_que->new_id."-".$match_answer_code;
-                $in_first = false;
-            } else {
-                $answer_field .= ",".$match_que->new_id."-".$match_answer_code;
+            //Get the match_sub from backup_ids (for the answer)
+            if ($match_answer_id) { // only recode answer if not 0, not answered yet
+              if (!$match_ans = backup_getid($restore->backup_unique_code,"question_match_sub",$match_answer_id)) {
+                  echo 'Could not recode answer in question_match_sub '.$match_answer_id.'<br />';
+              }
+            }
+
+            if ($match_que) {
+                //If the question hasn't response, it must be 0
+                if (!$match_ans and $match_answer_id == 0) {
+                    $match_ans->new_id = 0;
+                }
+
+                if ($in_first) {
+                    $answer_field .= $match_que->new_id."-".$match_ans->new_id;
+                    $in_first = false;
+                } else {
+                    $answer_field .= ",".$match_que->new_id."-".$match_ans->new_id;
+                }
             }
             //check for next
             $tok = strtok(",");
index 20c85465798a545a0938e7c9a3fa3bdfa9a16215..d6024c41b17c5c580a451213955adc725cae18c0 100644 (file)
@@ -284,6 +284,49 @@ class random_qtype extends default_questiontype {
          ->compare_responses($wrappedquestion, $state, $teststate);
     }
 
+    function restore_recode_answer($state, $restore) {
+        // The answer looks like 'randomXX-ANSWER', where XX is
+        // the id of the used question and ANSWER the actual
+        // response to that question.
+        // However, there may still be old-style states around,
+        // which store the id of the wrapped question in the
+        // state of the random question and store the response
+        // in a separate state for the wrapped question
+
+        global $QTYPES;
+        $answer_field = "";
+
+        if (ereg('^random([0-9]+)-(.*)$', $state->answer, $answerregs)) {
+            // Recode the question id in $answerregs[1]
+            // Get the question from backup_ids
+            if(!$wrapped = backup_getid($restore->backup_unique_code,"question",$answerregs[1])) {
+              echo 'Could not recode question in random-'.$answerregs[1].'<br />';
+              return($answer_field);
+            }
+            // Get the question type for recursion
+            if (!$wrappedquestion->qtype = get_field('question', 'qtype', 'id', $wrapped->new_id)) {
+              echo 'Could not get qtype while recoding question random-'.$answerregs[1].'<br />';
+              return($answer_field);
+            }
+            $newstate = $state;
+            $newstate->question = $wrapped->new_id;
+            $newstate->answer = $answerregs[2];
+            $answer_field = 'random'.$wrapped->new_id.'-';
+
+            // Recode the answer field in $answerregs[2] depending on
+            // the qtype of question with id $answerregs[1]
+            $answer_field .= $QTYPES[$wrappedquestion->qtype]->restore_recode_answer($newstate, $restore);
+        } else {
+            // Handle old-style states
+            $answer_link = backup_getid($restore->backup_unique_code,"question",$state->answer);
+            if ($answer_link) {
+                $answer_field = $answer_link->new_id;
+            }
+        }
+
+        return $answer_field;
+    }
+
 }
 //// END OF CLASS ////
 
index a45bdc56ad5dcc8b39ebc3bf8031db026e5c3e6d..b34c4bf226518b7503570cc8873bdbee52a972b6 100644 (file)
@@ -334,13 +334,15 @@ class question_truefalse_qtype extends default_questiontype {
     }
 
     function restore_recode_answer($state, $restore) {
-        $answer = backup_getid($restore->backup_unique_code,"question_answers",$state->answer);
-        if ($answer) {
-            return $answer->new_id;
-        } else {
-            echo 'Could not recode truefalse answer id '.$state->answer.' for state '.$state->oldid.'<br />';
+        //answer may be empty
+        if ($state->answer) {
+            $answer = backup_getid($restore->backup_unique_code,"question_answers",$state->answer);
+            if ($answer) {
+                return $answer->new_id;
+            } else {
+                echo 'Could not recode truefalse answer id '.$state->answer.' for state '.$state->oldid.'<br />';
+            }
         }
-        return '';
     }
 
 }