MDL-36088 questions: Add new events

This commit is contained in:
Stephen Bourget 2016-08-21 21:41:16 -04:00 committed by VinhLe
parent 14cdf51189
commit 93e435b909
25 changed files with 1636 additions and 30 deletions

View File

@ -142,6 +142,17 @@ $string['errorprocessingresponses'] = 'An error occurred while processing your r
$string['errorsavingcomment'] = 'Error saving the comment for question {$a->name} in the database.';
$string['errorupdatingattempt'] = 'Error updating attempt {$a->id} in the database.';
$string['eventquestioncategorycreated'] = 'Question category created';
$string['eventquestioncategorydeleted'] = 'Question category deleted';
$string['eventquestioncategorymoved'] = 'Question category moved';
$string['eventquestioncategoryupdated'] = 'Question category updated';
$string['eventquestioncategoryviewed'] = 'Question category viewed';
$string['eventquestioncreated'] = 'Question created';
$string['eventquestiondeleted'] = 'Question deleted';
$string['eventquestionmoved'] = 'Question moved';
$string['eventquestionpreviewed'] = 'Question previewed';
$string['eventquestionsexported'] = 'Questions exported';
$string['eventquestionsimported'] = 'Questions imported';
$string['eventquestionupdated'] = 'Question updated';
$string['export'] = 'Export';
$string['exportcategory'] = 'Export category';
$string['exportcategory_help'] = 'This setting determines the category from which the exported questions will be taken.

View File

@ -0,0 +1,98 @@
<?php
// This file is part of Moodle - http://moodle.org/
//
// Moodle is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// Moodle is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with Moodle. If not, see <http://www.gnu.org/licenses/>.
/**
* Base class for question events.
*
* @package core
* @copyright 2016 Stephen Bourget
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
namespace core\event;
defined('MOODLE_INTERNAL') || die();
/**
* Base class for question events.
*
* @package core
* @since Moodle 3.2
* @copyright 2016 Stephen Bourget
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
class question_base extends base {
/**
* Init method.
*/
protected function init() {
$this->data['edulevel'] = self::LEVEL_TEACHING;
}
/**
* Returns relevant URL.
*
* @return \moodle_url
*/
public function get_url() {
if ($this->courseid) {
$cat = $this->other['categoryid'] . ',' . $this->contextid;
if ($this->contextlevel == CONTEXT_MODULE) {
return new \moodle_url('/question/edit.php', array('cmid' => $this->contextinstanceid, 'cat' => $cat, 'lastchanged' => $this->objectid));
}
return new \moodle_url('/question/edit.php', array('courseid' => $this->courseid, 'cat' => $cat, 'lastchanged' => $this->objectid));
}
// Lets try viewing from the frontpage for contexts above course.
return new \moodle_url('/question/category.php', array('courseid' => SITEID, 'edit' => $this->other['categoryid'], 'lastchanged' => $this->objectid));
}
/**
* Custom validations.
*
* @throws \coding_exception
* @return void
*/
protected function validate_data() {
parent::validate_data();
if (!isset($this->other['categoryid'])) {
throw new \coding_exception('The \'categoryid\' must be set in \'other\'.');
}
}
/**
* Returns DB mappings used with backup / restore.
*
* @return array
*/
public static function get_objectid_mapping() {
return array('db' => 'question', 'restore' => 'question');
}
/**
* Used for maping events on restore
*
* @return array
*/
public static function get_other_mapping() {
$othermapped = array();
$othermapped['categoryid'] = array('db' => 'question_categories', 'restore' => 'question_categories');
return $othermapped;
}
}

View File

@ -0,0 +1,72 @@
<?php
// This file is part of Moodle - http://moodle.org/
//
// Moodle is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// Moodle is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with Moodle. If not, see <http://www.gnu.org/licenses/>.
/**
* Base class for question category events.
*
* @package core
* @copyright 2016 Stephen Bourget
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
namespace core\event;
defined('MOODLE_INTERNAL') || die();
/**
* Base class for question category events
*
* @package core
* @since Moodle 3.6
* @copyright 2016 Stephen Bourget
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
class question_category_base extends base {
/**
* Init method.
*/
protected function init() {
$this->data['objecttable'] = 'question_categories';
$this->data['edulevel'] = self::LEVEL_TEACHING;
}
/**
* Returns relevant URL.
*
* @return \moodle_url
*/
public function get_url() {
if ($this->courseid) {
$cat = $this->objectid . ',' . $this->contextid;
if ($this->contextlevel == CONTEXT_MODULE) {
return new \moodle_url('/question/edit.php', array('cmid' => $this->contextinstanceid, 'cat' => $cat));
}
return new \moodle_url('/question/edit.php', array('courseid' => $this->courseid, 'cat' => $cat));
}
// Lets try viewing from the frontpage for contexts above course.
return new \moodle_url('/question/category.php', array('courseid' => SITEID, 'edit' => $this->objectid));
}
/**
* Returns DB mappings used with backup / restore.
* @return array
*/
public static function get_objectid_mapping() {
return array('db' => 'question_categories', 'restore' => 'question_categories');
}
}

View File

@ -34,7 +34,7 @@ defined('MOODLE_INTERNAL') || die();
* @copyright 2014 Mark Nelson <markn@moodle.com>
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
class question_category_created extends base {
class question_category_created extends question_category_base {
/**
* Init method.
@ -63,26 +63,6 @@ class question_category_created extends base {
return "The user with id '$this->userid' created the question category with id '$this->objectid'.";
}
/**
* Returns relevant URL.
*
* @return \moodle_url
*/
public function get_url() {
if ($this->courseid) {
$cat = $this->objectid . ',' . $this->contextid;
if ($this->contextlevel == CONTEXT_MODULE) {
return new \moodle_url('/question/edit.php', array('cmid' => $this->contextinstanceid, 'cat' => $cat));
}
return new \moodle_url('/question/edit.php', array('courseid' => $this->courseid, 'cat' => $cat));
}
// Bad luck, there does not seem to be any simple intelligent way
// to go to specific question category in context above course,
// let's try to edit it from frontpage which may surprisingly work.
return new \moodle_url('/question/category.php', array('courseid' => SITEID, 'edit' => $this->objectid));
}
/**
* Return the legacy event log data.
*
@ -97,7 +77,4 @@ class question_category_created extends base {
return null;
}
public static function get_objectid_mapping() {
return array('db' => 'question_categories', 'restore' => 'question_category');
}
}

View File

@ -0,0 +1,66 @@
<?php
// This file is part of Moodle - http://moodle.org/
//
// Moodle is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// Moodle is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with Moodle. If not, see <http://www.gnu.org/licenses/>.
/**
* Question category deleted event.
*
* @package core
* @copyright 2016 Stephen Bourget
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
namespace core\event;
defined('MOODLE_INTERNAL') || die();
/**
* Question category deleted event class.
*
* @package core
* @since Moodle 3.2
* @copyright 2016 Stephen Bourget
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
class question_category_deleted extends question_category_base {
/**
* Init method.
*/
protected function init() {
$this->data['objecttable'] = 'question_categories';
$this->data['crud'] = 'd';
$this->data['edulevel'] = self::LEVEL_TEACHING;
}
/**
* Returns localised general event name.
*
* @return string
*/
public static function get_name() {
return get_string('eventquestioncategorydeleted', 'question');
}
/**
* Returns description of what happened.
*
* @return string
*/
public function get_description() {
return "The user with id '$this->userid' deleted the question category with id '$this->objectid'.";
}
}

View File

@ -0,0 +1,66 @@
<?php
// This file is part of Moodle - http://moodle.org/
//
// Moodle is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// Moodle is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with Moodle. If not, see <http://www.gnu.org/licenses/>.
/**
* Question category moved event.
*
* @package core
* @copyright 2016 Stephen Bourget
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
namespace core\event;
defined('MOODLE_INTERNAL') || die();
/**
* Question category moved event class.
*
* @package core
* @since Moodle 3.2
* @copyright 2016 Stephen Bourget
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
class question_category_moved extends question_category_base {
/**
* Init method.
*/
protected function init() {
$this->data['objecttable'] = 'question_categories';
$this->data['crud'] = 'u';
$this->data['edulevel'] = self::LEVEL_TEACHING;
}
/**
* Returns localised general event name.
*
* @return string
*/
public static function get_name() {
return get_string('eventquestioncategorymoved', 'question');
}
/**
* Returns description of what happened.
*
* @return string
*/
public function get_description() {
return "The user with id '$this->userid' moved the question category with id '$this->objectid'.";
}
}

View File

@ -0,0 +1,65 @@
<?php
// This file is part of Moodle - http://moodle.org/
//
// Moodle is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// Moodle is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with Moodle. If not, see <http://www.gnu.org/licenses/>.
/**
* Question category updated event.
*
* @package core
* @copyright 2016 Stephen Bourget
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
namespace core\event;
defined('MOODLE_INTERNAL') || die();
/**
* Question category updated event class.
*
* @package core
* @since Moodle 3.6
* @copyright 2016 Stephen Bourget
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
class question_category_updated extends question_category_base {
/**
* Init method.
*/
protected function init() {
$this->data['objecttable'] = 'question_categories';
$this->data['crud'] = 'u';
$this->data['edulevel'] = self::LEVEL_TEACHING;
}
/**
* Returns localised general event name.
*
* @return string
*/
public static function get_name() {
return get_string('eventquestioncategoryupdated', 'question');
}
/**
* Returns description of what happened.
*
* @return string
*/
public function get_description() {
return "The user with id '$this->userid' updated the question category with id '$this->objectid'.";
}
}

View File

@ -0,0 +1,66 @@
<?php
// This file is part of Moodle - http://moodle.org/
//
// Moodle is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// Moodle is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with Moodle. If not, see <http://www.gnu.org/licenses/>.
/**
* Question category viewed event.
*
* @package core
* @copyright 2016 Stephen Bourget
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
namespace core\event;
defined('MOODLE_INTERNAL') || die();
/**
* Question category viewed event class.
*
* @package core
* @since Moodle 3.2
* @copyright 2016 Stephen Bourget
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
class question_category_viewed extends question_category_base {
/**
* Init method.
*/
protected function init() {
$this->data['objecttable'] = 'question_categories';
$this->data['crud'] = 'r';
$this->data['edulevel'] = self::LEVEL_TEACHING;
}
/**
* Returns localised general event name.
*
* @return string
*/
public static function get_name() {
return get_string('eventquestioncategoryviewed', 'question');
}
/**
* Returns description of what happened.
*
* @return string
*/
public function get_description() {
return "The user with id '$this->userid' viewed the question category with id '$this->objectid'.";
}
}

View File

@ -0,0 +1,88 @@
<?php
// This file is part of Moodle - http://moodle.org/
//
// Moodle is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// Moodle is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with Moodle. If not, see <http://www.gnu.org/licenses/>.
/**
* Question created event.
*
* @package core
* @copyright 2016 Stephen Bourget
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
namespace core\event;
defined('MOODLE_INTERNAL') || die();
/**
* Question created event class.
*
* @property-read array $other {
* Extra information about the event.
*
* - int categoryid: The ID of the category where the question resides
* }
*
* @package core
* @since Moodle 3.2
* @copyright 2016 Stephen Bourget
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
class question_created extends question_base {
/**
* Init method.
*/
protected function init() {
$this->data['objecttable'] = 'question';
$this->data['crud'] = 'c';
$this->data['edulevel'] = self::LEVEL_TEACHING;
}
/**
* Returns localised general event name.
*
* @return string
*/
public static function get_name() {
return get_string('eventquestioncreated', 'question');
}
/**
* Returns description of what happened.
*
* @return string
*/
public function get_description() {
return "The user with id '$this->userid' created a question with the id of '$this->objectid'".
" in the category with the id '".$this->other['categoryid']."'.";
}
/**
* Returns relevant URL.
*
* @return \moodle_url
*/
public function get_url() {
if ($this->courseid) {
if ($this->contextlevel == CONTEXT_MODULE) {
return new \moodle_url('/question/preview.php', array('cmid' => $this->contextinstanceid, 'id' => $this->objectid));
}
return new \moodle_url('/question/preview.php', array('courseid' => $this->courseid, 'id' => $this->objectid));
}
// Lets try editing from the frontpage for contexts above course.
return new \moodle_url('/question/preview.php', array('courseid' => SITEID, 'id' => $this->objectid));
}
}

View File

@ -0,0 +1,83 @@
<?php
// This file is part of Moodle - http://moodle.org/
//
// Moodle is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// Moodle is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with Moodle. If not, see <http://www.gnu.org/licenses/>.
/**
* Question deleted event.
*
* @package core
* @copyright 2016 Stephen Bourget
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
namespace core\event;
defined('MOODLE_INTERNAL') || die();
/**
* Question deleted event class.
*
* @property-read array $other {
* Extra information about the event.
*
* - int categoryid: The ID of the category where the question resides
* }
*
* @package core
* @since Moodle 3.2
* @copyright 2016 Stephen Bourget
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
class question_deleted extends question_base {
/**
* Init method.
*/
protected function init() {
$this->data['objecttable'] = 'question';
$this->data['crud'] = 'd';
$this->data['edulevel'] = self::LEVEL_TEACHING;
}
/**
* Returns localised general event name.
*
* @return string
*/
public static function get_name() {
return get_string('eventquestiondeleted', 'question');
}
/**
* Returns description of what happened.
*
* @return string
*/
public function get_description() {
return "The user with id '$this->userid' deleted the question with id '$this->objectid'".
" from the category with the id '".$this->other['categoryid']."'.";
}
/**
* Returns relevant URL.
* This is needed to override the function in question_base
*
* @return \moodle_url
*/
public function get_url() {
// No URL for delete.
return null;
}
}

View File

@ -0,0 +1,130 @@
<?php
// This file is part of Moodle - http://moodle.org/
//
// Moodle is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// Moodle is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with Moodle. If not, see <http://www.gnu.org/licenses/>.
/**
* Question moved event.
*
* @package core
* @copyright 2016 Stephen Bourget
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
namespace core\event;
defined('MOODLE_INTERNAL') || die();
/**
* Question moved event class.
*
* @property-read array $other {
* Extra information about the event.
*
* - int categoryid: The ID of the category where the question resides
* }
*
* @package core
* @since Moodle 3.6
* @copyright 2016 Stephen Bourget
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
class question_moved extends base {
/**
* Init method.
*/
protected function init() {
$this->data['objecttable'] = 'question';
$this->data['crud'] = 'u';
$this->data['edulevel'] = self::LEVEL_TEACHING;
}
/**
* Returns localised general event name.
*
* @return string
*/
public static function get_name() {
return get_string('eventquestionmoved', 'question');
}
/**
* Returns description of what happened.
*
* @return string
*/
public function get_description() {
return "The user with id '$this->userid' moved the question with the id of '$this->objectid'".
" from the category with the id of '".$this->other['oldcategoryid'].
"' to the category with the id of '".$this->other['newcategoryid']."'.";
}
/**
* Returns relevant URL.
*
* @return \moodle_url
*/
public function get_url() {
if ($this->courseid) {
$cat = $this->other['newcategoryid'] . ',' . $this->contextid;
if ($this->contextlevel == CONTEXT_MODULE) {
return new \moodle_url('/question/edit.php', array('cmid' => $this->contextinstanceid, 'cat' => $cat, 'lastchanged' => $this->objectid));
}
return new \moodle_url('/question/edit.php', array('courseid' => $this->courseid, 'cat' => $cat, 'lastchanged' => $this->objectid));
}
// Lets try viewing from the frontpage for contexts above course.
return new \moodle_url('/question/category.php', array('courseid' => SITEID, 'edit' => $this->other['newcategoryid'], 'lastchanged' => $this->objectid));
}
/**
* Custom validations.
*
* @throws \coding_exception
* @return void
*/
protected function validate_data() {
parent::validate_data();
if (!isset($this->other['oldcategoryid'])) {
throw new \coding_exception('The \'oldcategoryid\' must be set in \'other\'.');
}
if (!isset($this->other['newcategoryid'])) {
throw new \coding_exception('The \'newcategoryid\' must be set in \'other\'.');
}
}
/**
* Returns DB mappings used with backup / restore.
*
* @return array
*/
public static function get_objectid_mapping() {
return array('db' => 'question', 'restore' => 'question');
}
/**
* Used for maping events on restore
*
* @return array
*/
public static function get_other_mapping() {
$othermapped = array();
$othermapped['newcategoryid'] = array('db' => 'question_categories', 'restore' => 'question_categories');
$othermapped['oldcategoryid'] = array('db' => 'question_categories', 'restore' => 'question_categories');
return $othermapped;
}
}

View File

@ -0,0 +1,72 @@
<?php
// This file is part of Moodle - http://moodle.org/
//
// Moodle is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// Moodle is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with Moodle. If not, see <http://www.gnu.org/licenses/>.
/**
* Question previewed event.
*
* @package core
* @copyright 2016 Stephen Bourget
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
namespace core\event;
defined('MOODLE_INTERNAL') || die();
/**
* Question previewed event class.
*
* @property-read array $other {
* Extra information about the event.
*
* - int categoryid: The ID of the category where the question resides
* }
*
* @package core
* @since Moodle 3.2
* @copyright 2016 Stephen Bourget
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
class question_previewed extends question_base {
/**
* Init method.
*/
protected function init() {
$this->data['objecttable'] = 'question';
$this->data['crud'] = 'r';
$this->data['edulevel'] = self::LEVEL_TEACHING;
}
/**
* Returns localised general event name.
*
* @return string
*/
public static function get_name() {
return get_string('eventquestionpreviewed', 'question');
}
/**
* Returns description of what happened.
*
* @return string
*/
public function get_description() {
return "The user with id '$this->userid' previewed the question with the id of '$this->objectid'.";
}
}

View File

@ -0,0 +1,72 @@
<?php
// This file is part of Moodle - http://moodle.org/
//
// Moodle is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// Moodle is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with Moodle. If not, see <http://www.gnu.org/licenses/>.
/**
* Question updated event.
*
* @package core
* @copyright 2016 Stephen Bourget
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
namespace core\event;
defined('MOODLE_INTERNAL') || die();
/**
* Question updated event class.
*
* @property-read array $other {
* Extra information about the event.
*
* - int categoryid: The ID of the category where the question resides
* }
*
* @package core
* @since Moodle 3.6
* @copyright 2016 Stephen Bourget
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
class question_updated extends question_base {
/**
* Init method.
*/
protected function init() {
$this->data['objecttable'] = 'question';
$this->data['crud'] = 'u';
$this->data['edulevel'] = self::LEVEL_TEACHING;
}
/**
* Returns localised general event name.
*
* @return string
*/
public static function get_name() {
return get_string('eventquestionupdated', 'question');
}
/**
* Returns description of what happened.
*
* @return string
*/
public function get_description() {
return "The user with id '$this->userid' updated the question with the id of '$this->objectid'.";
}
}

View File

@ -0,0 +1,107 @@
<?php
// This file is part of Moodle - http://moodle.org/
//
// Moodle is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// Moodle is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with Moodle. If not, see <http://www.gnu.org/licenses/>.
/**
* Questions exported event.
*
* @package core
* @copyright 2016 Stephen Bourget
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
namespace core\event;
defined('MOODLE_INTERNAL') || die();
/**
* Question category exported event class.
*
* @package core
* @since Moodle 3.2
* @copyright 2016 Stephen Bourget
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
class questions_exported extends base {
/**
* Init method.
*/
protected function init() {
$this->data['crud'] = 'r';
$this->data['edulevel'] = self::LEVEL_TEACHING;
}
/**
* Returns localised general event name.
*
* @return string
*/
public static function get_name() {
return get_string('eventquestionsexported', 'question');
}
/**
* Returns description of what happened.
*
* @return string
*/
public function get_description() {
return "The user with id '$this->userid' exported questions in '". $this->other['format'].
"' format from the category with id '".$this->other['categoryid']."'.";
}
/**
* Returns relevant URL.
*
* @return \moodle_url
*/
public function get_url() {
if ($this->courseid) {
$cat = $this->other['categoryid'] . ',' . $this->contextid;
if ($this->contextlevel == CONTEXT_MODULE) {
return new \moodle_url('/question/edit.php', array('cmid' => $this->contextinstanceid, 'cat' => $cat));
}
return new \moodle_url('/question/edit.php', array('courseid' => $this->courseid, 'cat' => $cat));
}
return new \moodle_url('/question/category.php', array('courseid' => SITEID, 'edit' => $this->other['categoryid']));
}
/**
* Custom validations.
*
* @throws \coding_exception
* @return void
*/
protected function validate_data() {
parent::validate_data();
if (!isset($this->other['format'])) {
throw new \coding_exception('The \'format\' must be set in \'other\'.');
}
}
/**
* Returns DB mappings used with backup / restore.
* This is needed to override the function in question_base
*
* @return array
*/
public static function get_objectid_mapping() {
// No mappings.
return array();
}
}

View File

@ -0,0 +1,109 @@
<?php
// This file is part of Moodle - http://moodle.org/
//
// Moodle is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// Moodle is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with Moodle. If not, see <http://www.gnu.org/licenses/>.
/**
* Questions imported event.
*
* @package core
* @copyright 2016 Stephen Bourget
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
namespace core\event;
defined('MOODLE_INTERNAL') || die();
/**
* Question category imported event class.
*
* @package core
* @since Moodle 3.2
* @copyright 2016 Stephen Bourget
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
class questions_imported extends question_base {
/**
* Init method.
*/
protected function init() {
$this->data['crud'] = 'c';
$this->data['edulevel'] = self::LEVEL_TEACHING;
}
/**
* Returns localised general event name.
*
* @return string
*/
public static function get_name() {
return get_string('eventquestionsimported', 'question');
}
/**
* Returns description of what happened.
*
* @return string
*/
public function get_description() {
return "The user with id '$this->userid' imported questions in '". $this->other['format'].
"' format into the category with id '".$this->other['categoryid']."'.";
}
/**
* Returns relevant URL.
*
* @return \moodle_url
*/
public function get_url() {
if ($this->courseid) {
$cat = $this->other['categoryid'] . ',' . $this->contextid;
if ($this->contextlevel == CONTEXT_MODULE) {
return new \moodle_url('/question/edit.php', array('cmid' => $this->contextinstanceid, 'cat' => $cat));
}
return new \moodle_url('/question/edit.php', array('courseid' => $this->courseid, 'cat' => $cat));
}
return new \moodle_url('/question/category.php', array('courseid' => SITEID, 'edit' => $this->other['categoryid']));
}
/**
* Custom validations.
*
* @throws \coding_exception
* @return void
*/
protected function validate_data() {
parent::validate_data();
if (!isset($this->other['categoryid'])) {
throw new \coding_exception('The \'categoryid\' must be set in \'other\'.');
}
if (!isset($this->other['format'])) {
throw new \coding_exception('The \'format\' must be set in \'other\'.');
}
}
/**
* Returns DB mappings used with backup / restore.
* This is needed to override the function in question_base
*
* @return array
*/
public static function get_objectid_mapping() {
// No mappings.
return array();
}
}

View File

@ -380,6 +380,16 @@ function question_delete_question($questionid) {
// Finally delete the question record itself
$DB->delete_records('question', array('id' => $questionid));
question_bank::notify_question_edited($questionid);
// Log the deletion of this question.
$eventparams = array(
'contextid' => $question->contextid,
'objectid' => $question->id,
'other' => array('categoryid' => $question->category)
);
$event = \core\event\question_deleted::create($eventparams);
$event->trigger();
}
/**
@ -673,7 +683,7 @@ function question_move_questions_to_category($questionids, $newcategoryid) {
array('id' => $newcategoryid));
list($questionidcondition, $params) = $DB->get_in_or_equal($questionids);
$questions = $DB->get_records_sql("
SELECT q.id, q.qtype, qc.contextid, q.idnumber
SELECT q.id, q.qtype, qc.contextid, q.idnumber, q.category
FROM {question} q
JOIN {question_categories} qc ON q.category = qc.id
WHERE q.id $questionidcondition", $params);
@ -703,6 +713,15 @@ function question_move_questions_to_category($questionids, $newcategoryid) {
$q->idnumber = $question->idnumber . '_' . $unique;
$DB->update_record('question', $q);
}
// Log this question move.
$eventparams = array(
'contextid' => $question->contextid,
'objectid' => $question->id,
'other' => array('oldcategoryid' => $question->category, 'newcategoryid' => $newcategoryid)
);
$event = \core\event\question_moved::create($eventparams);
$event->trigger();
}
// Move the questions themselves.

View File

@ -81,6 +81,13 @@ if ($param->moveupcontext || $param->movedowncontext) {
print_error('invalidcontext');
}
$oldcat = $DB->get_record('question_categories', array('id' => $catid), '*', MUST_EXIST);
// Log the move to another context.
$params = array(
'objectid' => explode(',',$pagevars['cat'], -1)[0],
'contextid' => $param->tocontext,
);
$event = \core\event\question_category_moved::create($params);
$event->trigger();
$qcobject->update_category($catid, "{$newtopcat->id},{$param->tocontext}", $oldcat->name, $oldcat->info);
// The previous line does a redirect().
}

View File

@ -76,6 +76,27 @@ class question_category_list extends moodle_list {
$topcategory = question_get_top_category($item->item->contextid, true);
return $topcategory->id;
}
public function process_actions($left, $right, $moveup, $movedown) {
if (!empty($left)) {
// Moved Left (In to another category).
$params = array(
'objectid' => $left,
'contextid' => $this->context->id
);
$event = \core\event\question_category_moved::create($params);
$event->trigger();
} else if (!empty($right)) {
// Moved Right (Out of the current category).
$params = array(
'objectid' => $right,
'contextid' => $this->context->id
);
$event = \core\event\question_category_moved::create($params);
$event->trigger();
}
parent::process_actions($left, $right, $moveup, $movedown);
}
}
@ -375,6 +396,15 @@ class question_category_object {
/// Finally delete the category itself
$DB->delete_records("question_categories", array("id" => $category->id));
// Log the deletion of this category.
$params = array(
'objectid' => $category->id,
'contextid' => $category->contextid
);
$event = \core\event\question_category_deleted::create($params);
$event->trigger();
}
public function move_questions_and_delete_category($oldcat, $newcat){
@ -458,9 +488,18 @@ class question_category_object {
/**
* Updates an existing category with given params
*
* @param int $updateid
* @param int $newparent
* @param string $newname
* @param string $newinfo
* @param int $newinfoformat
* @param int $idnumber
* @param bool $redirect
* @return int
*/
public function update_category($updateid, $newparent, $newname, $newinfo, $newinfoformat = FORMAT_HTML,
$idnumber = null) {
$idnumber = null, $redirect = true) {
global $CFG, $DB;
if (empty($newname)) {
print_error('categorynamecantbeblank', 'question');
@ -519,6 +558,14 @@ class question_category_object {
}
$DB->update_record('question_categories', $cat);
// Log the update of this category.
$params = array(
'objectid' => $cat->id,
'contextid' => $cat->contextid
);
$event = \core\event\question_category_updated::create($params);
$event->trigger();
// If the category name has changed, rename any random questions in that category.
if ($oldcat->name != $cat->name) {
$where = "qtype = 'random' AND category = ? AND " . $DB->sql_compare_text('questiontext') . " = ?";
@ -538,6 +585,8 @@ class question_category_object {
// Cat param depends on the context id, so update it.
$this->pageurl->param('cat', $updateid . ',' . $tocontextid);
redirect($this->pageurl);
if ($redirect) {
redirect($this->pageurl); // Always redirect after successful action.
}
}
}

View File

@ -39,8 +39,6 @@ $PAGE->set_url($url);
$questionbank = new core_question\bank\view($contexts, $thispageurl, $COURSE, $cm);
$questionbank->process_actions();
// TODO log this page view.
$context = $contexts->lowest();
$streditingquestions = get_string('editquestions', 'question');
$PAGE->set_title($streditingquestions);
@ -57,4 +55,13 @@ $questionbank->display('questions', $pagevars['qpage'], $pagevars['qperpage'],
$pagevars['qbshowtext'], $pagevars['qtagids']);
echo "</div>\n";
// Log the view of this category.
$categoryid = explode(',' , urldecode($pagevars['cat']));
$params = array(
'objectid' => $categoryid[0],
'context' => $context
);
$event = \core\event\question_category_viewed::create($params);
$event->trigger();
echo $OUTPUT->footer();

View File

@ -77,6 +77,14 @@ if ($from_form = $export_form->get_data()) {
echo get_string('yourfileshoulddownload', 'question', $export_url->out());
echo $OUTPUT->box_end();
// Log the export of these questions.
$eventparams = array(
'contextid' => $category->contextid,
'other' => array('format' => $from_form->format, 'categoryid' => $category->id)
);
$event = \core\event\questions_exported::create($eventparams);
$event->trigger();
// Don't allow force download for behat site, as pop-up can't be handled by selenium.
if (!defined('BEHAT_SITE_RUNNING')) {
$PAGE->requires->js_function_call('document.location.replace', array($export_url->out(false)), false, 1);

View File

@ -129,6 +129,14 @@ if ($form = $import_form->get_data()) {
print_error('cannotimport', '', $thispageurl->out());
}
// Log the import into this category.
$eventparams = array(
'contextid' => $category->contextid,
'other' => array('format' => $form->format, 'categoryid' => $category->id)
);
$event = \core\event\questions_imported::create($eventparams);
$event->trigger();
$params = $thispageurl->params() + array(
'category' => $qformat->category->id . ',' . $qformat->category->contextid);
echo $OUTPUT->continue_button(new moodle_url('edit.php', $params));

View File

@ -280,6 +280,16 @@ if (question_has_capability_on($question, 'view')) {
get_string('exportonequestion', 'question'));
}
// Log the preview of this question.
$eventparams = array(
'context' => $context,
'objectid' => $question->id,
'other' => array('categoryid' => $question->category)
);
$newquestion = true;
$event = \core\event\question_previewed::create($eventparams);
$event->trigger();
// Display the settings form.
$optionsform->display();

View File

@ -73,4 +73,398 @@ class core_question_events_testcase extends advanced_testcase {
$this->assertEventLegacyLogData($expected, $event);
$this->assertEventContextNotUsed($event);
}
/**
* Test the question category deleted event.
*/
public function test_question_category_deleted() {
$this->setAdminUser();
$course = $this->getDataGenerator()->create_course();
$quiz = $this->getDataGenerator()->create_module('quiz', array('course' => $course->id));
$contexts = new question_edit_contexts(context_module::instance($quiz->cmid));
$defaultcategoryobj = question_make_default_categories(array($contexts->lowest()));
$defaultcategory = $defaultcategoryobj->id . ',' . $defaultcategoryobj->contextid;
$qcobject = new question_category_object(
1,
new moodle_url('/mod/quiz/edit.php', array('cmid' => $quiz->cmid)),
$contexts->having_one_edit_tab_cap('categories'),
$defaultcategoryobj->id,
$defaultcategory,
null,
$contexts->having_cap('moodle/question:add'));
// Create the category.
$categoryid = $qcobject->add_category($defaultcategory, 'newcategory', '', true);
// Trigger and capture the event.
$sink = $this->redirectEvents();
$qcobject->delete_category($categoryid);
$events = $sink->get_events();
$event = reset($events);
// Check that the event data is valid.
$this->assertInstanceOf('\core\event\question_category_deleted', $event);
$this->assertEquals(context_module::instance($quiz->cmid), $event->get_context());
$this->assertEquals($categoryid, $event->objectid);
$this->assertDebuggingNotCalled();
}
/**
* Test the question category updated event.
*/
public function test_question_category_updated() {
$this->setAdminUser();
$course = $this->getDataGenerator()->create_course();
$quiz = $this->getDataGenerator()->create_module('quiz', array('course' => $course->id));
$contexts = new question_edit_contexts(context_module::instance($quiz->cmid));
$defaultcategoryobj = question_make_default_categories(array($contexts->lowest()));
$defaultcategory = $defaultcategoryobj->id . ',' . $defaultcategoryobj->contextid;
$qcobject = new question_category_object(
1,
new moodle_url('/mod/quiz/edit.php', array('cmid' => $quiz->cmid)),
$contexts->having_one_edit_tab_cap('categories'),
$defaultcategoryobj->id,
$defaultcategory,
null,
$contexts->having_cap('moodle/question:add'));
// Create the category.
$categoryid = $qcobject->add_category($defaultcategory, 'newcategory', '', true);
// Trigger and capture the event.
$sink = $this->redirectEvents();
$qcobject->update_category($categoryid, $defaultcategory, 'updatedcategory', '', FORMAT_HTML, '', false);
$events = $sink->get_events();
$event = reset($events);
// Check that the event data is valid.
$this->assertInstanceOf('\core\event\question_category_updated', $event);
$this->assertEquals(context_module::instance($quiz->cmid), $event->get_context());
$this->assertEquals($categoryid, $event->objectid);
$this->assertDebuggingNotCalled();
}
/**
* Test the question category viewed event.
* There is no external API for viewing the category, so the unit test will simply
* create and trigger the event and ensure data is returned as expected.
*/
public function test_question_category_viewed() {
$this->setAdminUser();
$course = $this->getDataGenerator()->create_course();
$quiz = $this->getDataGenerator()->create_module('quiz', array('course' => $course->id));
$contexts = new question_edit_contexts(context_module::instance($quiz->cmid));
$defaultcategoryobj = question_make_default_categories(array($contexts->lowest()));
$defaultcategory = $defaultcategoryobj->id . ',' . $defaultcategoryobj->contextid;
$qcobject = new question_category_object(
1,
new moodle_url('/mod/quiz/edit.php', array('cmid' => $quiz->cmid)),
$contexts->having_one_edit_tab_cap('categories'),
$defaultcategoryobj->id,
$defaultcategory,
null,
$contexts->having_cap('moodle/question:add'));
// Create the category.
$categoryid = $qcobject->add_category($defaultcategory, 'newcategory', '', true);
// Log the view of this category.
$params = array(
'objectid' => $categoryid,
'context' => context_module::instance($quiz->cmid)
);
$event = \core\event\question_category_viewed::create($params);
// Trigger and capture the event.
$sink = $this->redirectEvents();
$event->trigger();
$events = $sink->get_events();
$event = reset($events);
// Check that the event data is valid.
$this->assertInstanceOf('\core\event\question_category_viewed', $event);
$this->assertEquals(context_module::instance($quiz->cmid), $event->get_context());
$this->assertEquals($categoryid, $event->objectid);
$this->assertDebuggingNotCalled();
}
/**
* Test the questions imported event.
* There is no easy way to trigger this event using the API, so the unit test will simply
* create and trigger the event and ensure data is returned as expected.
*/
public function test_questions_imported() {
$this->setAdminUser();
$course = $this->getDataGenerator()->create_course();
$quiz = $this->getDataGenerator()->create_module('quiz', array('course' => $course->id));
$contexts = new question_edit_contexts(context_module::instance($quiz->cmid));
$defaultcategoryobj = question_make_default_categories(array($contexts->lowest()));
$defaultcategory = $defaultcategoryobj->id . ',' . $defaultcategoryobj->contextid;
$qcobject = new question_category_object(
1,
new moodle_url('/mod/quiz/edit.php', array('cmid' => $quiz->cmid)),
$contexts->having_one_edit_tab_cap('categories'),
$defaultcategoryobj->id,
$defaultcategory,
null,
$contexts->having_cap('moodle/question:add'));
// Create the category.
$categoryid = $qcobject->add_category($defaultcategory, 'newcategory', '', true);
// Log the view of this category.
$params = array(
'context' => context_module::instance($quiz->cmid),
'other' => array('categoryid' => $categoryid, 'format' => 'testformat')
);
$event = \core\event\questions_imported::create($params);
// Trigger and capture the event.
$sink = $this->redirectEvents();
$event->trigger();
$events = $sink->get_events();
$event = reset($events);
// Check that the event data is valid.
$this->assertInstanceOf('\core\event\questions_imported', $event);
$this->assertEquals(context_module::instance($quiz->cmid), $event->get_context());
$this->assertEquals($categoryid, $event->other['categoryid']);
$this->assertEquals('testformat', $event->other['format']);
$this->assertDebuggingNotCalled();
}
/**
* Test the questions exported event.
* There is no easy way to trigger this event using the API, so the unit test will simply
* create and trigger the event and ensure data is returned as expected.
*/
public function test_questions_exported() {
$this->setAdminUser();
$course = $this->getDataGenerator()->create_course();
$quiz = $this->getDataGenerator()->create_module('quiz', array('course' => $course->id));
$contexts = new question_edit_contexts(context_module::instance($quiz->cmid));
$defaultcategoryobj = question_make_default_categories(array($contexts->lowest()));
$defaultcategory = $defaultcategoryobj->id . ',' . $defaultcategoryobj->contextid;
$qcobject = new question_category_object(
1,
new moodle_url('/mod/quiz/edit.php', array('cmid' => $quiz->cmid)),
$contexts->having_one_edit_tab_cap('categories'),
$defaultcategoryobj->id,
$defaultcategory,
null,
$contexts->having_cap('moodle/question:add'));
// Create the category.
$categoryid = $qcobject->add_category($defaultcategory, 'newcategory', '', true);
// Log the view of this category.
$params = array(
'context' => context_module::instance($quiz->cmid),
'other' => array('categoryid' => $categoryid, 'format' => 'testformat')
);
$event = \core\event\questions_exported::create($params);
// Trigger and capture the event.
$sink = $this->redirectEvents();
$event->trigger();
$events = $sink->get_events();
$event = reset($events);
// Check that the event data is valid.
$this->assertInstanceOf('\core\event\questions_exported', $event);
$this->assertEquals(context_module::instance($quiz->cmid), $event->get_context());
$this->assertEquals($categoryid, $event->other['categoryid']);
$this->assertEquals('testformat', $event->other['format']);
$this->assertDebuggingNotCalled();
}
/**
* Test the question created event.
*/
public function test_question_created() {
$this->setAdminUser();
$generator = $this->getDataGenerator()->get_plugin_generator('core_question');
$cat = $generator->create_question_category(array(
'name' => 'My category', 'sortorder' => 1));
// Trigger and capture the event.
$sink = $this->redirectEvents();
$questiondata = $generator->create_question('description', null, array('category' => $cat->id));
$question = question_bank::load_question($questiondata->id);
$events = $sink->get_events();
$event = reset($events);
// Check that the event data is valid.
$this->assertInstanceOf('\core\event\question_created', $event);
$this->assertEquals($question->id, $event->objectid);
$this->assertEquals($cat->id, $event->other['categoryid']);
$this->assertDebuggingNotCalled();
}
/**
* Test the question deleted event.
*/
public function test_question_deleted() {
$this->setAdminUser();
$generator = $this->getDataGenerator()->get_plugin_generator('core_question');
$cat = $generator->create_question_category(array(
'name' => 'My category', 'sortorder' => 1));
$questiondata = $generator->create_question('description', null, array('category' => $cat->id));
$question = question_bank::load_question($questiondata->id);
// Trigger and capture the event.
$sink = $this->redirectEvents();
question_delete_question($question->id);
$events = $sink->get_events();
$event = reset($events);
// Check that the event data is valid.
$this->assertInstanceOf('\core\event\question_deleted', $event);
$this->assertEquals($question->id, $event->objectid);
$this->assertEquals($cat->id, $event->other['categoryid']);
$this->assertDebuggingNotCalled();
}
/**
* Test the question updated event.
*/
public function test_question_updated() {
global $CFG;
require_once($CFG->dirroot . '/question/type/description/questiontype.php');
require_once($CFG->dirroot . '/question/type/edit_question_form.php');
require_once($CFG->dirroot . '/question/type/description/edit_description_form.php');
$this->setAdminUser();
$generator = $this->getDataGenerator()->get_plugin_generator('core_question');
$cat = $generator->create_question_category(array(
'name' => 'My category', 'sortorder' => 1));
$questiondata = $generator->create_question('description', null, array('category' => $cat->id));
$question = question_bank::load_question($questiondata->id);
$qtype = new qtype_description();
$formdata = test_question_maker::get_question_form_data('description');
$formdata->category = "{$cat->id},{$cat->contextid}";
qtype_description_edit_form::mock_submit((array)$formdata);
$form = qtype_description_test_helper::get_question_editing_form($cat, $questiondata);
$fromform = $form->get_data();
// Trigger and capture the event.
$sink = $this->redirectEvents();
$qtype->save_question($questiondata, $fromform);
$events = $sink->get_events();
$event = reset($events);
// Check that the event data is valid.
$this->assertInstanceOf('\core\event\question_updated', $event);
$this->assertEquals($question->id, $event->objectid);
$this->assertEquals($cat->id, $event->other['categoryid']);
$this->assertDebuggingNotCalled();
}
/**
* Test the question moved event.
*/
public function test_question_moved() {
$this->setAdminUser();
$generator = $this->getDataGenerator()->get_plugin_generator('core_question');
$cat1 = $generator->create_question_category(array(
'name' => 'My category 1', 'sortorder' => 1));
$cat2 = $generator->create_question_category(array(
'name' => 'My category 2', 'sortorder' => 2));
$questiondata = $generator->create_question('description', null, array('category' => $cat1->id));
$question = question_bank::load_question($questiondata->id);
// Trigger and capture the event.
$sink = $this->redirectEvents();
question_move_questions_to_category(array($question->id), $cat2->id);
$events = $sink->get_events();
$event = reset($events);
// Check that the event data is valid.
$this->assertInstanceOf('\core\event\question_moved', $event);
$this->assertEquals($question->id, $event->objectid);
$this->assertEquals($cat1->id, $event->other['oldcategoryid']);
$this->assertEquals($cat2->id, $event->other['newcategoryid']);
$this->assertDebuggingNotCalled();
}
/**
* Test the question viewed event.
* There is no external API for viewing the question, so the unit test will simply
* create and trigger the event and ensure data is returned as expected.
*/
public function test_question_viewed() {
$this->setAdminUser();
$generator = $this->getDataGenerator()->get_plugin_generator('core_question');
$cat = $generator->create_question_category(array(
'name' => 'My category', 'sortorder' => 1));
$questiondata = $generator->create_question('description', null, array('category' => $cat->id));
$question = question_bank::load_question($questiondata->id);
$params = array(
'objectid' => $question->id,
'context' => context::instance_by_id($cat->contextid),
'other' => array('categoryid' => $question->category)
);
$event = \core\event\question_previewed::create($params);
// Trigger and capture the event.
$sink = $this->redirectEvents();
$event->trigger();
$events = $sink->get_events();
$event = reset($events);
// Check that the event data is valid.
$this->assertInstanceOf('\core\event\question_previewed', $event);
$this->assertEquals($question->id, $event->objectid);
$this->assertEquals($cat->id, $event->other['categoryid']);
$this->assertDebuggingNotCalled();
}
}

View File

@ -364,12 +364,14 @@ class question_type {
}
// If the question is new, create it.
$newquestion = false;
if (empty($question->id)) {
// Set the unique code.
$question->stamp = make_unique_id_code();
$question->createdby = $USER->id;
$question->timecreated = time();
$question->id = $DB->insert_record('question', $question);
$newquestion = true;
}
// Now, whether we are updating a existing question, or creating a new
@ -391,6 +393,26 @@ class question_type {
}
$DB->update_record('question', $question);
if ($newquestion) {
// Log the creation of this question.
$eventparams = array(
'context' => $context,
'objectid' => $question->id,
'other' => array('categoryid' => $question->category)
);
$event = \core\event\question_created::create($eventparams);
$event->trigger();
} else {
// Log the update of this question.
$eventparams = array(
'context' => $context,
'objectid' => $question->id,
'other' => array('categoryid' => $question->category)
);
$event = \core\event\question_updated::create($eventparams);
$event->trigger();
}
// Now to save all the answers and type-specific options.
$form->id = $question->id;
$form->qtype = $question->qtype;

View File

@ -29,7 +29,7 @@
defined('MOODLE_INTERNAL') || die();
$version = 2019042700.00; // YYYYMMDD = weekly release date of this DEV branch.
$version = 2019042700.01; // YYYYMMDD = weekly release date of this DEV branch.
// RR = release increments - 00 in DEV branches.
// .XX = incremental changes.