From cf6bc1b1a2a91394125a5c32dfcf1bdcf71aec59 Mon Sep 17 00:00:00 2001 From: Frederic Massart Date: Fri, 8 Aug 2014 10:51:22 +0800 Subject: [PATCH] MDL-46571 gradereport_history: Unit tests for the table_sql results Part of MDL-46191 --- .../history/classes/output/tablelog.php | 4 +- grade/report/history/tests/report_test.php | 235 ++++++++++++++++++ 2 files changed, 237 insertions(+), 2 deletions(-) create mode 100644 grade/report/history/tests/report_test.php diff --git a/grade/report/history/classes/output/tablelog.php b/grade/report/history/classes/output/tablelog.php index 86f142a6179..c55dbec19d6 100644 --- a/grade/report/history/classes/output/tablelog.php +++ b/grade/report/history/classes/output/tablelog.php @@ -70,8 +70,8 @@ class tablelog extends \table_sql implements \renderable { * @param \context_course $context Context of the report. * @param \moodle_url $url url of the page where this table would be displayed. * @param array $filters options are: - * users : limit to specific users (default: none) - * gradeitem : limit to specific item (default: all) + * userids : limit to specific users (default: none) + * itemid : limit to specific grade item (default: all) * grader : limit to specific graders (default: all) * datefrom : start of date range * datetill : end of date range diff --git a/grade/report/history/tests/report_test.php b/grade/report/history/tests/report_test.php new file mode 100644 index 00000000000..624eb0a2e86 --- /dev/null +++ b/grade/report/history/tests/report_test.php @@ -0,0 +1,235 @@ +. + +/** + * Grade history report test. + * + * @package gradereport_history + * @copyright 2014 Frédéric Massart - FMCorz.net + * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later + */ + +defined('MOODLE_INTERNAL') || die(); + +/** + * Grade history report test class. + * + * @package gradereport_history + * @copyright 2014 Frédéric Massart - FMCorz.net + * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later + */ +class gradereport_history_report_testcase extends advanced_testcase { + + /** + * Create some grades. + */ + public function test_query_db() { + $this->resetAfterTest(); + + // Making the setup. + $c1 = $this->getDataGenerator()->create_course(); + $c2 = $this->getDataGenerator()->create_course(); + $c1ctx = context_course::instance($c1->id); + $c2ctx = context_course::instance($c2->id); + + // Users. + $u1 = $this->getDataGenerator()->create_user(); + $u2 = $this->getDataGenerator()->create_user(); + $u3 = $this->getDataGenerator()->create_user(); + $u4 = $this->getDataGenerator()->create_user(); + $u5 = $this->getDataGenerator()->create_user(); + $grader1 = $this->getDataGenerator()->create_user(); + $grader2 = $this->getDataGenerator()->create_user(); + + // Modules. + $c1m1 = $this->getDataGenerator()->create_module('assign', array('course' => $c1)); + $c1m2 = $this->getDataGenerator()->create_module('assign', array('course' => $c1)); + $c1m3 = $this->getDataGenerator()->create_module('assign', array('course' => $c1)); + $c2m1 = $this->getDataGenerator()->create_module('assign', array('course' => $c2)); + + // Creating fake history data. + $giparams = array('itemtype' => 'mod', 'itemmodule' => 'assign'); + $grades = array(); + + $gi = grade_item::fetch($giparams + array('iteminstance' => $c1m1->id)); + $grades['c1m1u1'] = $this->create_grade_history(array('itemid' => $gi->id, 'userid' => $u1->id, + 'timemodified' => time() - 3600)); + $grades['c1m1u2'] = $this->create_grade_history(array('itemid' => $gi->id, 'userid' => $u2->id, + 'timemodified' => time() + 3600)); + $grades['c1m1u3'] = $this->create_grade_history(array('itemid' => $gi->id, 'userid' => $u3->id)); + $grades['c1m1u4'] = $this->create_grade_history(array('itemid' => $gi->id, 'userid' => $u4->id)); + $grades['c1m1u5'] = $this->create_grade_history(array('itemid' => $gi->id, 'userid' => $u5->id)); + + $gi = grade_item::fetch($giparams + array('iteminstance' => $c1m2->id)); + $grades['c1m2u1'] = $this->create_grade_history(array('itemid' => $gi->id, 'userid' => $u1->id)); + $grades['c1m2u2'] = $this->create_grade_history(array('itemid' => $gi->id, 'userid' => $u2->id)); + + $gi = grade_item::fetch($giparams + array('iteminstance' => $c1m3->id)); + $grades['c1m3u1'] = $this->create_grade_history(array('itemid' => $gi->id, 'userid' => $u1->id)); + + $gi = grade_item::fetch($giparams + array('iteminstance' => $c2m1->id)); + $grades['c2m1u1'] = $this->create_grade_history(array('itemid' => $gi->id, 'userid' => $u1->id, + 'usermodified' => $grader1->id)); + $grades['c2m1u2'] = $this->create_grade_history(array('itemid' => $gi->id, 'userid' => $u2->id, + 'usermodified' => $grader1->id)); + $grades['c2m1u3'] = $this->create_grade_history(array('itemid' => $gi->id, 'userid' => $u3->id, + 'usermodified' => $grader1->id)); + $grades['c2m1u4'] = $this->create_grade_history(array('itemid' => $gi->id, 'userid' => $u4->id, + 'usermodified' => $grader2->id)); + + // Histories where grades have not been revised.. + $grades['c2m1u5'] = $this->create_grade_history(array('itemid' => $gi->id, 'userid' => $u5->id, + 'timemodified' => time() - 60)); + $grades['c2m1u5'] = $this->create_grade_history(array('itemid' => $gi->id, 'userid' => $u5->id, + 'timemodified' => time())); + $grades['c2m1u5'] = $this->create_grade_history(array('itemid' => $gi->id, 'userid' => $u5->id, + 'timemodified' => time() + 60)); + + // TODO MDL-46737 Handle deleted/non-existing grade items. + // Histories with missing grade items, considered as deleted. + // $grades['c2x1u5'] = $this->create_grade_history($giparams + array('itemid' => -1, 'userid' => $u5->id, 'courseid' => $c1->id)); + // $grades['c2x2u5'] = $this->create_grade_history($giparams + array('itemid' => 999999, 'userid' => $u5->id, 'courseid' => $c1->id)); + + // Basic filtering based on course id. + $this->assertEquals(8, $this->get_tablelog_results($c1ctx, array(), true)); + $this->assertEquals(7, $this->get_tablelog_results($c2ctx, array(), true)); + + // Filtering on 1 user. + $this->assertEquals(3, $this->get_tablelog_results($c1ctx, array('userids' => $u1->id), true)); + + // Filtering on more users. + $this->assertEquals(4, $this->get_tablelog_results($c1ctx, array('userids' => "$u1->id,$u3->id"), true)); + + // Filtering based on one grade item. + $gi = grade_item::fetch($giparams + array('iteminstance' => $c1m1->id)); + $this->assertEquals(5, $this->get_tablelog_results($c1ctx, array('itemid' => $gi->id), true)); + $gi = grade_item::fetch($giparams + array('iteminstance' => $c1m3->id)); + $this->assertEquals(1, $this->get_tablelog_results($c1ctx, array('itemid' => $gi->id), true)); + + // Filtering based on the grader. + $this->assertEquals(3, $this->get_tablelog_results($c2ctx, array('grader' => $grader1->id), true)); + $this->assertEquals(1, $this->get_tablelog_results($c2ctx, array('grader' => $grader2->id), true)); + + // Filtering based on date. + $results = $this->get_tablelog_results($c1ctx, array('datefrom' => time() + 1800)); + $this->assertGradeHistoryIds(array($grades['c1m1u2']->id), $results); + $results = $this->get_tablelog_results($c1ctx, array('datetill' => time() - 1800)); + $this->assertGradeHistoryIds(array($grades['c1m1u1']->id), $results); + $results = $this->get_tablelog_results($c1ctx, array('datefrom' => time() - 1800, 'datetill' => time() + 1800)); + $this->assertGradeHistoryIds(array($grades['c1m1u3']->id, $grades['c1m1u4']->id, $grades['c1m1u5']->id, + $grades['c1m2u1']->id, $grades['c1m2u2']->id, $grades['c1m3u1']->id), $results); + + // Filtering based on revised only. + $this->assertEquals(3, $this->get_tablelog_results($c2ctx, array('userids' => $u5->id), true)); + $this->assertEquals(1, $this->get_tablelog_results($c2ctx, array('userids' => $u5->id, 'revisedonly' => true), true)); + } + + /** + * Asserts that the array of grade objects contains exactly the right IDs. + * + * @param array $expectedids Array of expected IDs. + * @param array $objects Array of objects returned by the table. + */ + protected function assertGradeHistoryIds(array $expectedids, array $objects) { + $this->assertCount(count($expectedids), $objects); + $expectedids = array_flip($expectedids); + foreach ($objects as $object) { + $this->assertArrayHasKey($object->id, $expectedids); + unset($expectedids[$object->id]); + } + $this->assertCount(0, $expectedids); + } + + /** + * Create a new grade history entry. + * + * @param array $params Of values. + * @return object The grade object. + */ + protected function create_grade_history($params) { + global $DB; + $params = (array) $params; + + if (!isset($params['itemid'])) { + throw new coding_exception('Missing itemid key.'); + } + if (!isset($params['userid'])) { + throw new coding_exception('Missing userid key.'); + } + + // Default object. + $grade = new stdClass(); + $grade->itemid = 0; + $grade->userid = 0; + $grade->oldid = 123; + $grade->rawgrade = 50; + $grade->finalgrade = 50; + $grade->timecreated = time(); + $grade->timemodified = time(); + $grade->information = ''; + $grade->informationformat = FORMAT_PLAIN; + $grade->feedback = ''; + $grade->feedbackformat = FORMAT_PLAIN; + $grade->usermodified = 2; + + // Merge with data passed. + $grade = (object) array_merge((array) $grade, $params); + + // Insert record. + $grade->id = $DB->insert_record('grade_grades_history', $grade); + + return $grade; + } + + /** + * Returns a table log object. + * + * @param context_course $coursecontext The course context. + * @param array $filters An array of filters. + * @param boolean $count When true, returns a count rather than an array of objects. + * @return mixed Count or array of objects. + */ + protected function get_tablelog_results($coursecontext, $filters = array(), $count = false) { + $table = new gradereport_history_tests_tablelog('something', $coursecontext, new moodle_url(''), $filters); + return $table->get_test_results($count); + } + +} + +/** + * Extended table log class. + */ +class gradereport_history_tests_tablelog extends \gradereport_history\output\tablelog { + + /** + * Get the test results. + * + * @param boolean $count Whether or not we want the count. + * @return mixed Count or array of objects. + */ + public function get_test_results($count = false) { + global $DB; + if ($count) { + list($sql, $params) = $this->get_sql_and_params(true); + return $DB->count_records_sql($sql, $params); + } else { + $this->setup(); + list($sql, $params) = $this->get_sql_and_params(); + return $DB->get_records_sql($sql, $params); + } + } + +}