mirror of
https://github.com/moodle/moodle.git
synced 2025-04-21 00:12:56 +02:00
MDL-26854 COMMENT
1. added pluginname_comment_validate callback to comments api 2. change permission callback defaults to false 3. Tidied up serveal areas of comments and implemented callback to ignore system permissions for view (credits to Sam Hemelryk) AMOS BEGIN MOV [modulerejectcomment,error],[callbackrejectcomment,error] AMOS END
This commit is contained in:
parent
b8df9414bd
commit
c1951ea953
@ -1,5 +1,31 @@
|
||||
<?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/>.
|
||||
|
||||
/**
|
||||
* The comments block
|
||||
*
|
||||
* @package block
|
||||
* @subpackage comments
|
||||
* @copyright 2009 Dongsheng Cai <dongsheng@moodle.com>
|
||||
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
|
||||
*/
|
||||
|
||||
defined('MOODLE_INTERNAL') || die();
|
||||
|
||||
// Obviously required
|
||||
require_once($CFG->dirroot . '/comment/lib.php');
|
||||
|
||||
class block_comments extends block_base {
|
||||
@ -38,13 +64,12 @@ class block_comments extends block_base {
|
||||
$this->content->footer = '';
|
||||
$this->content->text = '';
|
||||
list($context, $course, $cm) = get_context_info_array($PAGE->context->id);
|
||||
$args = new stdClass();
|
||||
|
||||
$args = new stdClass;
|
||||
$args->context = $PAGE->context;
|
||||
$args->course = $course;
|
||||
$args->area = 'page_comments';
|
||||
$args->itemid = 0;
|
||||
// set 'env' to tell moodle tweak ui for this block
|
||||
$args->env = 'block_comments';
|
||||
$args->component = 'block_comments';
|
||||
$args->linktext = get_string('showcomments');
|
||||
$args->notoggle = true;
|
||||
|
62
blog/lib.php
62
blog/lib.php
@ -966,3 +966,65 @@ function blog_get_associated_count($courseid, $cmid=null) {
|
||||
}
|
||||
return $DB->count_records('blog_association', array('contextid' => $context->id));
|
||||
}
|
||||
|
||||
/**
|
||||
* Running addtional permission check on plugin, for example, plugins
|
||||
* may have switch to turn on/off comments option, this callback will
|
||||
* affect UI display, not like pluginname_comment_validate only throw
|
||||
* exceptions.
|
||||
* Capability check has been done in comment->check_permissions(), we
|
||||
* don't need to do it again here.
|
||||
*
|
||||
* @param stdClass $comment_param {
|
||||
* context => context the context object
|
||||
* courseid => int course id
|
||||
* cm => stdClass course module object
|
||||
* commentarea => string comment area
|
||||
* itemid => int itemid
|
||||
* }
|
||||
* @return array
|
||||
*/
|
||||
function blog_comment_permissions($comment_param) {
|
||||
return array('post'=>true, 'view'=>true);
|
||||
}
|
||||
|
||||
/**
|
||||
* Validate comment parameter before perform other comments actions
|
||||
*
|
||||
* @param stdClass $comment {
|
||||
* context => context the context object
|
||||
* courseid => int course id
|
||||
* cm => stdClass course module object
|
||||
* commentarea => string comment area
|
||||
* itemid => int itemid
|
||||
* }
|
||||
* @return boolean
|
||||
*/
|
||||
function blog_comment_validate($comment_param) {
|
||||
global $DB;
|
||||
// validate comment itemid
|
||||
if (!$entry = $DB->get_record('post', array('id'=>$comment_param->itemid))) {
|
||||
throw new comment_exception('invalidcommentitemid');
|
||||
}
|
||||
// validate comment area
|
||||
if ($comment_param->commentarea != 'format_blog') {
|
||||
throw new comment_exception('invalidcommentarea');
|
||||
}
|
||||
// validation for comment deletion
|
||||
if (!empty($comment_param->commentid)) {
|
||||
if ($record = $DB->get_record('comments', array('id'=>$comment_param->commentid))) {
|
||||
if ($record->commentarea != 'format_blog') {
|
||||
throw new comment_exception('invalidcommentarea');
|
||||
}
|
||||
if ($record->contextid != $comment_param->context->id) {
|
||||
throw new comment_exception('invalidcontext');
|
||||
}
|
||||
if ($record->itemid != $comment_param->itemid) {
|
||||
throw new comment_exception('invalidcommentitemid');
|
||||
}
|
||||
} else {
|
||||
throw new comment_exception('invalidcommentid');
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
@ -40,7 +40,6 @@ M.core_comment = {
|
||||
this.component = args.component;
|
||||
this.courseid = args.courseid;
|
||||
this.contextid = args.contextid;
|
||||
this.env = args.env;
|
||||
this.autostart = (args.autostart);
|
||||
// expand comments?
|
||||
if (this.autostart) {
|
||||
@ -116,7 +115,6 @@ bodyContent: '<div class="comment-delete-confirm"><a href="#" id="confirmdelete-
|
||||
scope = args['scope'];
|
||||
}
|
||||
//params['page'] = args.page?args.page:'';
|
||||
params['env'] = '';
|
||||
// the form element only accept certain file types
|
||||
params['sesskey'] = M.cfg.sesskey;
|
||||
params['action'] = args.action?args.action:'';
|
||||
@ -348,7 +346,7 @@ bodyContent: '<div class="comment-delete-confirm"><a href="#" id="confirmdelete-
|
||||
var d = container.getStyle('display');
|
||||
if (d=='none'||d=='') {
|
||||
// show
|
||||
if (this.autostart) {
|
||||
if (!this.autostart) {
|
||||
this.load(page);
|
||||
} else {
|
||||
this.register_delete_buttons();
|
||||
|
@ -1,5 +1,4 @@
|
||||
<?php
|
||||
|
||||
// This file is part of Moodle - http://moodle.org/
|
||||
//
|
||||
// Moodle is free software: you can redistribute it and/or modify
|
||||
@ -24,87 +23,96 @@ require_once('../config.php');
|
||||
require_once($CFG->dirroot . '/comment/lib.php');
|
||||
|
||||
$contextid = optional_param('contextid', SYSCONTEXTID, PARAM_INT);
|
||||
$action = optional_param('action', '', PARAM_ALPHA);
|
||||
|
||||
if (empty($CFG->usecomments)) {
|
||||
throw new comment_exception('commentsnotenabled', 'moodle');
|
||||
}
|
||||
|
||||
list($context, $course, $cm) = get_context_info_array($contextid);
|
||||
|
||||
$PAGE->set_context($context);
|
||||
$PAGE->set_url('/comment/comment_ajax.php');
|
||||
|
||||
$action = optional_param('action', '', PARAM_ALPHA);
|
||||
// Allow anonymous user to view comments providing forcelogin now enabled
|
||||
require_course_login($course, true, $cm);
|
||||
$PAGE->set_context($context);
|
||||
if (!empty($cm)) {
|
||||
$PAGE->set_cm($cm, $course);
|
||||
} else if (!empty($course)) {
|
||||
$PAGE->set_course($course);
|
||||
}
|
||||
|
||||
if (!confirm_sesskey()) {
|
||||
$error = array('error'=>get_string('invalidsesskey'));
|
||||
$error = array('error'=>get_string('invalidsesskey', 'error'));
|
||||
die(json_encode($error));
|
||||
}
|
||||
|
||||
if (!isloggedin()) {
|
||||
// display comments on front page without permission check
|
||||
if ($action == 'get') {
|
||||
if ($context->id == get_context_instance(CONTEXT_COURSE, SITEID)->id) {
|
||||
$ignore_permission = true;
|
||||
} else {
|
||||
// tell user to log in to view comments
|
||||
$ignore_permission = false;
|
||||
echo json_encode(array('error'=>'require_login'));
|
||||
die;
|
||||
}
|
||||
} else {
|
||||
// ignore request
|
||||
die;
|
||||
}
|
||||
} else {
|
||||
$ignore_permission = false;
|
||||
}
|
||||
|
||||
$client_id = required_param('client_id', PARAM_ALPHANUM);
|
||||
$area = optional_param('area', '', PARAM_ALPHAEXT);
|
||||
$client_id = optional_param('client_id', '', PARAM_RAW);
|
||||
$commentid = optional_param('commentid', -1, PARAM_INT);
|
||||
$content = optional_param('content', '', PARAM_RAW);
|
||||
$itemid = optional_param('itemid', '', PARAM_INT);
|
||||
$page = optional_param('page', 0, PARAM_INT);
|
||||
$component = optional_param('component', '', PARAM_ALPHAEXT);
|
||||
|
||||
echo $OUTPUT->header(); // send headers
|
||||
|
||||
// initilising comment object
|
||||
if (!empty($client_id)) {
|
||||
$args = new stdClass();
|
||||
$args->context = $context;
|
||||
$args->course = $course;
|
||||
$args->cm = $cm;
|
||||
$args->area = $area;
|
||||
$args->itemid = $itemid;
|
||||
$args->client_id = $client_id;
|
||||
$args->component = $component;
|
||||
// only for comments in frontpage
|
||||
$args->ignore_permission = $ignore_permission;
|
||||
$manager = new comment($args);
|
||||
} else {
|
||||
die;
|
||||
}
|
||||
$args = new stdClass;
|
||||
$args->context = $context;
|
||||
$args->course = $course;
|
||||
$args->cm = $cm;
|
||||
$args->area = $area;
|
||||
$args->itemid = $itemid;
|
||||
$args->client_id = $client_id;
|
||||
$args->component = $component;
|
||||
$manager = new comment($args);
|
||||
|
||||
echo $OUTPUT->header(); // send headers
|
||||
|
||||
// process ajax request
|
||||
switch ($action) {
|
||||
case 'add':
|
||||
$result = $manager->add($content);
|
||||
if (!empty($result) && is_object($result)) {
|
||||
$result->count = $manager->count();
|
||||
$result->client_id = $client_id;
|
||||
echo json_encode($result);
|
||||
if ($manager->can_post()) {
|
||||
$result = $manager->add($content);
|
||||
if (!empty($result) && is_object($result)) {
|
||||
$result->count = $manager->count();
|
||||
$result->client_id = $client_id;
|
||||
echo json_encode($result);
|
||||
die();
|
||||
}
|
||||
}
|
||||
break;
|
||||
case 'delete':
|
||||
$result = $manager->delete($commentid);
|
||||
if ($result === true) {
|
||||
echo json_encode(array('client_id'=>$client_id, 'commentid'=>$commentid));
|
||||
$comment_record = $DB->get_record('comments', array('id'=>$commentid));
|
||||
if ($manager->can_delete($commentid) || $comment_record->userid == $USER->id) {
|
||||
if ($manager->delete($commentid)) {
|
||||
$result = array(
|
||||
'client_id' => $client_id,
|
||||
'commentid' => $commentid
|
||||
);
|
||||
echo json_encode($result);
|
||||
die();
|
||||
}
|
||||
}
|
||||
break;
|
||||
case 'get':
|
||||
default:
|
||||
$result = array();
|
||||
$comments = $manager->get_comments($page);
|
||||
$result['list'] = $comments;
|
||||
$result['count'] = $manager->count();
|
||||
$result['pagination'] = $manager->get_pagination($page);
|
||||
$result['client_id'] = $client_id;
|
||||
echo json_encode($result);
|
||||
if ($manager->can_view()) {
|
||||
$comments = $manager->get_comments($page);
|
||||
$result = array(
|
||||
'list' => $comments,
|
||||
'count' => $manager->count(),
|
||||
'pagination' => $manager->get_pagination($page),
|
||||
'client_id' => $client_id
|
||||
);
|
||||
echo json_encode($result);
|
||||
die();
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
if (!isloggedin()) {
|
||||
// tell user to log in to view comments
|
||||
echo json_encode(array('error'=>'require_login'));
|
||||
}
|
||||
// ignore request
|
||||
die;
|
||||
|
@ -1,5 +1,4 @@
|
||||
<?php
|
||||
|
||||
// This file is part of Moodle - http://moodle.org/
|
||||
//
|
||||
// Moodle is free software: you can redistribute it and/or modify
|
||||
@ -21,35 +20,40 @@
|
||||
require_once('../config.php');
|
||||
require_once($CFG->dirroot . '/comment/lib.php');
|
||||
|
||||
if (empty($CFG->usecomments)) {
|
||||
throw new comment_exception('commentsnotenabled', 'moodle');
|
||||
}
|
||||
|
||||
$contextid = optional_param('contextid', SYSCONTEXTID, PARAM_INT);
|
||||
list($context, $course, $cm) = get_context_info_array($contextid);
|
||||
|
||||
require_login($course, true, $cm);
|
||||
require_sesskey();
|
||||
|
||||
$action = optional_param('action', '', PARAM_ALPHA);
|
||||
$area = optional_param('area', '', PARAM_ALPHAEXT);
|
||||
$commentid = optional_param('commentid', -1, PARAM_INT);
|
||||
$content = optional_param('content', '', PARAM_RAW);
|
||||
$itemid = optional_param('itemid', '', PARAM_INT);
|
||||
$returnurl = optional_param('returnurl', '', PARAM_URL);
|
||||
$component = optional_param('component', '', PARAM_ALPHAEXT);
|
||||
$action = optional_param('action', '', PARAM_ALPHA);
|
||||
$area = optional_param('area', '', PARAM_ALPHAEXT);
|
||||
$content = optional_param('content', '', PARAM_RAW);
|
||||
$itemid = optional_param('itemid', '', PARAM_INT);
|
||||
$returnurl = optional_param('returnurl', '/', PARAM_URL);
|
||||
$component = optional_param('component', '', PARAM_ALPHAEXT);
|
||||
|
||||
$cmt = new stdClass();
|
||||
// Currently this script can only add comments
|
||||
if ($action !== 'add') {
|
||||
redirect($returnurl);
|
||||
}
|
||||
|
||||
$cmt = new stdClass;
|
||||
$cmt->contextid = $contextid;
|
||||
$cmt->courseid = $course->id;
|
||||
$cmt->cm = $cm;
|
||||
$cmt->area = $area;
|
||||
$cmt->itemid = $itemid;
|
||||
$cmt->component = $component;
|
||||
$comment = new comment($cmt);
|
||||
|
||||
switch ($action) {
|
||||
case 'add':
|
||||
if ($comment->can_post()) {
|
||||
$cmt = $comment->add($content);
|
||||
if (!empty($cmt) && is_object($cmt)) {
|
||||
redirect($returnurl);
|
||||
}
|
||||
break;
|
||||
default:
|
||||
exit;
|
||||
}
|
||||
|
@ -20,7 +20,7 @@
|
||||
*/
|
||||
require_once('../config.php');
|
||||
require_once($CFG->libdir.'/adminlib.php');
|
||||
require_once('locallib.php');
|
||||
require_once($CFG->dirroot.'/comment/locallib.php');
|
||||
|
||||
require_login();
|
||||
admin_externalpage_setup('comments', '', null, '', array('pagelayout'=>'report'));
|
||||
@ -81,8 +81,11 @@ if (!empty($err)) {
|
||||
}
|
||||
if (empty($action)) {
|
||||
echo '<form method="post">';
|
||||
$manager->print_comments($page);
|
||||
echo '<input type="submit" id="comments_delete" name="batchdelete" value="'.get_string('delete').'" />';
|
||||
$return = $manager->print_comments($page);
|
||||
// if no comments available, $return will be false
|
||||
if ($return) {
|
||||
echo '<input type="submit" id="comments_delete" name="batchdelete" value="'.get_string('delete').'" />';
|
||||
}
|
||||
echo '</form>';
|
||||
}
|
||||
|
||||
|
499
comment/lib.php
499
comment/lib.php
@ -1,5 +1,4 @@
|
||||
<?php
|
||||
|
||||
// This file is part of Moodle - http://moodle.org/
|
||||
//
|
||||
// Moodle is free software: you can redistribute it and/or modify
|
||||
@ -23,18 +22,15 @@
|
||||
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
|
||||
*/
|
||||
|
||||
defined('MOODLE_INTERNAL') || die();
|
||||
|
||||
class comment {
|
||||
/**
|
||||
* @var integer
|
||||
*/
|
||||
private $page;
|
||||
/**
|
||||
* there may be several comment box in one page
|
||||
* so we need a client_id to recognize them
|
||||
* @var integer
|
||||
*/
|
||||
private $cid;
|
||||
private $contextid;
|
||||
/**
|
||||
* commentarea is used to specify different
|
||||
* parts shared the same itemid
|
||||
@ -46,80 +42,133 @@ class comment {
|
||||
* @var integer
|
||||
*/
|
||||
private $itemid;
|
||||
|
||||
/**
|
||||
* this html snippet will be used as a template
|
||||
* to build comment content
|
||||
* @var string
|
||||
*/
|
||||
private $template;
|
||||
/**
|
||||
* The context id for comments
|
||||
* @var int
|
||||
*/
|
||||
private $contextid;
|
||||
/**
|
||||
* The context itself
|
||||
* @var stdClass
|
||||
*/
|
||||
private $context;
|
||||
/**
|
||||
* The course id for comments
|
||||
* @var int
|
||||
*/
|
||||
private $courseid;
|
||||
/**
|
||||
* course module object, only be used to help find pluginname automatically
|
||||
* if pluginname is specified, it won't be used at all
|
||||
* @var string
|
||||
* @var stdClass
|
||||
*/
|
||||
private $cm;
|
||||
private $plugintype;
|
||||
/**
|
||||
* When used in module, it is recommended to use it
|
||||
* The component that this comment is for. It is STRONGLY recommended to set this.
|
||||
* @var string
|
||||
*/
|
||||
private $component;
|
||||
/**
|
||||
* This is calculated by normalising the component
|
||||
* @var string
|
||||
*/
|
||||
private $pluginname;
|
||||
private $viewcap;
|
||||
private $postcap;
|
||||
/**
|
||||
* to tell comments api where it is used
|
||||
* This is calculated by normalising the component
|
||||
* @var string
|
||||
*/
|
||||
private $env;
|
||||
private $plugintype;
|
||||
/**
|
||||
* Whether the user has the required capabilities/permissions to view comments.
|
||||
* @var bool
|
||||
*/
|
||||
private $viewcap = false;
|
||||
/**
|
||||
* Whether the user has the required capabilities/permissions to post comments.
|
||||
* @var bool
|
||||
*/
|
||||
private $postcap = false;
|
||||
/**
|
||||
* to costomize link text
|
||||
* @var string
|
||||
*/
|
||||
private $linktext;
|
||||
|
||||
/**
|
||||
* If set to true then comment sections won't be able to be opened and closed
|
||||
* instead they will always be visible.
|
||||
* @var bool
|
||||
*/
|
||||
protected $notoggle = false;
|
||||
|
||||
/**
|
||||
* If set to true comments are automatically loaded as soon as the page loads.
|
||||
* Normally this happens when the user expands the comment section.
|
||||
* @var bool
|
||||
*/
|
||||
protected $autostart = false;
|
||||
|
||||
/**
|
||||
* If set to true the total count of comments is displayed when displaying comments.
|
||||
* @var bool
|
||||
*/
|
||||
protected $displaytotalcount = false;
|
||||
/**
|
||||
* If set to true a cancel button will be shown on the form used to submit comments.
|
||||
* @var bool
|
||||
*/
|
||||
protected $displaycancel = false;
|
||||
/**
|
||||
* The number of comments associated with this comments params
|
||||
* @var int
|
||||
*/
|
||||
protected $totalcommentcount = null;
|
||||
/**
|
||||
* By default a user must have the generic comment capabilities plus any capabilities the
|
||||
* component being commented on requires.
|
||||
* When set to true only the component capabilities are checked, the system capabilities are
|
||||
* ignored.
|
||||
* This can be toggled by the component defining a callback in its lib.php e.g.
|
||||
* function forum_comment_allow_anonymous_access(comment $comment) {}
|
||||
* Note: On the front page this defaults to true.
|
||||
* @var bool
|
||||
*/
|
||||
protected $ignoresystempermissions = false;
|
||||
|
||||
// static variable will be used by non-js comments UI
|
||||
/**#@+
|
||||
* static variable will be used by non-js comments UI
|
||||
*/
|
||||
private static $nonjs = false;
|
||||
private static $comment_itemid = null;
|
||||
private static $comment_context = null;
|
||||
private static $comment_area = null;
|
||||
private static $comment_page = null;
|
||||
private static $comment_component = null;
|
||||
/**#@-*/
|
||||
|
||||
/**
|
||||
* Construct function of comment class, initialise
|
||||
* class members
|
||||
* @param object $options
|
||||
* @param stdClass $options
|
||||
* @param object $options {
|
||||
* context => context context to use for the comment [required]
|
||||
* component => string which plugin will comment being added to [required]
|
||||
* itemid => int the id of the associated item (forum post, glossary item etc) [required]
|
||||
* area => string comment area
|
||||
* cm => stdClass course module
|
||||
* course => course course object
|
||||
* client_id => string an unique id to identify comment area
|
||||
* autostart => boolean automatically expend comments
|
||||
* showcount => boolean display the number of comments
|
||||
* displaycancel => boolean display cancel button
|
||||
* notoggle => boolean don't show/hide button
|
||||
* linktext => string title of show/hide button
|
||||
* }
|
||||
*/
|
||||
public function __construct($options) {
|
||||
global $CFG, $DB;
|
||||
|
||||
if (empty($CFG->commentsperpage)) {
|
||||
$CFG->commentsperpage = 15;
|
||||
}
|
||||
|
||||
public function __construct(stdClass $options) {
|
||||
$this->viewcap = false;
|
||||
$this->postcap = false;
|
||||
|
||||
@ -142,7 +191,11 @@ class comment {
|
||||
}
|
||||
|
||||
if (!empty($options->component)) {
|
||||
// set and validate component
|
||||
$this->set_component($options->component);
|
||||
} else {
|
||||
// component cannot be empty
|
||||
throw new comment_exception('invalidcomponent');
|
||||
}
|
||||
|
||||
// setup course
|
||||
@ -174,13 +227,6 @@ class comment {
|
||||
$this->itemid = 0;
|
||||
}
|
||||
|
||||
// setup env
|
||||
if (!empty($options->env)) {
|
||||
$this->env = $options->env;
|
||||
} else {
|
||||
$this->env = '';
|
||||
}
|
||||
|
||||
// setup customized linktext
|
||||
if (!empty($options->linktext)) {
|
||||
$this->linktext = $options->linktext;
|
||||
@ -188,10 +234,24 @@ class comment {
|
||||
$this->linktext = get_string('comments');
|
||||
}
|
||||
|
||||
if (!empty($options->ignore_permission)) {
|
||||
$this->ignore_permission = true;
|
||||
} else {
|
||||
$this->ignore_permission = false;
|
||||
// setup options for callback functions
|
||||
$this->comment_param = new stdClass();
|
||||
$this->comment_param->context = $this->context;
|
||||
$this->comment_param->courseid = $this->courseid;
|
||||
$this->comment_param->cm = $this->cm;
|
||||
$this->comment_param->commentarea = $this->commentarea;
|
||||
$this->comment_param->itemid = $this->itemid;
|
||||
|
||||
$this->allowanonymousaccess = false;
|
||||
// By default everyone can view comments on the front page
|
||||
if ($this->context->contextlevel == CONTEXT_COURSE && $this->context->instanceid == SITEID) {
|
||||
$this->allowanonymousaccess = true;
|
||||
} else if ($this->context->contextlevel == CONTEXT_MODULE && $this->courseid == SITEID) {
|
||||
$this->allowanonymousaccess = true;
|
||||
}
|
||||
if (!empty($this->plugintype) && !empty($this->pluginname)) {
|
||||
// Plugins can override this if they wish.
|
||||
$this->allowanonymousaccess = plugin_callback($this->plugintype, $this->pluginname, 'comment', 'allow_anonymous_access', array($this), $this->allowanonymousaccess);
|
||||
}
|
||||
|
||||
// setup notoggle
|
||||
@ -209,38 +269,23 @@ class comment {
|
||||
$this->set_displaycancel($options->displaycancel);
|
||||
}
|
||||
|
||||
// setup displaytotalcount
|
||||
if (!empty($options->showcount)) {
|
||||
$count = $this->count();
|
||||
if (empty($count)) {
|
||||
$this->count = '';
|
||||
} else {
|
||||
$this->count = '('.$count.')';
|
||||
}
|
||||
} else {
|
||||
$this->count = '';
|
||||
$this->set_displaytotalcount($options->showcount);
|
||||
}
|
||||
|
||||
// setup options for callback functions
|
||||
$this->args = new stdClass();
|
||||
$this->args->context = $this->context;
|
||||
$this->args->courseid = $this->courseid;
|
||||
$this->args->cm = $this->cm;
|
||||
$this->args->commentarea = $this->commentarea;
|
||||
$this->args->itemid = $this->itemid;
|
||||
|
||||
// setting post and view permissions
|
||||
$this->check_permissions();
|
||||
|
||||
// load template
|
||||
$this->template = <<<EOD
|
||||
<div class="comment-userpicture">___picture___</div>
|
||||
<div class="comment-content">
|
||||
___name___ - <span>___time___</span>
|
||||
<div>___content___</div>
|
||||
</div>
|
||||
EOD;
|
||||
$this->template = html_writer::tag('div', '___picture___', array('class' => 'comment-userpicture'));
|
||||
$this->template .= html_writer::start_tag('div', array('class' => 'comment-content'));
|
||||
$this->template .= '___name___ - ';
|
||||
$this->template .= html_writer::tag('span', '___time___');
|
||||
$this->template .= html_writer::tag('div', '___content___');
|
||||
$this->template .= html_writer::end_tag('div'); // .comment-content
|
||||
if (!empty($this->plugintype)) {
|
||||
$this->template = plugin_callback($this->plugintype, $this->pluginname, FEATURE_COMMENT, 'template', $this->args, $this->template);
|
||||
$this->template = plugin_callback($this->plugintype, $this->pluginname, 'comment', 'template', array($this->comment_param), $this->template);
|
||||
}
|
||||
|
||||
unset($options);
|
||||
@ -248,34 +293,63 @@ EOD;
|
||||
|
||||
/**
|
||||
* Receive nonjs comment parameters
|
||||
*
|
||||
* @param moodle_page $page The page object to initialise comments within
|
||||
* If not provided the global $PAGE is used
|
||||
*/
|
||||
public static function init() {
|
||||
global $PAGE, $CFG;
|
||||
public static function init(moodle_page $page = null) {
|
||||
global $PAGE;
|
||||
|
||||
if (empty($page)) {
|
||||
$page = $PAGE;
|
||||
}
|
||||
// setup variables for non-js interface
|
||||
self::$nonjs = optional_param('nonjscomment', '', PARAM_ALPHA);
|
||||
self::$nonjs = optional_param('nonjscomment', '', PARAM_ALPHANUM);
|
||||
self::$comment_itemid = optional_param('comment_itemid', '', PARAM_INT);
|
||||
self::$comment_context = optional_param('comment_context', '', PARAM_INT);
|
||||
self::$comment_page = optional_param('comment_page', '', PARAM_INT);
|
||||
self::$comment_area = optional_param('comment_area', '', PARAM_ALPHAEXT);
|
||||
|
||||
$PAGE->requires->string_for_js('addcomment', 'moodle');
|
||||
$PAGE->requires->string_for_js('deletecomment', 'moodle');
|
||||
$PAGE->requires->string_for_js('comments', 'moodle');
|
||||
$PAGE->requires->string_for_js('commentsrequirelogin', 'moodle');
|
||||
$page->requires->string_for_js('addcomment', 'moodle');
|
||||
$page->requires->string_for_js('deletecomment', 'moodle');
|
||||
$page->requires->string_for_js('comments', 'moodle');
|
||||
$page->requires->string_for_js('commentsrequirelogin', 'moodle');
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets the component.
|
||||
*
|
||||
* This method shouldn't be public, changing the component once it has been set potentially
|
||||
* invalidates permission checks.
|
||||
* A coding_error is now thrown if code attempts to change the component.
|
||||
*
|
||||
* @param string $component
|
||||
* @return void
|
||||
*/
|
||||
public function set_component($component) {
|
||||
if (!empty($this->component) && $this->component !== $component) {
|
||||
throw new coding_exception('You cannot change the component of a comment once it has been set');
|
||||
}
|
||||
$this->component = $component;
|
||||
list($this->plugintype, $this->pluginname) = normalize_component($component);
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Determines if the user can view the comment.
|
||||
*
|
||||
* @param bool $value
|
||||
*/
|
||||
public function set_view_permission($value) {
|
||||
$this->viewcap = $value;
|
||||
$this->viewcap = (bool)$value;
|
||||
}
|
||||
|
||||
/**
|
||||
* Determines if the user can post a comment
|
||||
*
|
||||
* @param bool $value
|
||||
*/
|
||||
public function set_post_permission($value) {
|
||||
$this->postcap = $value;
|
||||
$this->postcap = (bool)$value;
|
||||
}
|
||||
|
||||
/**
|
||||
@ -285,12 +359,11 @@ EOD;
|
||||
* function named $pluginname_check_comment_post must be implemented
|
||||
*/
|
||||
private function check_permissions() {
|
||||
global $CFG;
|
||||
$this->postcap = has_capability('moodle/comment:post', $this->context);
|
||||
$this->viewcap = has_capability('moodle/comment:view', $this->context);
|
||||
if (!empty($this->plugintype)) {
|
||||
$permissions = plugin_callback($this->plugintype, $this->pluginname, FEATURE_COMMENT, 'permissions', array($this->args), array('post'=>true, 'view'=>true));
|
||||
if ($this->ignore_permission) {
|
||||
$permissions = plugin_callback($this->plugintype, $this->pluginname, 'comment', 'permissions', array($this->comment_param), array('post'=>false, 'view'=>false));
|
||||
if ($this->allowanonymousaccess) {
|
||||
$this->postcap = $permissions['post'];
|
||||
$this->viewcap = $permissions['view'];
|
||||
} else {
|
||||
@ -319,7 +392,7 @@ EOD;
|
||||
'comment_context' => $this->context->id,
|
||||
'comment_area' => $this->commentarea,
|
||||
));
|
||||
$link->remove_params(array('nonjscomment', 'comment_page'));
|
||||
$link->remove_params(array('comment_page'));
|
||||
return $link;
|
||||
}
|
||||
|
||||
@ -359,6 +432,18 @@ EOD;
|
||||
$this->displaycancel = (bool)$newvalue;
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets the displaytotalcount option
|
||||
*
|
||||
* If set to true then the total number of comments will be displayed
|
||||
* when printing comments.
|
||||
*
|
||||
* @param bool $newvalue
|
||||
*/
|
||||
public function set_displaytotalcount($newvalue = true) {
|
||||
$this->displaytotalcount = (bool)$newvalue;
|
||||
}
|
||||
|
||||
/**
|
||||
* Initialises the JavaScript that enchances the comment API.
|
||||
*
|
||||
@ -374,7 +459,6 @@ EOD;
|
||||
$options->page = 0;
|
||||
$options->courseid = $this->courseid;
|
||||
$options->contextid = $this->contextid;
|
||||
$options->env = $this->env;
|
||||
$options->component = $this->component;
|
||||
$options->notoggle = $this->notoggle;
|
||||
$options->autostart = $this->autostart;
|
||||
@ -404,12 +488,12 @@ EOD;
|
||||
|
||||
// print html template
|
||||
// Javascript will use the template to render new comments
|
||||
if (empty($template_printed) && !empty($this->viewcap)) {
|
||||
if (empty($template_printed) && $this->can_view()) {
|
||||
$html .= html_writer::tag('div', $this->template, array('style' => 'display:none', 'id' => 'cmt-tmpl'));
|
||||
$template_printed = true;
|
||||
}
|
||||
|
||||
if (!empty($this->viewcap)) {
|
||||
if ($this->can_view()) {
|
||||
// print commenting icon and tooltip
|
||||
$html .= html_writer::start_tag('div', array('class' => 'mdl-left'));
|
||||
$html .= html_writer::link($this->get_nojslink($PAGE), get_string('showcommentsnonjs'), array('class' => 'showcommentsnonjs'));
|
||||
@ -417,27 +501,33 @@ EOD;
|
||||
if (!$this->notoggle) {
|
||||
// If toggling is enabled (notoggle=false) then print the controls to toggle
|
||||
// comments open and closed
|
||||
$countstring = '';
|
||||
if ($this->displaytotalcount) {
|
||||
$countstring = '('.$this->count().')';
|
||||
}
|
||||
$html .= html_writer::start_tag('a', array('class' => 'comment-link', 'id' => 'comment-link-'.$this->cid, 'href' => '#'));
|
||||
$html .= html_writer::empty_tag('img', array('id' => 'comment-img-'.$this->cid, 'src' => $OUTPUT->pix_url('t/collapsed'), 'alt' => $this->linktext, 'title' => $this->linktext));
|
||||
$html .= html_writer::tag('span', $this->linktext.' '.$this->count, array('id' => 'comment-link-text-'.$this->cid));
|
||||
$html .= html_writer::tag('span', $this->linktext.' '.$countstring, array('id' => 'comment-link-text-'.$this->cid));
|
||||
$html .= html_writer::end_tag('a');
|
||||
}
|
||||
|
||||
$html .= html_writer::start_tag('div', array('id' => 'comment-ctrl-'.$this->cid, 'class' => 'comment-ctrl'));
|
||||
$html .= html_writer::start_tag('ul', array('id' => 'comment-list-'.$this->cid, 'class' => 'comment-list'));
|
||||
$html .= html_writer::tag('li', '', array('class' => 'first'));
|
||||
|
||||
if ($this->autostart) {
|
||||
// If autostart has been enabled print the comments list immediatly
|
||||
$html .= html_writer::start_tag('ul', array('id' => 'comment-list-'.$this->cid, 'class' => 'comment-list comments-loaded'));
|
||||
$html .= html_writer::tag('li', '', array('class' => 'first'));
|
||||
$html .= $this->print_comments(0, true, false);
|
||||
$html .= html_writer::end_tag('ul'); // .comment-list
|
||||
$html .= $this->get_pagination(0);
|
||||
} else {
|
||||
$html .= html_writer::start_tag('ul', array('id' => 'comment-list-'.$this->cid, 'class' => 'comment-list'));
|
||||
$html .= html_writer::tag('li', '', array('class' => 'first'));
|
||||
$html .= html_writer::end_tag('ul'); // .comment-list
|
||||
$html .= html_writer::tag('div', '', array('id' => 'comment-pagination-'.$this->cid, 'class' => 'comment-pagination'));
|
||||
}
|
||||
|
||||
if (!empty($this->postcap)) {
|
||||
if ($this->can_post()) {
|
||||
// print posting textarea
|
||||
$html .= html_writer::start_tag('div', array('class' => 'comment-area'));
|
||||
$html .= html_writer::start_tag('div', array('class' => 'db'));
|
||||
@ -478,15 +568,15 @@ EOD;
|
||||
*/
|
||||
public function get_comments($page = '') {
|
||||
global $DB, $CFG, $USER, $OUTPUT;
|
||||
if (empty($this->viewcap)) {
|
||||
if (!$this->can_view()) {
|
||||
return false;
|
||||
}
|
||||
if (!is_numeric($page)) {
|
||||
$page = 0;
|
||||
}
|
||||
$this->page = $page;
|
||||
$params = array();
|
||||
$start = $page * $CFG->commentsperpage;
|
||||
$perpage = (!empty($CFG->commentsperpage))?$CFG->commentsperpage:15;
|
||||
$start = $page * $perpage;
|
||||
$ufields = user_picture::fields('u');
|
||||
$sql = "SELECT $ufields, c.id AS cid, c.content AS ccontent, c.format AS cformat, c.timecreated AS ctimecreated
|
||||
FROM {comments} c
|
||||
@ -498,9 +588,8 @@ EOD;
|
||||
$params['itemid'] = $this->itemid;
|
||||
|
||||
$comments = array();
|
||||
$candelete = has_capability('moodle/comment:delete', $this->context);
|
||||
$formatoptions = array('overflowdiv' => true);
|
||||
$rs = $DB->get_recordset_sql($sql, $params, $start, $CFG->commentsperpage);
|
||||
$rs = $DB->get_recordset_sql($sql, $params, $start, $perpage);
|
||||
foreach ($rs as $u) {
|
||||
$c = new stdClass();
|
||||
$c->id = $u->cid;
|
||||
@ -512,8 +601,9 @@ EOD;
|
||||
$c->fullname = fullname($u);
|
||||
$c->time = userdate($c->timecreated, get_string('strftimerecent', 'langconfig'));
|
||||
$c->content = format_text($c->content, $c->format, $formatoptions);
|
||||
|
||||
$c->avatar = $OUTPUT->user_picture($u, array('size'=>18));
|
||||
|
||||
$candelete = $this->can_delete($c->id);
|
||||
if (($USER->id == $u->id) || !empty($candelete)) {
|
||||
$c->delete = true;
|
||||
}
|
||||
@ -523,31 +613,45 @@ EOD;
|
||||
|
||||
if (!empty($this->plugintype)) {
|
||||
// moodle module will filter comments
|
||||
$comments = plugin_callback($this->plugintype, $this->pluginname, FEATURE_COMMENT, 'display', array($comments, $this->args), $comments);
|
||||
$comments = plugin_callback($this->plugintype, $this->pluginname, 'comment', 'display', array($comments, $this->comment_param), $comments);
|
||||
}
|
||||
|
||||
return $comments;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the number of comments associated with the details of this object
|
||||
*
|
||||
* @global moodle_database $DB
|
||||
* @return int
|
||||
*/
|
||||
public function count() {
|
||||
global $DB;
|
||||
if ($count = $DB->count_records('comments', array('itemid'=>$this->itemid, 'commentarea'=>$this->commentarea, 'contextid'=>$this->context->id))) {
|
||||
return $count;
|
||||
} else {
|
||||
return 0;
|
||||
if ($this->totalcommentcount === null) {
|
||||
$this->totalcommentcount = $DB->count_records('comments', array('itemid' => $this->itemid, 'commentarea' => $this->commentarea, 'contextid' => $this->context->id));
|
||||
}
|
||||
return $this->totalcommentcount;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns HTML to display a pagination bar
|
||||
*
|
||||
* @global stdClass $CFG
|
||||
* @global core_renderer $OUTPUT
|
||||
* @param int $page
|
||||
* @return string
|
||||
*/
|
||||
public function get_pagination($page = 0) {
|
||||
global $DB, $CFG, $OUTPUT;
|
||||
global $CFG, $OUTPUT;
|
||||
$count = $this->count();
|
||||
$pages = (int)ceil($count/$CFG->commentsperpage);
|
||||
$perpage = (!empty($CFG->commentsperpage))?$CFG->commentsperpage:15;
|
||||
$pages = (int)ceil($count/$perpage);
|
||||
if ($pages == 1 || $pages == 0) {
|
||||
return html_writer::tag('div', '', array('id' => 'comment-pagination-'.$this->cid, 'class' => 'comment-pagination'));
|
||||
}
|
||||
if (!empty(self::$nonjs)) {
|
||||
// used in non-js interface
|
||||
return $OUTPUT->paging_bar($count, $page, $CFG->commentsperpage, $this->get_nojslink(), 'comment_page');
|
||||
return $OUTPUT->paging_bar($count, $page, $perpage, $this->get_nojslink(), 'comment_page');
|
||||
} else {
|
||||
// return ajax paging bar
|
||||
$str = '';
|
||||
@ -567,16 +671,18 @@ EOD;
|
||||
|
||||
/**
|
||||
* Add a new comment
|
||||
*
|
||||
* @global moodle_database $DB
|
||||
* @param string $content
|
||||
* @return mixed
|
||||
*/
|
||||
public function add($content, $format = FORMAT_MOODLE) {
|
||||
global $CFG, $DB, $USER, $OUTPUT;
|
||||
if (empty($this->postcap)) {
|
||||
if (!$this->can_post()) {
|
||||
throw new comment_exception('nopermissiontocomment');
|
||||
}
|
||||
$now = time();
|
||||
$newcmt = new stdClass();
|
||||
$newcmt = new stdClass;
|
||||
$newcmt->contextid = $this->contextid;
|
||||
$newcmt->commentarea = $this->commentarea;
|
||||
$newcmt->itemid = $this->itemid;
|
||||
@ -585,20 +691,15 @@ EOD;
|
||||
$newcmt->userid = $USER->id;
|
||||
$newcmt->timecreated = $now;
|
||||
|
||||
if (!empty($this->plugintype)) {
|
||||
// moodle module will check content
|
||||
$ret = plugin_callback($this->plugintype, $this->pluginname, FEATURE_COMMENT, 'add', array(&$newcmt, $this->args), true);
|
||||
if (!$ret) {
|
||||
throw new comment_exception('modulererejectcomment');
|
||||
}
|
||||
}
|
||||
// This callback allow module to modify the content of comment, such as filter or replacement
|
||||
plugin_callback($this->plugintype, $this->pluginname, 'comment', 'add', array(&$newcmt, $this->comment_param));
|
||||
|
||||
$cmt_id = $DB->insert_record('comments', $newcmt);
|
||||
if (!empty($cmt_id)) {
|
||||
$newcmt->id = $cmt_id;
|
||||
$newcmt->time = userdate($now, get_string('strftimerecent', 'langconfig'));
|
||||
$newcmt->fullname = fullname($USER);
|
||||
$url = new moodle_url('/user/view.php', array('id'=>$USER->id, 'course'=>$this->courseid));
|
||||
$url = new moodle_url('/user/view.php', array('id' => $USER->id, 'course' => $this->courseid));
|
||||
$newcmt->profileurl = $url->out();
|
||||
$newcmt->content = format_text($newcmt->content, $format, array('overflowdiv'=>true));
|
||||
$newcmt->avatar = $OUTPUT->user_picture($USER, array('size'=>16));
|
||||
@ -610,7 +711,7 @@ EOD;
|
||||
|
||||
/**
|
||||
* delete by context, commentarea and itemid
|
||||
* @param object $param {
|
||||
* @param stdClass|array $param {
|
||||
* contextid => int the context in which the comments exist [required]
|
||||
* commentarea => string the comment area [optional]
|
||||
* itemid => int comment itemid [optional]
|
||||
@ -629,7 +730,8 @@ EOD;
|
||||
|
||||
/**
|
||||
* Delete page_comments in whole course, used by course reset
|
||||
* @param object $context course context
|
||||
*
|
||||
* @param stdClass $context course context
|
||||
*/
|
||||
public function reset_course_page_comments($context) {
|
||||
global $DB;
|
||||
@ -645,6 +747,7 @@ EOD;
|
||||
|
||||
/**
|
||||
* Delete a comment
|
||||
*
|
||||
* @param int $commentid
|
||||
* @return mixed
|
||||
*/
|
||||
@ -663,6 +766,7 @@ EOD;
|
||||
|
||||
/**
|
||||
* Print comments
|
||||
*
|
||||
* @param int $page
|
||||
* @param boolean $return return comments list string or print it out
|
||||
* @param boolean $nonjs print nonjs comments list or not?
|
||||
@ -670,6 +774,11 @@ EOD;
|
||||
*/
|
||||
public function print_comments($page = 0, $return = true, $nonjs = true) {
|
||||
global $DB, $CFG, $PAGE;
|
||||
|
||||
if (!$this->can_view()) {
|
||||
return '';
|
||||
}
|
||||
|
||||
$html = '';
|
||||
if (!(self::$comment_itemid == $this->itemid &&
|
||||
self::$comment_context == $this->context->id &&
|
||||
@ -680,38 +789,34 @@ EOD;
|
||||
|
||||
$html = '';
|
||||
if ($nonjs) {
|
||||
$html .= '<h3>'.get_string('comments').'</h3>';
|
||||
$html .= "<ul id='comment-list-$this->cid' class='comment-list'>";
|
||||
$html .= html_writer::tag('h3', get_string('comments'));
|
||||
$html .= html_writer::start_tag('ul', array('id' => 'comment-list-'.$this->cid, 'class' => 'comment-list'));
|
||||
}
|
||||
$results = array();
|
||||
$list = '';
|
||||
|
||||
foreach ($comments as $cmt) {
|
||||
$list = '<li id="comment-'.$cmt->id.'-'.$this->cid.'">'.$this->print_comment($cmt, $nonjs).'</li>' . $list;
|
||||
// Reverse the comments array to display them in the correct direction
|
||||
foreach (array_reverse($comments) as $cmt) {
|
||||
$html .= html_writer::tag('li', $this->print_comment($cmt, $nonjs), array('id' => 'comment-'.$cmt->id.'-'.$this->cid));
|
||||
}
|
||||
$html .= $list;
|
||||
if ($nonjs) {
|
||||
$html .= '</ul>';
|
||||
$html .= html_writer::end_tag('ul');
|
||||
$html .= $this->get_pagination($page);
|
||||
}
|
||||
$sesskey = sesskey();
|
||||
$returnurl = $PAGE->url;
|
||||
$strsubmit = get_string('submit');
|
||||
if ($nonjs) {
|
||||
$html .= <<<EOD
|
||||
<form method="POST" action="{$CFG->wwwroot}/comment/comment_post.php">
|
||||
<textarea name="content" rows="2"></textarea>
|
||||
<input type="hidden" name="contextid" value="$this->contextid" />
|
||||
<input type="hidden" name="action" value="add" />
|
||||
<input type="hidden" name="area" value="$this->commentarea" />
|
||||
<input type="hidden" name="component" value="$this->component" />
|
||||
<input type="hidden" name="itemid" value="$this->itemid" />
|
||||
<input type="hidden" name="courseid" value="{$this->courseid}" />
|
||||
<input type="hidden" name="sesskey" value="{$sesskey}" />
|
||||
<input type="hidden" name="returnurl" value="{$returnurl}" />
|
||||
<input type="submit" value="{$strsubmit}" />
|
||||
</form>
|
||||
EOD;
|
||||
if ($nonjs && $this->can_post()) {
|
||||
// Form to add comments
|
||||
$html .= html_writer::start_tag('form', array('method' => 'post', 'action' => new moodle_url('/comment/comment_post.php')));
|
||||
// Comment parameters
|
||||
$html .= html_writer::empty_tag('input', array('type' => 'hidden', 'name' => 'contextid', 'value' => $this->contextid));
|
||||
$html .= html_writer::empty_tag('input', array('type' => 'hidden', 'name' => 'action', 'value' => 'add'));
|
||||
$html .= html_writer::empty_tag('input', array('type' => 'hidden', 'name' => 'area', 'value' => $this->commentarea));
|
||||
$html .= html_writer::empty_tag('input', array('type' => 'hidden', 'name' => 'component', 'value' => $this->component));
|
||||
$html .= html_writer::empty_tag('input', array('type' => 'hidden', 'name' => 'itemid', 'value' => $this->itemid));
|
||||
$html .= html_writer::empty_tag('input', array('type' => 'hidden', 'name' => 'courseid', 'value' => $this->courseid));
|
||||
$html .= html_writer::empty_tag('input', array('type' => 'hidden', 'name' => 'sesskey', 'value' => sesskey()));
|
||||
$html .= html_writer::empty_tag('input', array('type' => 'hidden', 'name' => 'returnurl', 'value' => $PAGE->url));
|
||||
// Textarea for the actual comment
|
||||
$html .= html_writer::tag('textarea', '', array('name' => 'content', 'rows' => 2));
|
||||
// Submit button to add the comment
|
||||
$html .= html_writer::empty_tag('input', array('type' => 'submit', 'value' => get_string('submit')));
|
||||
$html .= html_writer::end_tag('form');
|
||||
}
|
||||
if ($return) {
|
||||
return $html;
|
||||
@ -720,14 +825,35 @@ EOD;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns an array containing comments in HTML format.
|
||||
*
|
||||
* @global core_renderer $OUTPUT
|
||||
* @param stdClass $cmt {
|
||||
* id => int comment id
|
||||
* content => string comment content
|
||||
* format => int comment text format
|
||||
* timecreated => int comment's timecreated
|
||||
* profileurl => string link to user profile
|
||||
* fullname => comment author's full name
|
||||
* avatar => string user's avatar
|
||||
* delete => boolean does user have permission to delete comment?
|
||||
* }
|
||||
* @param bool $nonjs
|
||||
* @return array
|
||||
*/
|
||||
public function print_comment($cmt, $nonjs = true) {
|
||||
global $OUTPUT;
|
||||
$patterns = array();
|
||||
$replacements = array();
|
||||
|
||||
if (!empty($cmt->delete) && empty($nonjs)) {
|
||||
$cmt->content = '<div class="comment-delete"><a href="#" id ="comment-delete-'.$this->cid.'-'.$cmt->id.'"><img src="'.$OUTPUT->pix_url('t/delete').'" alt="'.get_string('delete').'" /></a></div>' . $cmt->content;
|
||||
// add the button
|
||||
$deletelink = html_writer::start_tag('div', array('class'=>'comment-delete'));
|
||||
$deletelink .= html_writer::start_tag('a', array('href' => '#', 'id' => 'comment-delete-'.$this->cid.'-'.$cmt->id));
|
||||
$deletelink .= $OUTPUT->pix_icon('t/delete', get_string('delete'));
|
||||
$deletelink .= html_writer::end_tag('a');
|
||||
$deletelink .= html_writer::end_tag('div');
|
||||
$cmt->content = $deletelink . $cmt->content;
|
||||
}
|
||||
$patterns[] = '___picture___';
|
||||
$patterns[] = '___name___';
|
||||
@ -741,12 +867,101 @@ EOD;
|
||||
// use html template to format a single comment.
|
||||
return str_replace($patterns, $replacements, $this->template);
|
||||
}
|
||||
|
||||
/**
|
||||
* Revoke validate callbacks
|
||||
*
|
||||
* @param stdClass $params addtionall parameters need to add to callbacks
|
||||
*/
|
||||
protected function validate($params=array()) {
|
||||
foreach ($params as $key=>$value) {
|
||||
$this->comment_param->$key = $value;
|
||||
}
|
||||
$validation = plugin_callback($this->plugintype, $this->pluginname, 'comment', 'validate', array($this->comment_param), false);
|
||||
if (!$validation) {
|
||||
throw new comment_exception('invalidcommentparam');
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns true if the user is able to view comments
|
||||
* @return bool
|
||||
*/
|
||||
public function can_view() {
|
||||
$this->validate();
|
||||
return !empty($this->viewcap);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns true if the user can add comments against this comment description
|
||||
* @return bool
|
||||
*/
|
||||
public function can_post() {
|
||||
$this->validate();
|
||||
return isloggedin() && !empty($this->postcap);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns true if the user can delete this comment
|
||||
* @param int $commentid
|
||||
* @return bool
|
||||
*/
|
||||
public function can_delete($commentid) {
|
||||
$this->validate(array('commentid'=>$commentid));
|
||||
return has_capability('moodle/comment:delete', $this->context);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the component associated with the comment
|
||||
* @return string
|
||||
*/
|
||||
public function get_compontent() {
|
||||
return $this->component;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the context associated with the comment
|
||||
* @return stdClass
|
||||
*/
|
||||
public function get_context() {
|
||||
return $this->context;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the course id associated with the comment
|
||||
* @return int
|
||||
*/
|
||||
public function get_courseid() {
|
||||
return $this->courseid;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the course module associated with the comment
|
||||
*
|
||||
* @return stdClass
|
||||
*/
|
||||
public function get_cm() {
|
||||
return $this->cm;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the item id associated with the comment
|
||||
*
|
||||
* @return int
|
||||
*/
|
||||
public function get_itemid() {
|
||||
return $this->itemid;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the comment area associated with the commentarea
|
||||
*
|
||||
* @return stdClass
|
||||
*/
|
||||
public function get_commentarea() {
|
||||
return $this->commentarea;
|
||||
}
|
||||
}
|
||||
|
||||
class comment_exception extends moodle_exception {
|
||||
public $message;
|
||||
function __construct($errorcode) {
|
||||
$this->errorcode = $errorcode;
|
||||
$this->message = get_string($errorcode, 'error');
|
||||
}
|
||||
}
|
||||
|
@ -23,46 +23,70 @@
|
||||
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
|
||||
*/
|
||||
class comment_manager {
|
||||
|
||||
/**
|
||||
* The number of comments to display per page
|
||||
* @var int
|
||||
*/
|
||||
private $perpage;
|
||||
function __construct() {
|
||||
|
||||
/**
|
||||
* Constructs the comment_manage object
|
||||
*/
|
||||
public function __construct() {
|
||||
global $CFG;
|
||||
$this->perpage = $CFG->commentsperpage;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return comments by pages
|
||||
*
|
||||
* @global moodle_database $DB
|
||||
* @param int $page
|
||||
* @return mixed
|
||||
* @return array An array of comments
|
||||
*/
|
||||
function get_comments($page) {
|
||||
global $DB, $CFG, $USER;
|
||||
$params = array();
|
||||
global $DB;
|
||||
|
||||
if ($page == 0) {
|
||||
$start = 0;
|
||||
} else {
|
||||
$start = $page*$this->perpage;
|
||||
$start = $page * $this->perpage;
|
||||
}
|
||||
$sql = "SELECT c.id, c.contextid, c.itemid, c.commentarea, c.userid, c.content, u.firstname, u.lastname, c.timecreated
|
||||
FROM {comments} c, {user} u
|
||||
WHERE u.id=c.userid ORDER BY c.timecreated ASC";
|
||||
|
||||
$comments = array();
|
||||
|
||||
$sql = "SELECT c.id, c.contextid, c.itemid, c.commentarea, c.userid, c.content, u.firstname, u.lastname, c.timecreated
|
||||
FROM {comments} c
|
||||
JOIN {user} u
|
||||
ON u.id=c.userid
|
||||
ORDER BY c.timecreated ASC";
|
||||
$rs = $DB->get_recordset_sql($sql, null, $start, $this->perpage);
|
||||
$formatoptions = array('overflowdiv' => true);
|
||||
if ($records = $DB->get_records_sql($sql, array(), $start, $this->perpage)) {
|
||||
foreach ($records as $item) {
|
||||
$item->fullname = fullname($item);
|
||||
$item->time = userdate($item->timecreated);
|
||||
$item->content = format_text($item->content, FORMAT_MOODLE, $formatoptions);
|
||||
$comments[] = $item;
|
||||
unset($item->firstname);
|
||||
unset($item->lastname);
|
||||
unset($item->timecreated);
|
||||
}
|
||||
foreach ($rs as $item) {
|
||||
// Set calculated fields
|
||||
$item->fullname = fullname($item);
|
||||
$item->time = userdate($item->timecreated);
|
||||
$item->content = format_text($item->content, FORMAT_MOODLE, $formatoptions);
|
||||
// Unset fields not related to the comment
|
||||
unset($item->firstname);
|
||||
unset($item->lastname);
|
||||
unset($item->timecreated);
|
||||
// Record the comment
|
||||
$comments[] = $item;
|
||||
}
|
||||
$rs->close();
|
||||
|
||||
return $comments;
|
||||
}
|
||||
|
||||
/**
|
||||
* Records the course object
|
||||
*
|
||||
* @global moodle_page $PAGE
|
||||
* @global moodle_database $DB
|
||||
* @param int $courseid
|
||||
* @return void
|
||||
*/
|
||||
private function setup_course($courseid) {
|
||||
global $PAGE, $DB;
|
||||
if (!empty($this->course)) {
|
||||
@ -71,88 +95,116 @@ class comment_manager {
|
||||
}
|
||||
if ($courseid == $PAGE->course->id) {
|
||||
$this->course = $PAGE->course;
|
||||
} else if (!$this->course = $DB->get_record('course', array('id'=>$courseid))) {
|
||||
} else if (!$this->course = $DB->get_record('course', array('id' => $courseid))) {
|
||||
$this->course = null;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets up the module or block information for a comment
|
||||
*
|
||||
* @global moodle_database $DB
|
||||
* @param stdClass $comment
|
||||
* @return bool
|
||||
*/
|
||||
private function setup_plugin($comment) {
|
||||
global $DB;
|
||||
$this->context = get_context_instance_by_id($comment->contextid);
|
||||
if (!is_object($this->context)) {
|
||||
return;
|
||||
if (!$this->context) {
|
||||
return false;
|
||||
}
|
||||
if ($this->context->contextlevel == CONTEXT_BLOCK) {
|
||||
if ($block = $DB->get_record('block_instances', array('id'=>$this->context->instanceid))) {
|
||||
$this->plugintype = 'block';
|
||||
$this->pluginname = $block->blockname;
|
||||
}
|
||||
}
|
||||
if ($this->context->contextlevel == CONTEXT_MODULE) {
|
||||
$this->plugintype = 'mod';
|
||||
$this->cm = get_coursemodule_from_id('', $this->context->instanceid);
|
||||
$this->setup_course($this->cm->course);
|
||||
$this->modinfo = get_fast_modinfo($this->course);
|
||||
$this->pluginname = $this->modinfo->cms[$this->cm->id]->modname;
|
||||
switch ($this->context->contextlevel) {
|
||||
case CONTEXT_BLOCK:
|
||||
if ($block = $DB->get_record('block_instances', array('id' => $this->context->instanceid))) {
|
||||
$this->plugintype = 'block';
|
||||
$this->pluginname = $block->blockname;
|
||||
} else {
|
||||
return false;
|
||||
}
|
||||
break;
|
||||
case CONTEXT_MODULE:
|
||||
$this->plugintype = 'mod';
|
||||
$this->cm = get_coursemodule_from_id('', $this->context->instanceid);
|
||||
$this->setup_course($this->cm->course);
|
||||
$this->modinfo = get_fast_modinfo($this->course);
|
||||
$this->pluginname = $this->modinfo->cms[$this->cm->id]->modname;
|
||||
break;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Print comments
|
||||
* @param int $page
|
||||
* @return boolean return false if no comments available
|
||||
*/
|
||||
function print_comments($page=0) {
|
||||
global $CFG, $OUTPUT, $DB;
|
||||
$count = $DB->count_records_sql('SELECT COUNT(*) FROM {comments} c');
|
||||
public function print_comments($page = 0) {
|
||||
global $OUTPUT, $CFG, $OUTPUT, $DB;
|
||||
|
||||
$count = $DB->count_records('comments');
|
||||
$comments = $this->get_comments($page);
|
||||
if (count($comments) == 0) {
|
||||
echo $OUTPUT->notification(get_string('nocomments', 'moodle'));
|
||||
return false;
|
||||
}
|
||||
|
||||
$table = new html_table();
|
||||
$table->head = array (html_writer::checkbox('selectall', '', false, get_string('selectall'), array('id'=>'comment_select_all', 'class'=>'comment-report-selectall')), get_string('author', 'search'), get_string('content'), get_string('action'));
|
||||
$table->head = array (
|
||||
html_writer::checkbox('selectall', '', false, get_string('selectall'), array('id'=>'comment_select_all', 'class'=>'comment-report-selectall')),
|
||||
get_string('author', 'search'),
|
||||
get_string('content'),
|
||||
get_string('action')
|
||||
);
|
||||
$table->align = array ('left', 'left', 'left', 'left');
|
||||
$table->attributes = array('class'=>'generaltable commentstable');
|
||||
$table->data = array();
|
||||
$linkbase = $CFG->wwwroot.'/comment/index.php?action=delete&sesskey='.sesskey();
|
||||
|
||||
$link = new moodle_url('/comment/index.php', array('action' => 'delete', 'sesskey' => sesskey()));
|
||||
foreach ($comments as $c) {
|
||||
$link = $linkbase . '&commentid='. $c->id;
|
||||
$this->setup_plugin($c);
|
||||
if (!empty($this->plugintype)) {
|
||||
$context_url = plugin_callback($this->plugintype, $this->pluginname, FEATURE_COMMENT, 'url', array($c));
|
||||
$context_url = plugin_callback($this->plugintype, $this->pluginname, 'comment', 'url', array($c));
|
||||
}
|
||||
$checkbox = html_writer::checkbox('comments', $c->id, false);
|
||||
$action = html_writer::link($link, get_string('delete'));
|
||||
$action = html_writer::link(new moodle_url($link, array('commentid' => $c->id)), get_string('delete'));
|
||||
if (!empty($context_url)) {
|
||||
$action .= html_writer::tag('br', null);
|
||||
$action .= html_writer::empty_tag('br');
|
||||
$action .= html_writer::link($context_url, get_string('commentincontext'), array('target'=>'_blank'));
|
||||
}
|
||||
$table->data[] = array($checkbox, $c->fullname, $c->content, $action);
|
||||
}
|
||||
echo html_writer::table($table);
|
||||
echo $OUTPUT->paging_bar($count, $page, $this->perpage, $CFG->wwwroot.'/comment/index.php');
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* delete a comment
|
||||
* Delete a comment
|
||||
*
|
||||
* @param int $commentid
|
||||
* @return bool
|
||||
*/
|
||||
public function delete_comment($commentid) {
|
||||
global $DB;
|
||||
if ($comment = $DB->get_record('comments', array('id'=>$commentid))) {
|
||||
$DB->delete_records('comments', array('id'=>$commentid));
|
||||
if ($DB->record_exists('comments', array('id' => $commentid))) {
|
||||
$DB->delete_records('comments', array('id' => $commentid));
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
/**
|
||||
* delete comments
|
||||
* @param int $commentid
|
||||
* Delete comments
|
||||
*
|
||||
* @param string $list A list of comment ids separated by hyphens
|
||||
* @return bool
|
||||
*/
|
||||
public function delete_comments($list) {
|
||||
global $DB;
|
||||
$ids = explode('-', $list);
|
||||
foreach ($ids as $id) {
|
||||
if (is_int((int)$id)) {
|
||||
if ($comment = $DB->get_record('comments', array('id'=>$id))) {
|
||||
$DB->delete_records('comments', array('id'=>$comment->id));
|
||||
}
|
||||
$id = (int)$id;
|
||||
if ($DB->record_exists('comments', array('id' => $id))) {
|
||||
$DB->delete_records('comments', array('id' => $id));
|
||||
}
|
||||
}
|
||||
return true;
|
||||
|
@ -32,6 +32,7 @@ $string['blockcannotread'] = 'Could not read data for blockid= {$a}';
|
||||
$string['blockdoesnotexist'] = 'This block does not exist';
|
||||
$string['blockdoesnotexistonpage'] = 'This block (id={$a->instanceid}) does not exist on this page ({$a->url}).';
|
||||
$string['blocknameconflict'] = 'Naming conflict: block {$a->name} has the same title with an existing block: {$a->conflict}!';
|
||||
$string['callbackrejectcomment'] = 'Comment callback rejected this comment.';
|
||||
$string['cannotaddcoursemodule'] = 'Could not add a new course module';
|
||||
$string['cannotaddcoursemoduletosection'] = 'Could not add the new course module to that section';
|
||||
$string['cannotaddmodule'] = '{$a} module could not be added to the module list!';
|
||||
@ -262,6 +263,11 @@ $string['invalidbulkenrolop'] = 'Invalid bulk enrolment operation requested.';
|
||||
$string['invalidcategory'] = 'Incorrect category!';
|
||||
$string['invalidcategoryid'] = 'Incorrect category id!';
|
||||
$string['invalidcomment'] = 'Comment is incorrect';
|
||||
$string['invalidcommentid'] = 'Invalid comment id';
|
||||
$string['invalidcommentitemid'] = 'Invalid comment itemid';
|
||||
$string['invalidcommentarea'] = 'Invalid comment area';
|
||||
$string['invalidcommentparam'] = 'Invalid comment parameters';
|
||||
$string['invalidcomponent'] = 'Invalid component name';
|
||||
$string['invalidconfirmdata'] = 'Invalid confirmation data';
|
||||
$string['invalidcontext'] = 'Invalid context';
|
||||
$string['invalidcourse'] = 'Invalid course';
|
||||
@ -344,7 +350,6 @@ $string['moduledisable'] = 'This module ({$a}) has been disabled for this partic
|
||||
$string['moduledoesnotexist'] = 'This module does not exist';
|
||||
$string['moduleinstancedoesnotexist'] = 'The instance of this module does not exist';
|
||||
$string['modulemissingcode'] = 'Module {$a} is missing the code needed to perform this function';
|
||||
$string['modulerejectcomment'] = 'Module rejects to add this comment';
|
||||
$string['multiplerecordsfound'] = 'Multiple records found, only one record expected.';
|
||||
$string['multiplerestorenotallow'] = 'Multiple restore execution not allowed!';
|
||||
$string['mustbeloggedin'] = 'You must be logged in to do this';
|
||||
|
@ -242,6 +242,7 @@ $string['closewindow'] = 'Close this window';
|
||||
$string['collapseall'] = 'Collapse all';
|
||||
$string['commentincontext'] = 'Find this comment in context';
|
||||
$string['comments'] = 'Comments';
|
||||
$string['commentsnotenabled'] = 'Comments feature is not enabled';
|
||||
$string['commentsrequirelogin'] = 'You need to login to view the comments';
|
||||
$string['comparelanguage'] = 'Compare and edit current language';
|
||||
$string['complete'] = 'Complete';
|
||||
@ -1137,6 +1138,7 @@ $string['nobody'] = 'Nobody';
|
||||
$string['nocourses'] = 'No courses';
|
||||
$string['nocoursesfound'] = 'No courses were found with the words \'{$a}\'';
|
||||
$string['nocoursesyet'] = 'No courses in this category';
|
||||
$string['nocomments'] = 'No comments';
|
||||
$string['nodstpresets'] = 'The administrator has not enabled Daylight Savings Time support.';
|
||||
$string['nofilesselected'] = 'No files have been selected to restore';
|
||||
$string['nofilesyet'] = 'No files have been uploaded to your course yet';
|
||||
|
@ -7284,7 +7284,7 @@ function plugin_callback($type, $name, $feature, $action, $options = null, $defa
|
||||
|
||||
$name = clean_param($name, PARAM_SAFEDIR);
|
||||
$function = $name.'_'.$feature.'_'.$action;
|
||||
$file = get_plugin_directory($type, $name) . '/lib.php';
|
||||
$file = get_component_directory($type . '_' . $name) . '/lib.php';
|
||||
|
||||
// Load library and look for function
|
||||
if (file_exists($file)) {
|
||||
|
@ -62,6 +62,7 @@ $string['commentempty'] = 'Comment was empty';
|
||||
$string['comments'] = 'Comments';
|
||||
$string['commentsaved'] = 'Comment saved';
|
||||
$string['commentsn'] = '{$a} comment(s)';
|
||||
$string['commentsoff'] = 'Comments feature is not enabled';
|
||||
$string['configenablerssfeeds'] = 'This switch will enable the possibility of RSS feeds for all databases. You will still need to turn feeds on manually in the settings for each database.';
|
||||
$string['confirmdeletefield'] = 'You are about to delete this field, are you sure?';
|
||||
$string['confirmdeleterecord'] = 'Are you sure you want to delete this entry?';
|
||||
|
105
mod/data/lib.php
105
mod/data/lib.php
@ -3098,3 +3098,108 @@ function data_presets_export($course, $cm, $data, $tostorage=false) {
|
||||
// Return the full path to the exported preset file:
|
||||
return $exportfile;
|
||||
}
|
||||
|
||||
/**
|
||||
* Running addtional permission check on plugin, for example, plugins
|
||||
* may have switch to turn on/off comments option, this callback will
|
||||
* affect UI display, not like pluginname_comment_validate only throw
|
||||
* exceptions.
|
||||
* Capability check has been done in comment->check_permissions(), we
|
||||
* don't need to do it again here.
|
||||
*
|
||||
* @param stdClass $comment_param {
|
||||
* context => context the context object
|
||||
* courseid => int course id
|
||||
* cm => stdClass course module object
|
||||
* commentarea => string comment area
|
||||
* itemid => int itemid
|
||||
* }
|
||||
* @return array
|
||||
*/
|
||||
function data_comment_permissions($comment_param) {
|
||||
global $CFG, $DB;
|
||||
if (!$record = $DB->get_record('data_records', array('id'=>$comment_param->itemid))) {
|
||||
throw new comment_exception('invalidcommentitemid');
|
||||
}
|
||||
if (!$data = $DB->get_record('data', array('id'=>$record->dataid))) {
|
||||
throw new comment_exception('invalidid', 'data');
|
||||
}
|
||||
if ($data->comments) {
|
||||
return array('post'=>true, 'view'=>true);
|
||||
} else {
|
||||
return array('post'=>false, 'view'=>false);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Validate comment parameter before perform other comments actions
|
||||
*
|
||||
* @param stdClass $comment_param {
|
||||
* context => context the context object
|
||||
* courseid => int course id
|
||||
* cm => stdClass course module object
|
||||
* commentarea => string comment area
|
||||
* itemid => int itemid
|
||||
* }
|
||||
* @return boolean
|
||||
*/
|
||||
function data_comment_validate($comment_param) {
|
||||
global $DB;
|
||||
// validate comment area
|
||||
if ($comment_param->commentarea != 'database_entry') {
|
||||
throw new comment_exception('invalidcommentarea');
|
||||
}
|
||||
// validate itemid
|
||||
if (!$record = $DB->get_record('data_records', array('id'=>$comment_param->itemid))) {
|
||||
throw new comment_exception('invalidcommentitemid');
|
||||
}
|
||||
if (!$data = $DB->get_record('data', array('id'=>$record->dataid))) {
|
||||
throw new comment_exception('invalidid', 'data');
|
||||
}
|
||||
if (!$course = $DB->get_record('course', array('id'=>$data->course))) {
|
||||
throw new comment_exception('coursemisconf');
|
||||
}
|
||||
if (!$cm = get_coursemodule_from_instance('data', $data->id, $course->id)) {
|
||||
throw new comment_exception('invalidcoursemodule');
|
||||
}
|
||||
if (!$data->comments) {
|
||||
throw new comment_exception('commentsoff', 'data');
|
||||
}
|
||||
$context = get_context_instance(CONTEXT_MODULE, $cm->id);
|
||||
|
||||
//check if approved
|
||||
if ($data->approval and !$record->approved and !data_isowner($record) and !has_capability('mod/data:approve', $context)) {
|
||||
throw new comment_exception('notapproved', 'data');
|
||||
}
|
||||
|
||||
// group access
|
||||
if ($record->groupid) {
|
||||
$groupmode = groups_get_activity_groupmode($cm, $course);
|
||||
if ($groupmode == SEPARATEGROUPS and !has_capability('moodle/site:accessallgroups', $context)) {
|
||||
if (!groups_is_member($record->groupid)) {
|
||||
throw new comment_exception('notmemberofgroup');
|
||||
}
|
||||
}
|
||||
}
|
||||
// validate context id
|
||||
if ($context->id != $comment_param->context->id) {
|
||||
throw new comment_exception('invalidcontext');
|
||||
}
|
||||
// validation for comment deletion
|
||||
if (!empty($comment_param->commentid)) {
|
||||
if ($comment = $DB->get_record('comments', array('id'=>$comment_param->commentid))) {
|
||||
if ($comment->commentarea != 'database_entry') {
|
||||
throw new comment_exception('invalidcommentarea');
|
||||
}
|
||||
if ($comment->contextid != $comment_param->context->id) {
|
||||
throw new comment_exception('invalidcontext');
|
||||
}
|
||||
if ($comment->itemid != $comment_param->itemid) {
|
||||
throw new comment_exception('invalidcommentitemid');
|
||||
}
|
||||
} else {
|
||||
throw new comment_exception('invalidcommentid');
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
@ -216,6 +216,7 @@ $string['nopermissiontodelcomment'] = 'You can\'t delete other people\'s comment
|
||||
$string['nopermissiontodelinglossary'] = 'You can\'t comments in this glossary!';
|
||||
$string['nopermissiontoviewresult'] = 'You can only look at results for your own entries';
|
||||
$string['notcategorised'] = 'Not categorised';
|
||||
$string['notapproved'] = 'glossary entry is not approved yet.';
|
||||
$string['numberofentries'] = 'Number of entries';
|
||||
$string['onebyline'] = '(one per line)';
|
||||
$string['pluginadministration'] = 'Glossary administration';
|
||||
|
@ -2654,3 +2654,82 @@ function glossary_extend_settings_navigation(settings_navigation $settings, navi
|
||||
$glossarynode->add($string, $url, settings_navigation::TYPE_SETTING, null, null, new pix_icon('i/rss', ''));
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Running addtional permission check on plugin, for example, plugins
|
||||
* may have switch to turn on/off comments option, this callback will
|
||||
* affect UI display, not like pluginname_comment_validate only throw
|
||||
* exceptions.
|
||||
* Capability check has been done in comment->check_permissions(), we
|
||||
* don't need to do it again here.
|
||||
*
|
||||
* @param stdClass $comment_param {
|
||||
* context => context the context object
|
||||
* courseid => int course id
|
||||
* cm => stdClass course module object
|
||||
* commentarea => string comment area
|
||||
* itemid => int itemid
|
||||
* }
|
||||
* @return array
|
||||
*/
|
||||
function glossary_comment_permissions($comment_param) {
|
||||
return array('post'=>true, 'view'=>true);
|
||||
}
|
||||
|
||||
/**
|
||||
* Validate comment parameter before perform other comments actions
|
||||
*
|
||||
* @param stdClass $comment_param {
|
||||
* context => context the context object
|
||||
* courseid => int course id
|
||||
* cm => stdClass course module object
|
||||
* commentarea => string comment area
|
||||
* itemid => int itemid
|
||||
* }
|
||||
* @return boolean
|
||||
*/
|
||||
function glossary_comment_validate($comment_param) {
|
||||
global $DB;
|
||||
// validate comment area
|
||||
if ($comment_param->commentarea != 'glossary_entry') {
|
||||
throw new comment_exception('invalidcommentarea');
|
||||
}
|
||||
if (!$record = $DB->get_record('glossary_entries', array('id'=>$comment_param->itemid))) {
|
||||
throw new comment_exception('invalidcommentitemid');
|
||||
}
|
||||
if (!$glossary = $DB->get_record('glossary', array('id'=>$record->glossaryid))) {
|
||||
throw new comment_exception('invalidid', 'data');
|
||||
}
|
||||
if (!$course = $DB->get_record('course', array('id'=>$glossary->course))) {
|
||||
throw new comment_exception('coursemisconf');
|
||||
}
|
||||
if (!$cm = get_coursemodule_from_instance('glossary', $glossary->id, $course->id)) {
|
||||
throw new comment_exception('invalidcoursemodule');
|
||||
}
|
||||
$context = get_context_instance(CONTEXT_MODULE, $cm->id);
|
||||
|
||||
if ($glossary->defaultapproval and !$record->approved and !has_capability('mod/glossary:approve', $context)) {
|
||||
throw new comment_exception('notapproved', 'glossary');
|
||||
}
|
||||
// validate context id
|
||||
if ($context->id != $comment_param->context->id) {
|
||||
throw new comment_exception('invalidcontext');
|
||||
}
|
||||
// validation for comment deletion
|
||||
if (!empty($comment_param->commentid)) {
|
||||
if ($comment = $DB->get_record('comments', array('id'=>$comment_param->commentid))) {
|
||||
if ($comment->commentarea != 'glossary_entry') {
|
||||
throw new comment_exception('invalidcommentarea');
|
||||
}
|
||||
if ($comment->contextid != $comment_param->context->id) {
|
||||
throw new comment_exception('invalidcontext');
|
||||
}
|
||||
if ($comment->itemid != $comment_param->itemid) {
|
||||
throw new comment_exception('invalidcommentitemid');
|
||||
}
|
||||
} else {
|
||||
throw new comment_exception('invalidcommentid');
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
@ -548,3 +548,92 @@ function wiki_extend_navigation(navigation_node $navref, $course, $module, $cm)
|
||||
function wiki_get_extra_capabilities() {
|
||||
return array('moodle/comment:view', 'moodle/comment:post', 'moodle/comment:delete');
|
||||
}
|
||||
|
||||
/**
|
||||
* Running addtional permission check on plugin, for example, plugins
|
||||
* may have switch to turn on/off comments option, this callback will
|
||||
* affect UI display, not like pluginname_comment_validate only throw
|
||||
* exceptions.
|
||||
* Capability check has been done in comment->check_permissions(), we
|
||||
* don't need to do it again here.
|
||||
*
|
||||
* @param stdClass $comment_param {
|
||||
* context => context the context object
|
||||
* courseid => int course id
|
||||
* cm => stdClass course module object
|
||||
* commentarea => string comment area
|
||||
* itemid => int itemid
|
||||
* }
|
||||
* @return array
|
||||
*/
|
||||
function wiki_comment_permissions($comment_param) {
|
||||
return array('post'=>true, 'view'=>true);
|
||||
}
|
||||
|
||||
/**
|
||||
* Validate comment parameter before perform other comments actions
|
||||
*
|
||||
* @param stdClass $comment_param {
|
||||
* context => context the context object
|
||||
* courseid => int course id
|
||||
* cm => stdClass course module object
|
||||
* commentarea => string comment area
|
||||
* itemid => int itemid
|
||||
* }
|
||||
* @return boolean
|
||||
*/
|
||||
function wiki_comment_validate($comment_param) {
|
||||
global $DB, $CFG;
|
||||
require_once($CFG->dirroot . '/mod/wiki/locallib.php');
|
||||
// validate comment area
|
||||
if ($comment_param->commentarea != 'wiki_page') {
|
||||
throw new comment_exception('invalidcommentarea');
|
||||
}
|
||||
// validate itemid
|
||||
if (!$record = $DB->get_record('wiki_pages', array('id'=>$comment_param->itemid))) {
|
||||
throw new comment_exception('invalidcommentitemid');
|
||||
}
|
||||
if (!$subwiki = wiki_get_subwiki($record->subwikiid)) {
|
||||
throw new comment_exception('invalidsubwikiid');
|
||||
}
|
||||
if (!$wiki = wiki_get_wiki_from_pageid($comment_param->itemid)) {
|
||||
throw new comment_exception('invalidid', 'data');
|
||||
}
|
||||
if (!$course = $DB->get_record('course', array('id'=>$wiki->course))) {
|
||||
throw new comment_exception('coursemisconf');
|
||||
}
|
||||
if (!$cm = get_coursemodule_from_instance('wiki', $wiki->id, $course->id)) {
|
||||
throw new comment_exception('invalidcoursemodule');
|
||||
}
|
||||
$context = get_context_instance(CONTEXT_MODULE, $cm->id);
|
||||
// group access
|
||||
if ($subwiki->groupid) {
|
||||
$groupmode = groups_get_activity_groupmode($cm, $course);
|
||||
if ($groupmode == SEPARATEGROUPS and !has_capability('moodle/site:accessallgroups', $context)) {
|
||||
if (!groups_is_member($subwiki->groupid)) {
|
||||
throw new comment_exception('notmemberofgroup');
|
||||
}
|
||||
}
|
||||
}
|
||||
// validate context id
|
||||
if ($context->id != $comment_param->context->id) {
|
||||
throw new comment_exception('invalidcontext');
|
||||
}
|
||||
// validation for comment deletion
|
||||
if (!empty($comment_param->commentid)) {
|
||||
if ($comment = $DB->get_record('comments', array('id'=>$comment_param->commentid))) {
|
||||
if ($comment->commentarea != 'wiki_page') {
|
||||
throw new comment_exception('invalidcommentarea');
|
||||
}
|
||||
if ($comment->contextid != $context->id) {
|
||||
throw new comment_exception('invalidcontext');
|
||||
}
|
||||
if ($comment->itemid != $comment_param->itemid) {
|
||||
throw new comment_exception('invalidcommentitemid');
|
||||
}
|
||||
} else {
|
||||
throw new comment_exception('invalidcommentid');
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user