Skip to content

Commit

Permalink
Merge branch 'MDL-52852-master' of git://github.com/jleyva/moodle
Browse files Browse the repository at this point in the history
  • Loading branch information
danpoltawski committed Mar 21, 2016
2 parents 121b46e + 96d5607 commit f6a0594
Show file tree
Hide file tree
Showing 4 changed files with 157 additions and 2 deletions.
85 changes: 85 additions & 0 deletions mod/quiz/classes/external.php
Original file line number Diff line number Diff line change
Expand Up @@ -1073,4 +1073,89 @@ public static function get_attempt_summary_returns() {
);
}

/**
* Describes the parameters for save_attempt.
*
* @return external_external_function_parameters
* @since Moodle 3.1
*/
public static function save_attempt_parameters() {
return new external_function_parameters (
array(
'attemptid' => new external_value(PARAM_INT, 'attempt id'),
'data' => new external_multiple_structure(
new external_single_structure(
array(
'name' => new external_value(PARAM_RAW, 'data name'),
'value' => new external_value(PARAM_RAW, 'data value'),
)
), 'the data to be saved'
),
'preflightdata' => new external_multiple_structure(
new external_single_structure(
array(
'name' => new external_value(PARAM_ALPHANUMEXT, 'data name'),
'value' => new external_value(PARAM_RAW, 'data value'),
)
), 'Preflight required data (like passwords)', VALUE_DEFAULT, array()
)
)
);
}

/**
* Processes save requests during the quiz. This function is intended for the quiz auto-save feature.
*
* @param int $attemptid attempt id
* @param array $data the data to be saved
* @param array $preflightdata preflight required data (like passwords)
* @return array of warnings and execution result
* @since Moodle 3.1
*/
public static function save_attempt($attemptid, $data, $preflightdata = array()) {
global $DB;

$warnings = array();

$params = array(
'attemptid' => $attemptid,
'data' => $data,
'preflightdata' => $preflightdata,
);
$params = self::validate_parameters(self::save_attempt_parameters(), $params);

// Add a page, required by validate_attempt.
list($attemptobj, $messages) = self::validate_attempt($params);

$transaction = $DB->start_delegated_transaction();
// Create the $_POST object required by the question engine.
$_POST = array();
foreach ($data as $element) {
$_POST[$element['name']] = $element['value'];
}
$timenow = time();
$attemptobj->process_auto_save($timenow);
$transaction->allow_commit();

$result = array();
$result['status'] = true;
$result['warnings'] = $warnings;
return $result;
}

/**
* Describes the save_attempt return value.
*
* @return external_single_structure
* @since Moodle 3.1
*/
public static function save_attempt_returns() {
return new external_single_structure(
array(
'status' => new external_value(PARAM_BOOL, 'status: true if success'),
'warnings' => new external_warnings(),
)
);
}

}
10 changes: 10 additions & 0 deletions mod/quiz/db/services.php
Original file line number Diff line number Diff line change
Expand Up @@ -100,4 +100,14 @@
'capabilities' => 'mod/quiz:attempt',
'services' => array(MOODLE_OFFICIAL_MOBILE_SERVICE)
),

'mod_quiz_save_attempt' => array(
'classname' => 'mod_quiz_external',
'methodname' => 'save_attempt',
'description' => 'Processes save requests during the quiz.
This function is intended for the quiz auto-save feature.',
'type' => 'write',
'capabilities' => 'mod/quiz:attempt',
'services' => array(MOODLE_OFFICIAL_MOBILE_SERVICE)
),
);
62 changes: 61 additions & 1 deletion mod/quiz/tests/external_test.php
Original file line number Diff line number Diff line change
Expand Up @@ -139,7 +139,7 @@ private function create_quiz_with_questions($startattempt = false, $finishattemp
// Finish the attempt.
$attemptobj->process_finish(time(), false);
}
return array($quiz, $context, $quizobj, $attempt, $attemptobj);
return array($quiz, $context, $quizobj, $attempt, $attemptobj, $quba);
} else {
return array($quiz, $context, $quizobj);
}
Expand Down Expand Up @@ -950,4 +950,64 @@ public function test_get_attempt_summary() {

}

/**
* Test save_attempt
*/
public function test_save_attempt() {

// Create a new quiz with one attempt started.
list($quiz, $context, $quizobj, $attempt, $attemptobj, $quba) = $this->create_quiz_with_questions(true);

// Response for slot 1.
$prefix = $quba->get_field_prefix(1);
$data = array(
array('name' => 'slots', 'value' => 1),
array('name' => $prefix . ':sequencecheck',
'value' => $attemptobj->get_question_attempt(1)->get_sequence_check_count()),
array('name' => $prefix . 'answer', 'value' => 1),
);

$this->setUser($this->student);

$result = mod_quiz_external::save_attempt($attempt->id, $data);
$result = external_api::clean_returnvalue(mod_quiz_external::save_attempt_returns(), $result);
$this->assertTrue($result['status']);

// Now, get the summary.
$result = mod_quiz_external::get_attempt_summary($attempt->id);
$result = external_api::clean_returnvalue(mod_quiz_external::get_attempt_summary_returns(), $result);

// Check it's marked as completed only the first one.
$this->assertEquals('complete', $result['questions'][0]['state']);
$this->assertEquals('todo', $result['questions'][1]['state']);
$this->assertEquals(1, $result['questions'][0]['number']);
$this->assertEquals(2, $result['questions'][1]['number']);
$this->assertFalse($result['questions'][0]['flagged']);
$this->assertFalse($result['questions'][1]['flagged']);
$this->assertEmpty($result['questions'][0]['mark']);
$this->assertEmpty($result['questions'][1]['mark']);

// Now, second slot.
$prefix = $quba->get_field_prefix(2);
$data = array(
array('name' => 'slots', 'value' => 2),
array('name' => $prefix . ':sequencecheck',
'value' => $attemptobj->get_question_attempt(1)->get_sequence_check_count()),
array('name' => $prefix . 'answer', 'value' => 1),
);

$result = mod_quiz_external::save_attempt($attempt->id, $data);
$result = external_api::clean_returnvalue(mod_quiz_external::save_attempt_returns(), $result);
$this->assertTrue($result['status']);

// Now, get the summary.
$result = mod_quiz_external::get_attempt_summary($attempt->id);
$result = external_api::clean_returnvalue(mod_quiz_external::get_attempt_summary_returns(), $result);

// Check it's marked as completed only the first one.
$this->assertEquals('complete', $result['questions'][0]['state']);
$this->assertEquals('complete', $result['questions'][1]['state']);

}

}
2 changes: 1 addition & 1 deletion mod/quiz/version.php
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@

defined('MOODLE_INTERNAL') || die();

$plugin->version = 2016032101;
$plugin->version = 2016032102;
$plugin->requires = 2015111000;
$plugin->component = 'mod_quiz';
$plugin->cron = 60;

0 comments on commit f6a0594

Please sign in to comment.