From f0a31525c3d17b6003dc271f5d979c10fb5eaf4c Mon Sep 17 00:00:00 2001 From: lushonline <56685070+lushonline@users.noreply.github.com> Date: Wed, 21 Jul 2021 14:50:40 +0100 Subject: [PATCH] MOODLE_311_STABLE MOODLE_311_STABLE UPDATE Add custom_completion.php Ensure events always sent --- classes/completion/custom_completion.php | 100 ++++++++++++++++++ .../course_module_completedexternally.php | 3 +- .../event/course_module_scoredexternally.php | 4 +- db/services.php | 2 +- grade.php | 4 +- lib.php | 29 ++--- lrs/aboutcontroller.php | 2 +- lrs/statementcontroller.php | 2 +- lrs/xapihelper.php | 2 +- version.php | 4 +- view.php | 5 +- 11 files changed, 131 insertions(+), 26 deletions(-) create mode 100644 classes/completion/custom_completion.php diff --git a/classes/completion/custom_completion.php b/classes/completion/custom_completion.php new file mode 100644 index 0000000..28c5f3c --- /dev/null +++ b/classes/completion/custom_completion.php @@ -0,0 +1,100 @@ +. + +/** + * The mod_externalcontent module custom completion class. + * + * @package mod_externalcontent + * @copyright 2019-2021 LushOnline + * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later + */ + +namespace mod_externalcontent\completion; + +defined('MOODLE_INTERNAL') || die(); + +if (!class_exists('\core_completion\activity_custom_completion')) { + // New API does not exist in this site, so do nothing. + return; +} + +/** + * The mod_externalcontent module custom completion. + * + * @package mod_externalcontent + * @copyright 2019-2021 LushOnline + * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later + */ +class custom_completion extends \core_completion\activity_custom_completion { + /** + * Fetches the completion state for a given completion rule. + * + * @param string $rule The completion rule. + * @return int The completion state. + */ + public function get_state(string $rule): int { + global $DB; + + $this->validate_rule($rule); + // Get external content details. + $externalcontent = $DB->get_record('externalcontent', array('id' => $this->cm->instance), '*', MUST_EXIST); + + switch ($rule) { + case 'completionexternally': + $params = array('userid' => $this->userid, 'externalcontentid' => $externalcontent->id, 'completed' => 1); + $completed = $DB->record_exists('externalcontent_track', $params); + + $status = $completed ? COMPLETION_COMPLETE : COMPLETION_INCOMPLETE; + break; + + default : + $status = COMPLETION_INCOMPLETE; + break; + } + + return $status; + } + + /** + * Fetch the list of custom completion rules that this module defines. + * + * @return array + */ + public static function get_defined_custom_rules(): array { + return ['completionexternally']; + } + + /** + * Returns an associative array of the descriptions of custom completion rules. + * + * @return array + */ + public function get_custom_rule_descriptions(): array { + return ['completionexternally' => get_string('eventcompletedexternally', 'externalcontent')]; + } + + /** + * Returns an array of all completion rules, in the order they should be displayed to users. + * + * @return array + */ + public function get_sort_order(): array { + return [ + 'completionview', + 'completionexternally', + ]; + } +} diff --git a/classes/event/course_module_completedexternally.php b/classes/event/course_module_completedexternally.php index 86e443e..34350ad 100644 --- a/classes/event/course_module_completedexternally.php +++ b/classes/event/course_module_completedexternally.php @@ -70,7 +70,8 @@ public static function get_name() { */ public function get_description() { return get_string('eventcompletedexternallydesc', 'externalcontent', - ['userid' => $this->userid, 'contextinstanceid' => $this->contextinstanceid]); + ['userid' => $this->relateduserid ?? $this->userid, + 'contextinstanceid' => $this->contextinstanceid]); } /** diff --git a/classes/event/course_module_scoredexternally.php b/classes/event/course_module_scoredexternally.php index 6a562c1..3b618a5 100644 --- a/classes/event/course_module_scoredexternally.php +++ b/classes/event/course_module_scoredexternally.php @@ -70,7 +70,9 @@ public static function get_name() { */ public function get_description() { return get_string('eventscoredexternallydesc', 'externalcontent', - ['userid' => $this->userid, 'contextinstanceid' => $this->contextinstanceid, 'score' => $this->other]); + ['userid' => $this->relateduserid ?? $this->userid, + 'contextinstanceid' => $this->contextinstanceid, + 'score' => $this->other]); } /** diff --git a/db/services.php b/db/services.php index 23b1fb4..e8be590 100644 --- a/db/services.php +++ b/db/services.php @@ -46,4 +46,4 @@ 'capabilities' => 'mod/externalcontent:view', 'services' => array(MOODLE_OFFICIAL_MOBILE_SERVICE), ), -); \ No newline at end of file +); diff --git a/grade.php b/grade.php index d16ea1c..203b435 100644 --- a/grade.php +++ b/grade.php @@ -28,7 +28,7 @@ $id = required_param('id', PARAM_INT); if (!$cm = get_coursemodule_from_id('externalcontent', $id)) { - print_error('invalidcoursemodule'); + throw new moodle_exception('invalidcoursemodule', 'error'); } $externalcontent = $DB->get_record('externalcontent', array('id' => $cm->instance), '*', MUST_EXIST); $course = $DB->get_record('course', array('id' => $cm->course), '*', MUST_EXIST); @@ -36,4 +36,4 @@ require_course_login($course, true, $cm); $context = context_module::instance($cm->id); -redirect(new moodle_url('/mod/externalcontent/view.php', array('id' => $cm->id))); \ No newline at end of file +redirect(new moodle_url('/mod/externalcontent/view.php', array('id' => $cm->id))); diff --git a/lib.php b/lib.php index c35cadc..7f039b1 100644 --- a/lib.php +++ b/lib.php @@ -426,6 +426,7 @@ function externalcontent_update_completion_state($course, $cm, $context = null, } $response = new \stdClass(); + $response->userid = $userid; $response->status = false; $response->completionupdated = false; $response->scoreupdated = false; @@ -458,22 +459,22 @@ function externalcontent_update_completion_state($course, $cm, $context = null, } if ($completed) { + $params = array( + 'context' => $context, + 'objectid' => $externalcontent->id, + 'relateduserid' => $userid, + ); + + $event = \mod_externalcontent\event\course_module_completedexternally::create($params); + $event->add_record_snapshot('course_modules', $cm); + $event->add_record_snapshot('course', $course); + $event->add_record_snapshot('externalcontent', $externalcontent); + $event->trigger(); + if ($currentstate->completionstate == COMPLETION_COMPLETE) { $response->message .= ' External content completion state already set to COMPLETION_COMPLETE.'; $response->completionupdated = false; } else { - $params = array( - 'context' => $context, - 'objectid' => $externalcontent->id, - 'userid' => $userid, - ); - - $event = \mod_externalcontent\event\course_module_completedexternally::create($params); - $event->add_record_snapshot('course_modules', $cm); - $event->add_record_snapshot('course', $course); - $event->add_record_snapshot('externalcontent', $externalcontent); - $event->trigger(); - $completion->update_state($cm, COMPLETION_COMPLETE, $userid); $response->message .= ' External content completion status set to COMPLETION_COMPLETE.'; $response->completionupdated = true; @@ -484,7 +485,7 @@ function externalcontent_update_completion_state($course, $cm, $context = null, $params = array( 'context' => $context, 'objectid' => $externalcontent->id, - 'userid' => $userid, + 'relateduserid' => $userid, 'other' => $score, ); @@ -646,4 +647,4 @@ function externalcontent_update_grades($externalcontent, $userid = 0, $removegra } else { externalcontent_grade_item_update($externalcontent); } -} \ No newline at end of file +} diff --git a/lrs/aboutcontroller.php b/lrs/aboutcontroller.php index bad1a18..3d6ea08 100644 --- a/lrs/aboutcontroller.php +++ b/lrs/aboutcontroller.php @@ -75,4 +75,4 @@ public function about(Request $request, Response $response, array $args) { return $response->withJson($versions); } -} \ No newline at end of file +} diff --git a/lrs/statementcontroller.php b/lrs/statementcontroller.php index 1f63e9c..71da3c8 100644 --- a/lrs/statementcontroller.php +++ b/lrs/statementcontroller.php @@ -228,4 +228,4 @@ public function notimplemented(Request $request, Response $response, array $args ->withAddedHeader('Content-Type', 'text/plain') ->write($message); } -} \ No newline at end of file +} diff --git a/lrs/xapihelper.php b/lrs/xapihelper.php index b31940e..8dbd802 100644 --- a/lrs/xapihelper.php +++ b/lrs/xapihelper.php @@ -216,4 +216,4 @@ public static function mark_completed($record) { } return $response; } -} \ No newline at end of file +} diff --git a/version.php b/version.php index f010868..a4fbf56 100644 --- a/version.php +++ b/version.php @@ -24,8 +24,8 @@ defined('MOODLE_INTERNAL') || die(); -$plugin->version = 2021030400; +$plugin->version = 2021072100; $plugin->requires = 2018051700; // Requires this Moodle version v3.5 see https://docs.moodle.org/dev/Releases. $plugin->component = 'mod_externalcontent'; $plugin->maturity = MATURITY_STABLE; -$plugin->release = '1.6'; +$plugin->release = '1.7'; diff --git a/view.php b/view.php index 1776752..8cc99bc 100644 --- a/view.php +++ b/view.php @@ -35,14 +35,14 @@ if ($p) { if (!$externalcontent = $DB->get_record('externalcontent', array('id' => $p))) { - print_error('invalidaccessparameter'); + throw new moodle_exception('invalidaccessparameter', 'error'); } $cm = get_coursemodule_from_instance('externalcontent', $externalcontent->id, $externalcontent->course, false, MUST_EXIST); } else { if (!$cm = get_coursemodule_from_id('externalcontent', $id)) { - print_error('invalidcoursemodule'); + throw new moodle_exception('invalidcoursemodule', 'error'); } $externalcontent = $DB->get_record('externalcontent', array('id' => $cm->instance), '*', MUST_EXIST); } @@ -91,3 +91,4 @@ } echo $OUTPUT->footer(); +