From e82f6a6e83b11f2960441753ea985149d26d9dc9 Mon Sep 17 00:00:00 2001 From: Riedler Date: Sat, 6 Sep 2025 18:54:42 +0200 Subject: [PATCH 1/3] fix: improved perf when getting courses --- lbplanner/classes/helpers/course_helper.php | 31 +++++++++++++++++---- 1 file changed, 25 insertions(+), 6 deletions(-) diff --git a/lbplanner/classes/helpers/course_helper.php b/lbplanner/classes/helpers/course_helper.php index dc822929..2923f7f3 100644 --- a/lbplanner/classes/helpers/course_helper.php +++ b/lbplanner/classes/helpers/course_helper.php @@ -17,6 +17,7 @@ namespace local_lbplanner\helpers; use core\context\course as context_course; +use DateTimeImmutable; use dml_exception; use dml_write_exception; use local_lbplanner\model\course; @@ -81,10 +82,32 @@ public static function get_all_eduplanner_courses(bool $onlyenrolled=true): arra global $DB, $USER; $userid = $USER->id; + // NOTE: we could use enrol_get_my_courses() and get_courses() here. + // But their perf is so abysmal that we have to roll our own function. + // The code is largely leaned on how these functions work internally, optimized for our purposes. if ($onlyenrolled) { - $mdlcourses = enrol_get_my_courses(); + $mdlcourses = $DB->get_records_sql(" + SELECT c.* FROM {course} c + INNER JOIN {enrol} e ON e.courseid = c.id + INNER JOIN {user_enrolments} ue ON (ue.enrolid = e.id AND ue.userid = :userid) + WHERE ue.status = :active AND e.status = :enabled AND ue.timestart <= :now AND c.enddate > :ayearago", + [ + "userid"=>$userid, + "active"=>ENROL_USER_ACTIVE, + "enabled"=>ENROL_INSTANCE_ENABLED, + "now"=>time(), + "ayearago"=>(new DateTimeImmutable('1 year ago'))->getTimestamp(), + ] + ); } else { - $mdlcourses = get_courses(); + $mdlcourses = $DB->get_records_sql(" + SELECT c.* FROM {course} c + WHERE c.enddate > :ayearago", + [ + "now"=>time(), + "ayearago"=>(new DateTimeImmutable('1 year ago'))->getTimestamp(), + ] + ); } // Remove Duplicates. $mdlcourses = array_unique($mdlcourses, SORT_REGULAR); @@ -92,10 +115,6 @@ public static function get_all_eduplanner_courses(bool $onlyenrolled=true): arra foreach ($mdlcourses as $mdlcourse) { $courseid = $mdlcourse->id; - // Check if the course is outdated. - if (!course::check_year($mdlcourse)) { - continue; - } // Check if the course is already in the Eduplanner database. if ($DB->record_exists(self::EDUPLANNER_COURSE_TABLE, ['courseid' => $courseid, 'userid' => $userid])) { $fetchedcourse = self::get_eduplanner_course($courseid, $userid); From 5d67abd3c498e3a780a4018c1240072b3e46531f Mon Sep 17 00:00:00 2001 From: Riedler Date: Sat, 6 Sep 2025 20:26:05 +0200 Subject: [PATCH 2/3] feat: added eduplanner tag to be able to vignette courses --- lbplanner/classes/helpers/course_helper.php | 23 +++++++++++++++++++-- lbplanner/db/upgrade.php | 18 +++++++++++++++- lbplanner/version.php | 2 +- 3 files changed, 39 insertions(+), 4 deletions(-) diff --git a/lbplanner/classes/helpers/course_helper.php b/lbplanner/classes/helpers/course_helper.php index 2923f7f3..2243ba3a 100644 --- a/lbplanner/classes/helpers/course_helper.php +++ b/lbplanner/classes/helpers/course_helper.php @@ -17,6 +17,8 @@ namespace local_lbplanner\helpers; use core\context\course as context_course; +use core_tag_collection; +use core_tag_tag; use DateTimeImmutable; use dml_exception; use dml_write_exception; @@ -37,6 +39,11 @@ class course_helper { */ const EDUPLANNER_COURSE_TABLE = 'local_lbplanner_courses'; + /** + * The tag name to identify courses as "should show up in eduplanner" + */ + const EDUPLANNER_TAG = 'eduplanner'; + /** * A list of nice colors to choose from :) */ @@ -82,6 +89,8 @@ public static function get_all_eduplanner_courses(bool $onlyenrolled=true): arra global $DB, $USER; $userid = $USER->id; + $lbptag = core_tag_tag::get_by_name(core_tag_collection::get_default(), self::EDUPLANNER_TAG, strictness:MUST_EXIST); + // NOTE: we could use enrol_get_my_courses() and get_courses() here. // But their perf is so abysmal that we have to roll our own function. // The code is largely leaned on how these functions work internally, optimized for our purposes. @@ -90,22 +99,32 @@ public static function get_all_eduplanner_courses(bool $onlyenrolled=true): arra SELECT c.* FROM {course} c INNER JOIN {enrol} e ON e.courseid = c.id INNER JOIN {user_enrolments} ue ON (ue.enrolid = e.id AND ue.userid = :userid) - WHERE ue.status = :active AND e.status = :enabled AND ue.timestart <= :now AND c.enddate > :ayearago", + INNER JOIN {tag_instance} ti ON (ti.itemid = c.id) + WHERE + ue.status = :active + AND e.status = :enabled + AND ue.timestart <= :now + AND c.enddate > :ayearago + AND ti.tagid = :lbptagid + AND ti.itemtype = \"course\"", [ "userid"=>$userid, "active"=>ENROL_USER_ACTIVE, "enabled"=>ENROL_INSTANCE_ENABLED, "now"=>time(), "ayearago"=>(new DateTimeImmutable('1 year ago'))->getTimestamp(), + "lbptagid"=>$lbptag->id, ] ); } else { $mdlcourses = $DB->get_records_sql(" SELECT c.* FROM {course} c - WHERE c.enddate > :ayearago", + INNER JOIN {tag_instance} ti ON (ti.itemid = c.id) + WHERE c.enddate > :ayearago AND ti.tagid = :lbptagid AND ti.itemtype = \"course\"", [ "now"=>time(), "ayearago"=>(new DateTimeImmutable('1 year ago'))->getTimestamp(), + "lbptagid"=>$lbptag->id, ] ); } diff --git a/lbplanner/db/upgrade.php b/lbplanner/db/upgrade.php index 75fcee5e..7d871a6c 100644 --- a/lbplanner/db/upgrade.php +++ b/lbplanner/db/upgrade.php @@ -23,7 +23,9 @@ * @license https://creativecommons.org/licenses/by-nc-sa/4.0/ CC-BY-NC-SA 4.0 International or later */ -use local_lbplanner\helpers\config_helper; +use core\context\course as context_course; + +use local_lbplanner\helpers\{config_helper, course_helper}; /** * Upgrades the DB version @@ -70,5 +72,19 @@ function xmldb_local_lbplanner_upgrade($oldversion): bool { upgrade_plugin_savepoint(true, 202509020001, 'local', 'lbplanner'); } + if ($oldversion < 202509060000) { + // Adds the eduplanner tag to the default collection. + core_tag_tag::create_if_missing(core_tag_collection::get_default(), [course_helper::EDUPLANNER_TAG], true); + } + if ($oldversion < 202509060001) { + // Adds eduplanner tag to all courses that are already in the eduplanner courses table, to make managers' lives easier. + $defaulttagcoll = core_tag_collection::get_default(); + $tag = core_tag_tag::get_by_name($defaulttagcoll, course_helper::EDUPLANNER_TAG, strictness:MUST_EXIST); + $courseids = $DB->get_fieldset(course_helper::EDUPLANNER_COURSE_TABLE, 'courseid'); + $courseids = array_unique($courseids, SORT_REGULAR); // Dedupe. + foreach ($courseids as $courseid) { + core_tag_tag::add_item_tag('core', 'course', $courseid, context_course::instance($courseid), $tag->rawname); + } + } return true; } diff --git a/lbplanner/version.php b/lbplanner/version.php index 88cb9940..768f6dc9 100644 --- a/lbplanner/version.php +++ b/lbplanner/version.php @@ -28,7 +28,7 @@ $plugin->maturity = MATURITY_BETA; $plugin->component = 'local_lbplanner'; $plugin->release = '1.0.2'; -$plugin->version = 202509020004; +$plugin->version = 202509050001; $plugin->dependencies = [ // Depend upon version 2023110600 of local_modcustomfields. 'local_modcustomfields' => 2023110600, From 8ae956fc3e695897a9dbb7391c093d33aace2715 Mon Sep 17 00:00:00 2001 From: Riedler Date: Sat, 6 Sep 2025 20:50:40 +0200 Subject: [PATCH 3/3] fix: pacified moodle code checker --- lbplanner/classes/helpers/course_helper.php | 24 ++++++++++----------- 1 file changed, 12 insertions(+), 12 deletions(-) diff --git a/lbplanner/classes/helpers/course_helper.php b/lbplanner/classes/helpers/course_helper.php index 2243ba3a..a4580178 100644 --- a/lbplanner/classes/helpers/course_helper.php +++ b/lbplanner/classes/helpers/course_helper.php @@ -91,9 +91,9 @@ public static function get_all_eduplanner_courses(bool $onlyenrolled=true): arra $lbptag = core_tag_tag::get_by_name(core_tag_collection::get_default(), self::EDUPLANNER_TAG, strictness:MUST_EXIST); - // NOTE: we could use enrol_get_my_courses() and get_courses() here. - // But their perf is so abysmal that we have to roll our own function. - // The code is largely leaned on how these functions work internally, optimized for our purposes. + /* NOTE: We could use enrol_get_my_courses() and get_courses() here. + But their perf is so abysmal that we have to roll our own function. + The code is largely leaned on how these functions work internally, optimized for our purposes. */ if ($onlyenrolled) { $mdlcourses = $DB->get_records_sql(" SELECT c.* FROM {course} c @@ -108,12 +108,12 @@ public static function get_all_eduplanner_courses(bool $onlyenrolled=true): arra AND ti.tagid = :lbptagid AND ti.itemtype = \"course\"", [ - "userid"=>$userid, - "active"=>ENROL_USER_ACTIVE, - "enabled"=>ENROL_INSTANCE_ENABLED, - "now"=>time(), - "ayearago"=>(new DateTimeImmutable('1 year ago'))->getTimestamp(), - "lbptagid"=>$lbptag->id, + "userid" => $userid, + "active" => ENROL_USER_ACTIVE, + "enabled" => ENROL_INSTANCE_ENABLED, + "now" => time(), + "ayearago" => (new DateTimeImmutable('1 year ago'))->getTimestamp(), + "lbptagid" => $lbptag->id, ] ); } else { @@ -122,9 +122,9 @@ public static function get_all_eduplanner_courses(bool $onlyenrolled=true): arra INNER JOIN {tag_instance} ti ON (ti.itemid = c.id) WHERE c.enddate > :ayearago AND ti.tagid = :lbptagid AND ti.itemtype = \"course\"", [ - "now"=>time(), - "ayearago"=>(new DateTimeImmutable('1 year ago'))->getTimestamp(), - "lbptagid"=>$lbptag->id, + "now" => time(), + "ayearago" => (new DateTimeImmutable('1 year ago'))->getTimestamp(), + "lbptagid" => $lbptag->id, ] ); }