Permalink
Browse files

MDL-28226 wrong final quiz grade when regrading with first/last attem…

…pt graded.

This is an intermitted problem that depends on the order the DB returns
rows in the absence of an order-by. At any rate, adding an explicit
order-by fixes it.

Also inprove a PHP doc comment and some code to make the API clearer.
  • Loading branch information...
1 parent 9e47a85 commit 4f24a95cddb4246156b4262f64f252ac2c980212 @timhunt timhunt committed Jul 7, 2011
Showing with 12 additions and 16 deletions.
  1. +9 −13 mod/quiz/locallib.php
  2. +3 −3 mod/quiz/report/overview/report.php
View
@@ -581,25 +581,21 @@ function quiz_save_best_grade($quiz, $userid = null, $attempts = array()) {
/**
* Calculate the overall grade for a quiz given a number of attempts by a particular user.
*
- * @return float The overall grade
- * @param object $quiz The quiz for which the best grade is to be calculated
- * @param array $attempts An array of all the attempts of the user at the quiz
+ * @param object $quiz the quiz settings object.
+ * @param array $attempts an array of all the user's attempts at this quiz in order.
+ * @return float the overall grade
*/
function quiz_calculate_best_grade($quiz, $attempts) {
switch ($quiz->grademethod) {
case QUIZ_ATTEMPTFIRST:
- foreach ($attempts as $attempt) {
- return $attempt->sumgrades;
- }
- break;
+ $firstattempt = reset($attempts);
+ return $firstattempt->sumgrades;
case QUIZ_ATTEMPTLAST:
- foreach ($attempts as $attempt) {
- $final = $attempt->sumgrades;
- }
- return $final;
+ $lastattempt = end($attempts);
+ return $lastattempt->sumgrades;
case QUIZ_GRADEAVERAGE:
$sum = 0;
@@ -608,10 +604,10 @@ function quiz_calculate_best_grade($quiz, $attempts) {
$sum += $attempt->sumgrades;
$count++;
}
- return (float)$sum/$count;
+ return (float) $sum/$count;
- default:
case QUIZ_GRADEHIGHEST:
+ default:
$max = 0;
foreach ($attempts as $attempt) {
if ($attempt->sumgrades > $max) {
@@ -596,7 +596,7 @@ function check_overall_grades($quiz, $userids=array(), $attemptids=array()) {
} else {
$params = array();
}
- $attemptsql .= "{quiz_attempts}.quiz =? AND preview = 0";
+ $attemptsql .= "{quiz_attempts}.quiz = ? AND preview = 0";
$params[] = $quiz->id;
} else {
list($asql, $params) = $DB->get_in_or_equal($attemptids);
@@ -613,10 +613,10 @@ function check_overall_grades($quiz, $userids=array(), $attemptids=array()) {
//not just those that have changed.
$sql = "SELECT qa2.* FROM {quiz_attempts} qa2 WHERE " .
"qa2.userid IN (SELECT DISTINCT userid FROM {quiz_attempts} WHERE $attemptsql) " .
- "AND qa2.timefinish > 0 AND qa2.quiz = ?";
+ "AND qa2.timefinish > 0 AND qa2.quiz = ? ORDER BY qa2.userid, qa2.attempt";
$params[] = $quiz->id;
} else {
- $sql = "SELECT * FROM {quiz_attempts} WHERE $attemptsql AND timefinish > 0";
+ $sql = "SELECT * FROM {quiz_attempts} WHERE $attemptsql AND timefinish > 0 ORDER BY userid, attempt";
}
if ($attempts = $DB->get_records_sql($sql, $params)) {
$attemptsbyuser = quiz_report_index_by_keys($attempts, array('userid', 'id'));

0 comments on commit 4f24a95

Please sign in to comment.