2007-11-07 15:41:20 +00:00
|
|
|
<?php // $Id$
|
2007-03-19 17:22:46 +00:00
|
|
|
/**
|
|
|
|
* Question bank backup code.
|
|
|
|
*
|
|
|
|
* @license http://www.gnu.org/copyleft/gpl.html GNU Public License
|
|
|
|
* @package questionbank
|
|
|
|
*//** */
|
2006-03-21 15:38:35 +00:00
|
|
|
|
2006-03-21 16:50:42 +00:00
|
|
|
//This is the "graphical" structure of the question database:
|
2006-03-21 15:38:35 +00:00
|
|
|
//To see, put your terminal to 160cc
|
|
|
|
|
2006-03-21 16:50:42 +00:00
|
|
|
// The following holds student-independent information about the questions
|
2006-03-21 15:38:35 +00:00
|
|
|
//
|
2006-03-21 16:50:42 +00:00
|
|
|
// question_categories
|
|
|
|
// (CL,pk->id)
|
|
|
|
// |
|
|
|
|
// |
|
|
|
|
// |.......................................
|
|
|
|
// | .
|
|
|
|
// | .
|
|
|
|
// | -------question_datasets------ .
|
|
|
|
// | | (CL,pk->id,fk->question, | .
|
|
|
|
// | | fk->dataset_definition) | .
|
|
|
|
// | | | .
|
|
|
|
// | | | .
|
|
|
|
// | | | .
|
|
|
|
// | | question_dataset_definitions
|
|
|
|
// | | (CL,pk->id,fk->category)
|
|
|
|
// question |
|
|
|
|
// (CL,pk->id,fk->category,files) |
|
|
|
|
// | question_dataset_items
|
|
|
|
// | (CL,pk->id,fk->definition)
|
2007-05-24 17:25:37 +00:00
|
|
|
// |
|
|
|
|
// |
|
|
|
|
// |
|
|
|
|
// --------------------------------------------------------------------------------------------------------------
|
|
|
|
// | | | | | | |
|
|
|
|
// | | | | | | |
|
2006-03-21 16:50:42 +00:00
|
|
|
// | | | | question_calculated | |
|
|
|
|
// question_truefalse | question_multichoice | (CL,pl->id,fk->question) | |
|
|
|
|
// (CL,pk->id,fk->question) | (CL,pk->id,fk->question) | . | | question_randomsamatch
|
2006-03-21 15:38:35 +00:00
|
|
|
// . | . | . | |--(CL,pk->id,fk->question)
|
2006-03-21 16:50:42 +00:00
|
|
|
// . question_shortanswer . question_numerical . question_multianswer. |
|
2006-03-21 15:38:35 +00:00
|
|
|
// . (CL,pk->id,fk->question) . (CL,pk->id,fk->question) . (CL,pk->id,fk->question) |
|
2006-03-21 16:50:42 +00:00
|
|
|
// . . . . . . | question_match
|
2006-03-21 15:38:35 +00:00
|
|
|
// . . . . . . |--(CL,pk->id,fk->question)
|
|
|
|
// . . . . . . | .
|
|
|
|
// . . . . . . | .
|
|
|
|
// . . . . . . | .
|
2006-03-21 16:50:42 +00:00
|
|
|
// . . . . . . | question_match_sub
|
2006-03-21 15:38:35 +00:00
|
|
|
// ........................................................................................ |--(CL,pk->id,fk->question)
|
|
|
|
// . |
|
|
|
|
// . |
|
2006-03-21 16:50:42 +00:00
|
|
|
// . | question_numerical_units
|
|
|
|
// question_answers |--(CL,pk->id,fk->question)
|
2006-03-21 15:38:35 +00:00
|
|
|
// (CL,pk->id,fk->question)----------------------------------------------------------
|
|
|
|
//
|
2006-03-21 16:50:42 +00:00
|
|
|
//
|
|
|
|
// The following holds the information about student interaction with the questions
|
|
|
|
//
|
|
|
|
// question_sessions
|
|
|
|
// (UL,pk->id,fk->attempt,question)
|
|
|
|
// .
|
|
|
|
// .
|
|
|
|
// question_states
|
|
|
|
// (UL,pk->id,fk->attempt,question)
|
|
|
|
//
|
2006-03-21 15:38:35 +00:00
|
|
|
// Meaning: pk->primary key field of the table
|
|
|
|
// fk->foreign key to link with parent
|
|
|
|
// nt->nested field (recursive data)
|
|
|
|
// SL->site level info
|
|
|
|
// CL->course level info
|
|
|
|
// UL->user level info
|
|
|
|
// files->table may have files
|
|
|
|
//
|
|
|
|
//-----------------------------------------------------------
|
|
|
|
|
2006-03-21 18:15:09 +00:00
|
|
|
require_once("$CFG->libdir/questionlib.php");
|
2006-03-21 15:38:35 +00:00
|
|
|
|
2007-08-09 21:51:09 +00:00
|
|
|
function backup_question_category_context($bf, $contextid, $course) {
|
2008-06-04 20:51:02 +00:00
|
|
|
global $DB;
|
|
|
|
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = true;
|
|
|
|
$context = get_context_instance_by_id($contextid);
|
|
|
|
$status = $status && fwrite($bf,start_tag("CONTEXT",4,true));
|
|
|
|
switch ($context->contextlevel){
|
|
|
|
case CONTEXT_MODULE:
|
|
|
|
$status = $status && fwrite($bf,full_tag("LEVEL",5,false, 'module'));
|
|
|
|
$status = $status && fwrite($bf,full_tag("INSTANCE",5,false, $context->instanceid));
|
|
|
|
break;
|
|
|
|
case CONTEXT_COURSE:
|
|
|
|
$status = $status && fwrite($bf,full_tag("LEVEL",5,false, 'course'));
|
|
|
|
break;
|
|
|
|
case CONTEXT_COURSECAT:
|
2008-06-04 20:51:02 +00:00
|
|
|
$thiscourse = $DB->get_record('course', array('id'=>$course));
|
2007-08-09 21:51:09 +00:00
|
|
|
$cat = $thiscourse->category;
|
|
|
|
$catno = 1;
|
|
|
|
while($context->instanceid != $cat){
|
|
|
|
$catno ++;
|
|
|
|
if ($cat ==0) {
|
|
|
|
return false;
|
|
|
|
}
|
2008-06-04 20:51:02 +00:00
|
|
|
$cat = $DB->get_field('course_categories', 'parent', array('id'=>$cat));
|
2007-08-09 21:51:09 +00:00
|
|
|
}
|
|
|
|
$status = $status && fwrite($bf,full_tag("LEVEL",5,false, 'coursecategory'));
|
|
|
|
$status = $status && fwrite($bf,full_tag("COURSECATEGORYLEVEL",5,false, $catno));
|
|
|
|
break;
|
|
|
|
case CONTEXT_SYSTEM:
|
|
|
|
$status = $status && fwrite($bf,full_tag("LEVEL",5,false, 'system'));
|
|
|
|
break;
|
|
|
|
default :
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
$status = $status && fwrite($bf,end_tag("CONTEXT",4,true));
|
|
|
|
return $status;
|
|
|
|
}
|
|
|
|
|
2006-03-21 16:50:42 +00:00
|
|
|
function backup_question_categories($bf,$preferences) {
|
2008-06-04 20:51:02 +00:00
|
|
|
global $CFG, $DB;
|
2006-03-21 15:38:35 +00:00
|
|
|
|
|
|
|
$status = true;
|
|
|
|
|
|
|
|
//First, we get the used categories from backup_ids
|
|
|
|
$categories = question_category_ids_by_backup ($preferences->backup_unique_code);
|
|
|
|
|
|
|
|
//If we've categories
|
|
|
|
if ($categories) {
|
|
|
|
//Write start tag
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = $status && fwrite($bf,start_tag("QUESTION_CATEGORIES",2,true));
|
2006-03-21 15:38:35 +00:00
|
|
|
//Iterate over each category
|
|
|
|
foreach ($categories as $cat) {
|
|
|
|
//Start category
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = $status && fwrite ($bf,start_tag("QUESTION_CATEGORY",3,true));
|
2006-03-21 15:38:35 +00:00
|
|
|
//Get category data from question_categories
|
2008-06-04 20:51:02 +00:00
|
|
|
$category = $DB->get_record ("question_categories", array("id"=>$cat->old_id));
|
2006-03-21 15:38:35 +00:00
|
|
|
//Print category contents
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = $status && fwrite($bf,full_tag("ID",4,false,$category->id));
|
|
|
|
$status = $status && fwrite($bf,full_tag("NAME",4,false,$category->name));
|
|
|
|
$status = $status && fwrite($bf,full_tag("INFO",4,false,$category->info));
|
|
|
|
$status = $status && backup_question_category_context($bf, $category->contextid, $preferences->backup_course);
|
|
|
|
$status = $status && fwrite($bf,full_tag("STAMP",4,false,$category->stamp));
|
|
|
|
$status = $status && fwrite($bf,full_tag("PARENT",4,false,$category->parent));
|
|
|
|
$status = $status && fwrite($bf,full_tag("SORTORDER",4,false,$category->sortorder));
|
2006-03-21 15:38:35 +00:00
|
|
|
//Now, backup their questions
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = $status && backup_question($bf,$preferences,$category->id);
|
2006-03-21 15:38:35 +00:00
|
|
|
//End category
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = $status && fwrite ($bf,end_tag("QUESTION_CATEGORY",3,true));
|
2006-03-21 15:38:35 +00:00
|
|
|
}
|
|
|
|
//Write end tag
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = $status && fwrite ($bf,end_tag("QUESTION_CATEGORIES",2,true));
|
2006-03-21 15:38:35 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
return $status;
|
|
|
|
}
|
|
|
|
|
|
|
|
//This function backups all the questions in selected category and their
|
|
|
|
//asociated data
|
2006-12-05 18:14:57 +00:00
|
|
|
function backup_question($bf,$preferences,$category, $level = 4) {
|
2008-06-04 20:51:02 +00:00
|
|
|
global $CFG, $QTYPES, $DB;
|
2006-03-21 15:38:35 +00:00
|
|
|
|
|
|
|
$status = true;
|
|
|
|
|
|
|
|
// We'll fetch the questions sorted by parent so that questions with no parents
|
|
|
|
// (these are the ones which could be parents themselves) are backed up first. This
|
|
|
|
// is important for the recoding of the parent field during the restore process
|
2007-08-09 21:51:09 +00:00
|
|
|
// Only select questions with ids in backup_ids table
|
2008-06-04 20:51:02 +00:00
|
|
|
$questions = $DB->get_records_sql("SELECT q.* FROM {backup_ids} bk, {question} q
|
|
|
|
WHERE q.category= ? AND
|
|
|
|
bk.old_id=q.id AND
|
|
|
|
bk.backup_code = ?
|
|
|
|
ORDER BY parent ASC, id", array($category, $preferences->backup_unique_code));
|
2006-03-21 15:38:35 +00:00
|
|
|
//If there are questions
|
|
|
|
if ($questions) {
|
|
|
|
//Write start tag
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = $status && fwrite ($bf,start_tag("QUESTIONS",$level,true));
|
2006-03-21 15:38:35 +00:00
|
|
|
$counter = 0;
|
|
|
|
//Iterate over each question
|
|
|
|
foreach ($questions as $question) {
|
2008-06-18 14:29:37 +00:00
|
|
|
// Deal with missing question types - they need to be included becuase
|
|
|
|
// user data or quizzes may refer to them.
|
|
|
|
if (!array_key_exists($question->qtype, $QTYPES)) {
|
|
|
|
$question->qtype = 'missingtype';
|
|
|
|
$question->questiontext = '<p>' . get_string('warningmissingtype', 'quiz') . '</p>' . $question->questiontext;
|
|
|
|
}
|
2006-03-21 15:38:35 +00:00
|
|
|
//Start question
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = $status && fwrite ($bf,start_tag("QUESTION",$level + 1,true));
|
2006-03-21 15:38:35 +00:00
|
|
|
//Print question contents
|
2006-12-05 18:14:57 +00:00
|
|
|
fwrite ($bf,full_tag("ID",$level + 2,false,$question->id));
|
|
|
|
fwrite ($bf,full_tag("PARENT",$level + 2,false,$question->parent));
|
|
|
|
fwrite ($bf,full_tag("NAME",$level + 2,false,$question->name));
|
|
|
|
fwrite ($bf,full_tag("QUESTIONTEXT",$level + 2,false,$question->questiontext));
|
|
|
|
fwrite ($bf,full_tag("QUESTIONTEXTFORMAT",$level + 2,false,$question->questiontextformat));
|
|
|
|
fwrite ($bf,full_tag("IMAGE",$level + 2,false,$question->image));
|
|
|
|
fwrite ($bf,full_tag("GENERALFEEDBACK",$level + 2,false,$question->generalfeedback));
|
|
|
|
fwrite ($bf,full_tag("DEFAULTGRADE",$level + 2,false,$question->defaultgrade));
|
|
|
|
fwrite ($bf,full_tag("PENALTY",$level + 2,false,$question->penalty));
|
|
|
|
fwrite ($bf,full_tag("QTYPE",$level + 2,false,$question->qtype));
|
|
|
|
fwrite ($bf,full_tag("LENGTH",$level + 2,false,$question->length));
|
|
|
|
fwrite ($bf,full_tag("STAMP",$level + 2,false,$question->stamp));
|
|
|
|
fwrite ($bf,full_tag("VERSION",$level + 2,false,$question->version));
|
|
|
|
fwrite ($bf,full_tag("HIDDEN",$level + 2,false,$question->hidden));
|
2007-08-09 21:51:09 +00:00
|
|
|
fwrite ($bf,full_tag("TIMECREATED",$level + 2,false,$question->timecreated));
|
|
|
|
fwrite ($bf,full_tag("TIMEMODIFIED",$level + 2,false,$question->timemodified));
|
|
|
|
fwrite ($bf,full_tag("CREATEDBY",$level + 2,false,$question->createdby));
|
|
|
|
fwrite ($bf,full_tag("MODIFIEDBY",$level + 2,false,$question->modifiedby));
|
2006-03-21 18:15:09 +00:00
|
|
|
// Backup question type specific data
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = $status && $QTYPES[$question->qtype]->backup($bf,$preferences,$question->id, $level + 2);
|
2006-03-21 15:38:35 +00:00
|
|
|
//End question
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = $status && fwrite ($bf,end_tag("QUESTION",$level + 1,true));
|
2006-03-21 15:38:35 +00:00
|
|
|
//Do some output
|
|
|
|
$counter++;
|
|
|
|
if ($counter % 10 == 0) {
|
|
|
|
echo ".";
|
|
|
|
if ($counter % 200 == 0) {
|
|
|
|
echo "<br />";
|
|
|
|
}
|
|
|
|
backup_flush(300);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
//Write end tag
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = $status && fwrite ($bf,end_tag("QUESTIONS",$level,true));
|
2006-03-21 15:38:35 +00:00
|
|
|
}
|
|
|
|
return $status;
|
|
|
|
}
|
|
|
|
|
|
|
|
//This function backups the answers data in some question types
|
|
|
|
//(truefalse, shortanswer,multichoice,numerical,calculated)
|
2006-12-05 18:14:57 +00:00
|
|
|
function question_backup_answers($bf,$preferences,$question, $level = 6) {
|
2008-06-04 20:51:02 +00:00
|
|
|
global $CFG, $DB;
|
2006-03-21 15:38:35 +00:00
|
|
|
|
|
|
|
$status = true;
|
|
|
|
|
2008-06-04 20:51:02 +00:00
|
|
|
$answers = $DB->get_records("question_answers", array("question"=>$question), "id");
|
2006-03-21 15:38:35 +00:00
|
|
|
//If there are answers
|
|
|
|
if ($answers) {
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = $status && fwrite ($bf,start_tag("ANSWERS",$level,true));
|
2006-03-21 15:38:35 +00:00
|
|
|
//Iterate over each answer
|
|
|
|
foreach ($answers as $answer) {
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = $status && fwrite ($bf,start_tag("ANSWER",$level + 1,true));
|
2006-03-21 15:38:35 +00:00
|
|
|
//Print answer contents
|
2006-12-05 18:14:57 +00:00
|
|
|
fwrite ($bf,full_tag("ID",$level + 2,false,$answer->id));
|
|
|
|
fwrite ($bf,full_tag("ANSWER_TEXT",$level + 2,false,$answer->answer));
|
|
|
|
fwrite ($bf,full_tag("FRACTION",$level + 2,false,$answer->fraction));
|
|
|
|
fwrite ($bf,full_tag("FEEDBACK",$level + 2,false,$answer->feedback));
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = $status && fwrite ($bf,end_tag("ANSWER",$level + 1,true));
|
2006-03-21 15:38:35 +00:00
|
|
|
}
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = $status && fwrite ($bf,end_tag("ANSWERS",$level,true));
|
2006-03-21 15:38:35 +00:00
|
|
|
}
|
|
|
|
return $status;
|
|
|
|
}
|
|
|
|
|
|
|
|
//This function backups question_numerical_units from different question types
|
2006-03-21 16:50:42 +00:00
|
|
|
function question_backup_numerical_units($bf,$preferences,$question,$level=7) {
|
2008-06-04 20:51:02 +00:00
|
|
|
global $CFG, $DB;
|
2006-03-21 15:38:35 +00:00
|
|
|
|
|
|
|
$status = true;
|
|
|
|
|
2008-06-04 20:51:02 +00:00
|
|
|
$numerical_units = $DB->get_records("question_numerical_units", array("question"=>$question), "id");
|
2006-03-21 15:38:35 +00:00
|
|
|
//If there are numericals_units
|
|
|
|
if ($numerical_units) {
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = $status && fwrite ($bf,start_tag("NUMERICAL_UNITS",$level,true));
|
2006-03-21 15:38:35 +00:00
|
|
|
//Iterate over each numerical_unit
|
|
|
|
foreach ($numerical_units as $numerical_unit) {
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = $status && fwrite ($bf,start_tag("NUMERICAL_UNIT",$level+1,true));
|
2006-03-21 15:38:35 +00:00
|
|
|
//Print numerical_unit contents
|
|
|
|
fwrite ($bf,full_tag("MULTIPLIER",$level+2,false,$numerical_unit->multiplier));
|
|
|
|
fwrite ($bf,full_tag("UNIT",$level+2,false,$numerical_unit->unit));
|
|
|
|
//Now backup numerical_units
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = $status && fwrite ($bf,end_tag("NUMERICAL_UNIT",$level+1,true));
|
2006-03-21 15:38:35 +00:00
|
|
|
}
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = $status && fwrite ($bf,end_tag("NUMERICAL_UNITS",$level,true));
|
2006-03-21 15:38:35 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
return $status;
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
//This function backups dataset_definitions (via question_datasets) from different question types
|
2006-03-21 16:50:42 +00:00
|
|
|
function question_backup_datasets($bf,$preferences,$question,$level=7) {
|
2008-06-04 20:51:02 +00:00
|
|
|
global $CFG, $DB;
|
2006-03-21 15:38:35 +00:00
|
|
|
|
|
|
|
$status = true;
|
|
|
|
|
|
|
|
//First, we get the used datasets for this question
|
2008-06-04 20:51:02 +00:00
|
|
|
$question_datasets = $DB->get_records("question_datasets", array("question"=>$question), "id");
|
2006-03-21 15:38:35 +00:00
|
|
|
//If there are question_datasets
|
|
|
|
if ($question_datasets) {
|
|
|
|
$status = $status &&fwrite ($bf,start_tag("DATASET_DEFINITIONS",$level,true));
|
|
|
|
//Iterate over each question_dataset
|
|
|
|
foreach ($question_datasets as $question_dataset) {
|
|
|
|
$def = NULL;
|
|
|
|
//Get dataset_definition
|
2008-06-04 20:51:02 +00:00
|
|
|
if ($def = $DB->get_record("question_dataset_definitions", array("id"=>$question_dataset->datasetdefinition))) {;
|
2006-03-21 15:38:35 +00:00
|
|
|
$status = $status &&fwrite ($bf,start_tag("DATASET_DEFINITION",$level+1,true));
|
|
|
|
//Print question_dataset contents
|
|
|
|
fwrite ($bf,full_tag("CATEGORY",$level+2,false,$def->category));
|
|
|
|
fwrite ($bf,full_tag("NAME",$level+2,false,$def->name));
|
|
|
|
fwrite ($bf,full_tag("TYPE",$level+2,false,$def->type));
|
|
|
|
fwrite ($bf,full_tag("OPTIONS",$level+2,false,$def->options));
|
|
|
|
fwrite ($bf,full_tag("ITEMCOUNT",$level+2,false,$def->itemcount));
|
|
|
|
//Now backup dataset_entries
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = $status && question_backup_dataset_items($bf,$preferences,$def->id,$level+2);
|
2006-03-21 15:38:35 +00:00
|
|
|
//End dataset definition
|
|
|
|
$status = $status &&fwrite ($bf,end_tag("DATASET_DEFINITION",$level+1,true));
|
|
|
|
}
|
|
|
|
}
|
|
|
|
$status = $status &&fwrite ($bf,end_tag("DATASET_DEFINITIONS",$level,true));
|
|
|
|
}
|
|
|
|
|
|
|
|
return $status;
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
//This function backups datases_items from dataset_definitions
|
2006-03-21 16:50:42 +00:00
|
|
|
function question_backup_dataset_items($bf,$preferences,$datasetdefinition,$level=9) {
|
2008-06-04 20:51:02 +00:00
|
|
|
global $CFG, $DB;
|
2006-03-21 15:38:35 +00:00
|
|
|
|
|
|
|
$status = true;
|
|
|
|
|
|
|
|
//First, we get the datasets_items for this dataset_definition
|
2008-06-04 20:51:02 +00:00
|
|
|
$dataset_items = $DB->get_records("question_dataset_items", array("definition"=>$datasetdefinition), "id");
|
2006-03-21 15:38:35 +00:00
|
|
|
//If there are dataset_items
|
|
|
|
if ($dataset_items) {
|
|
|
|
$status = $status &&fwrite ($bf,start_tag("DATASET_ITEMS",$level,true));
|
|
|
|
//Iterate over each dataset_item
|
|
|
|
foreach ($dataset_items as $dataset_item) {
|
|
|
|
$status = $status &&fwrite ($bf,start_tag("DATASET_ITEM",$level+1,true));
|
|
|
|
//Print question_dataset contents
|
2006-09-19 10:56:00 +00:00
|
|
|
fwrite ($bf,full_tag("NUMBER",$level+2,false,$dataset_item->itemnumber));
|
2006-03-21 15:38:35 +00:00
|
|
|
fwrite ($bf,full_tag("VALUE",$level+2,false,$dataset_item->value));
|
|
|
|
//End dataset definition
|
|
|
|
$status = $status &&fwrite ($bf,end_tag("DATASET_ITEM",$level+1,true));
|
|
|
|
}
|
|
|
|
$status = $status &&fwrite ($bf,end_tag("DATASET_ITEMS",$level,true));
|
|
|
|
}
|
|
|
|
|
|
|
|
return $status;
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
//Backup question_states contents (executed from backup_quiz_attempts)
|
2006-12-05 18:14:57 +00:00
|
|
|
function backup_question_states ($bf,$preferences,$attempt, $level = 6) {
|
2008-06-04 20:51:02 +00:00
|
|
|
global $CFG, $DB;
|
2006-03-21 15:38:35 +00:00
|
|
|
|
|
|
|
$status = true;
|
|
|
|
|
2008-06-04 20:51:02 +00:00
|
|
|
$question_states = $DB->get_records("question_states", array("attempt"=>$attempt),"id");
|
2006-03-21 15:38:35 +00:00
|
|
|
//If there are states
|
|
|
|
if ($question_states) {
|
|
|
|
//Write start tag
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = $status && fwrite ($bf,start_tag("STATES",$level,true));
|
2006-03-21 15:38:35 +00:00
|
|
|
//Iterate over each state
|
|
|
|
foreach ($question_states as $state) {
|
|
|
|
//Start state
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = $status && fwrite ($bf,start_tag("STATE",$level + 1,true));
|
2006-03-21 15:38:35 +00:00
|
|
|
//Print state contents
|
2006-12-05 18:14:57 +00:00
|
|
|
fwrite ($bf,full_tag("ID",$level + 2,false,$state->id));
|
|
|
|
fwrite ($bf,full_tag("QUESTION",$level + 2,false,$state->question));
|
|
|
|
fwrite ($bf,full_tag("SEQ_NUMBER",$level + 2,false,$state->seq_number));
|
|
|
|
fwrite ($bf,full_tag("ANSWER",$level + 2,false,$state->answer));
|
|
|
|
fwrite ($bf,full_tag("TIMESTAMP",$level + 2,false,$state->timestamp));
|
|
|
|
fwrite ($bf,full_tag("EVENT",$level + 2,false,$state->event));
|
|
|
|
fwrite ($bf,full_tag("GRADE",$level + 2,false,$state->grade));
|
|
|
|
fwrite ($bf,full_tag("RAW_GRADE",$level + 2,false,$state->raw_grade));
|
|
|
|
fwrite ($bf,full_tag("PENALTY",$level + 2,false,$state->penalty));
|
2006-03-21 15:38:35 +00:00
|
|
|
//End state
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = $status && fwrite ($bf,end_tag("STATE",$level + 1,true));
|
2006-03-21 15:38:35 +00:00
|
|
|
}
|
|
|
|
//Write end tag
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = $status && fwrite ($bf,end_tag("STATES",$level,true));
|
2006-03-21 15:38:35 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
//Backup question_sessions contents (executed from backup_quiz_attempts)
|
2006-12-05 18:14:57 +00:00
|
|
|
function backup_question_sessions ($bf,$preferences,$attempt, $level = 6) {
|
2008-06-04 20:51:02 +00:00
|
|
|
global $CFG, $DB;
|
2006-03-21 15:38:35 +00:00
|
|
|
|
|
|
|
$status = true;
|
|
|
|
|
2008-06-04 20:51:02 +00:00
|
|
|
$question_sessions = $DB->get_records("question_sessions", array("attemptid"=>$attempt), "id");
|
2006-03-21 15:38:35 +00:00
|
|
|
//If there are sessions
|
|
|
|
if ($question_sessions) {
|
|
|
|
//Write start tag (the funny name 'newest states' has historical reasons)
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = $status && fwrite ($bf,start_tag("NEWEST_STATES",$level,true));
|
2006-03-21 15:38:35 +00:00
|
|
|
//Iterate over each newest_state
|
|
|
|
foreach ($question_sessions as $newest_state) {
|
|
|
|
//Start newest_state
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = $status && fwrite ($bf,start_tag("NEWEST_STATE",$level + 1,true));
|
2006-03-21 15:38:35 +00:00
|
|
|
//Print newest_state contents
|
2006-12-05 18:14:57 +00:00
|
|
|
fwrite ($bf,full_tag("ID",$level + 2,false,$newest_state->id));
|
|
|
|
fwrite ($bf,full_tag("QUESTIONID",$level + 2,false,$newest_state->questionid));
|
|
|
|
fwrite ($bf,full_tag("NEWEST",$level + 2,false,$newest_state->newest));
|
|
|
|
fwrite ($bf,full_tag("NEWGRADED",$level + 2,false,$newest_state->newgraded));
|
|
|
|
fwrite ($bf,full_tag("SUMPENALTY",$level + 2,false,$newest_state->sumpenalty));
|
2007-08-09 21:51:09 +00:00
|
|
|
fwrite ($bf,full_tag("MANUALCOMMENT",$level + 2,false,$newest_state->manualcomment));
|
2006-03-21 15:38:35 +00:00
|
|
|
//End newest_state
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = $status && fwrite ($bf,end_tag("NEWEST_STATE",$level + 1,true));
|
2006-03-21 15:38:35 +00:00
|
|
|
}
|
|
|
|
//Write end tag
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = $status && fwrite ($bf,end_tag("NEWEST_STATES",$level,true));
|
2006-03-21 15:38:35 +00:00
|
|
|
}
|
|
|
|
return $status;
|
|
|
|
}
|
|
|
|
|
|
|
|
//Returns an array of categories id
|
|
|
|
function question_category_ids_by_backup ($backup_unique_code) {
|
2008-06-04 20:51:02 +00:00
|
|
|
global $CFG, $DB;
|
2006-03-21 15:38:35 +00:00
|
|
|
|
2008-06-04 20:51:02 +00:00
|
|
|
return $DB->get_records_sql("SELECT a.old_id, a.backup_code
|
|
|
|
FROM {backup_ids} a
|
|
|
|
WHERE a.backup_code = ? AND
|
|
|
|
a.table_name = 'question_categories'", array($backup_unique_code));
|
2006-03-21 15:38:35 +00:00
|
|
|
}
|
|
|
|
|
2006-03-21 16:50:42 +00:00
|
|
|
function question_ids_by_backup ($backup_unique_code) {
|
2008-06-04 20:51:02 +00:00
|
|
|
global $CFG, $DB;
|
2006-03-21 15:38:35 +00:00
|
|
|
|
2008-06-04 20:51:02 +00:00
|
|
|
return $DB->get_records_sql("SELECT old_id, backup_code
|
|
|
|
FROM {backup_ids}
|
|
|
|
WHERE backup_code = ? AND
|
|
|
|
table_name = 'question'", array($backup_unique_code));
|
2006-03-21 15:38:35 +00:00
|
|
|
}
|
2008-06-06 14:43:15 +00:00
|
|
|
|
2008-01-18 14:49:59 +00:00
|
|
|
//Function for inserting question and category ids into db that are all called from
|
2008-06-06 14:43:15 +00:00
|
|
|
// quiz_check_backup_mods during execution of backup_check.html
|
2006-03-21 15:38:35 +00:00
|
|
|
|
2008-01-18 14:49:59 +00:00
|
|
|
function question_insert_c_and_q_ids_for_course($coursecontext, $backup_unique_code){
|
2008-06-04 20:51:02 +00:00
|
|
|
global $CFG, $DB;
|
2009-01-20 04:24:07 +00:00
|
|
|
// First, all categories from this course's context.
|
2008-06-04 20:51:02 +00:00
|
|
|
$status = $DB->execute("INSERT INTO {backup_ids} (backup_code, table_name, old_id, info)
|
|
|
|
SELECT '$backup_unique_code', 'question_categories', qc.id, 'course'
|
|
|
|
FROM {question_categories} qc
|
|
|
|
WHERE qc.contextid = ?", array($coursecontext->id));
|
2008-01-18 14:49:59 +00:00
|
|
|
$status = $status && question_insert_q_ids($backup_unique_code, 'course');
|
|
|
|
return $status;
|
|
|
|
}
|
2008-06-04 20:51:02 +00:00
|
|
|
|
|
|
|
/**
|
2008-01-18 14:49:59 +00:00
|
|
|
* Insert all question ids for categories whose ids have already been inserted in the backup_ids table
|
|
|
|
* Insert code to identify categories to later insert all question ids later eg. course, quiz or other module name.
|
|
|
|
*/
|
|
|
|
function question_insert_q_ids($backup_unique_code, $info){
|
2008-07-01 13:19:24 +00:00
|
|
|
global $CFG,$DB;
|
2009-01-20 04:24:07 +00:00
|
|
|
//put the ids of the questions from all these categories into the db.
|
2008-06-04 20:51:02 +00:00
|
|
|
$status = $DB->execute("INSERT INTO {backup_ids} (backup_code, table_name, old_id, info)
|
|
|
|
SELECT '$backup_unique_code', 'question', q.id, ''
|
|
|
|
FROM {question} q, {backup_ids} bk
|
2008-06-06 14:43:15 +00:00
|
|
|
WHERE q.category = bk.old_id AND bk.table_name = 'question_categories'
|
2009-01-20 04:24:07 +00:00
|
|
|
AND " . $DB->sql_compare_text('bk.info') . " = ?
|
2008-06-04 20:51:02 +00:00
|
|
|
AND bk.backup_code = ?", array($info, $backup_unique_code));
|
2008-01-18 14:49:59 +00:00
|
|
|
return $status;
|
|
|
|
}
|
2008-06-06 14:43:15 +00:00
|
|
|
|
2008-01-18 14:49:59 +00:00
|
|
|
function question_insert_c_and_q_ids_for_module($backup_unique_code, $course, $modulename, $instances){
|
2008-06-01 16:08:16 +00:00
|
|
|
global $CFG, $DB;
|
2008-01-18 14:49:59 +00:00
|
|
|
$status = true;
|
2008-06-01 16:08:16 +00:00
|
|
|
// using 'dummykeyname' in sql because otherwise $DB->get_records_sql_menu returns an error
|
2008-01-18 14:49:59 +00:00
|
|
|
// if two key names are the same.
|
2008-04-29 03:30:01 +00:00
|
|
|
$cmcontexts = array();
|
|
|
|
if(!empty($instances)) {
|
2008-06-06 14:43:15 +00:00
|
|
|
list($usql, $params) = $DB->get_in_or_equal(array_keys($instances));
|
|
|
|
$params[] = $modulename;
|
|
|
|
$params[] = $course;
|
2008-06-01 16:08:16 +00:00
|
|
|
$cmcontexts = $DB->get_records_sql_menu("SELECT c.id, c.id AS dummykeyname FROM {modules} m,
|
|
|
|
{course_modules} cm, {context} c
|
2008-06-06 14:43:15 +00:00
|
|
|
WHERE cm.instance $usql AND m.name = ? AND m.id = cm.module AND cm.id = c.instanceid
|
|
|
|
AND c.contextlevel = ".CONTEXT_MODULE." AND cm.course = ?", $params);
|
2008-04-29 03:30:01 +00:00
|
|
|
}
|
2008-06-06 14:43:15 +00:00
|
|
|
|
2008-01-18 14:49:59 +00:00
|
|
|
if ($cmcontexts){
|
2008-06-06 14:43:15 +00:00
|
|
|
list($usql, $params) = $DB->get_in_or_equal(array_keys($cmcontexts));
|
2008-06-04 20:51:02 +00:00
|
|
|
$status = $status && $DB->execute("INSERT INTO {backup_ids} (backup_code, table_name, old_id, info)
|
|
|
|
SELECT '$backup_unique_code', 'question_categories', qc.id, '$modulename'
|
|
|
|
FROM {question_categories} qc
|
2008-06-06 14:43:15 +00:00
|
|
|
WHERE qc.contextid $usql", $params);
|
2008-01-18 14:49:59 +00:00
|
|
|
}
|
|
|
|
$status = $status && question_insert_q_ids($backup_unique_code, $modulename);
|
2007-08-09 21:51:09 +00:00
|
|
|
return $status;
|
|
|
|
}
|
2008-01-18 14:49:59 +00:00
|
|
|
|
2007-08-09 21:51:09 +00:00
|
|
|
function question_insert_site_file_names($course, $backup_unique_code){
|
2009-08-18 05:19:00 +00:00
|
|
|
global $QTYPES, $CFG, $DB, $OUTPUT;
|
2007-08-09 21:51:09 +00:00
|
|
|
$status = true;
|
|
|
|
$questionids = question_ids_by_backup ($backup_unique_code);
|
|
|
|
$urls = array();
|
|
|
|
if ($questionids){
|
|
|
|
foreach ($questionids as $question_bk){
|
2008-06-04 20:51:02 +00:00
|
|
|
$question = $DB->get_record('question', array('id'=>$question_bk->old_id));
|
2007-09-29 16:18:01 +00:00
|
|
|
$QTYPES[$question->qtype]->get_question_options($question);
|
2007-08-09 21:51:09 +00:00
|
|
|
$urls = array_merge_recursive($urls, $QTYPES[$question->qtype]->find_file_links($question, SITEID));
|
|
|
|
}
|
|
|
|
}
|
|
|
|
ksort($urls);
|
|
|
|
foreach (array_keys($urls) as $url){
|
|
|
|
if (file_exists($CFG->dataroot.'/'.SITEID.'/'.$url)){
|
|
|
|
$inserturl = new object();
|
|
|
|
$inserturl->backup_code = $backup_unique_code;
|
|
|
|
$inserturl->file_type = 'site';
|
|
|
|
$url = clean_param($url, PARAM_PATH);
|
2008-06-04 20:51:02 +00:00
|
|
|
$inserturl->path = $url;
|
|
|
|
$status = $status && $DB->insert_record('backup_files', $inserturl);
|
2007-08-09 21:51:09 +00:00
|
|
|
} else {
|
2009-08-18 05:19:00 +00:00
|
|
|
echo $OUTPUT->notification(get_string('linkedfiledoesntexist', 'question', $url));
|
2007-08-09 21:51:09 +00:00
|
|
|
}
|
|
|
|
}
|
2006-03-21 16:50:42 +00:00
|
|
|
return $status;
|
2006-03-21 15:38:35 +00:00
|
|
|
}
|
|
|
|
?>
|