官术网_书友最值得收藏!

Working with capabilities

In Chapter 1, Moodle Architecture, we covered an overview of Moodle's role and permission system. Now we will get a chance to see the system in action. In a later section, we will also add our own access permissions to Moodle.

Testing for built-in capabilities

We use two Moodle core functions to test for a capability, in this section of code. First, we call the get_context_instance() function with the site or global context, CONTEXT_SYSTEM. The function get_context_instance() will return a context object to us for the requested context type, in this case the system context. Once the context is loaded, we use the require_capability function to test if the user has the moodle/site:doanything capability (essentially, the ability to do anything and everything on the site). require_capability tests the current user's capabilities to see if they have the specified capability in the specified context. If they don't, the page is redirected to an error page:

function get_content() {
if ($this->content !== NULL) {
return $this->content;
}//if
$context = get_context_instance(CONTEXT_SYSTEM); require_capability('moodle/site:doanything', $context);
$this->content = new stdClass;
$this->content->text = 'Hello World!';
return $this->content;
}//function get_content

If we test this same code while logged in as a non-administrative user, we start to see some issues with how the error is handled. This is an example of using require_capability incorrectly. When the permission fails, we end up with a partially-rendered Moodle screen. The block bleeds out of its side column and the rest of screen is not printed. The following screenshot illustrates what this looks like if the block is placed in the left-hand side column and viewed by a non-administrative user:

Testing for built-in capabilities

The require_capability function is more appropriate for blocking access to an entire page of content. If we want to handle missing capabilities elegantly for a block, we should use the function has_capability. Using the following syntax leads to output that works correctly whether or not the user has the required permission. In this case, we use the has_capability function, which accepts a capability and a context. It returns a response indicating whether or not the user has access to the capability. We then route the results into an if/else clause, which outputs different information to the user depending on whether the capability is present or not.

$context = get_context_instance(CONTEXT_SYSTEM);
$this->content = new stdClass;
if (!has_capability('moodle/site:doanything', $context)){
$this->content->text = 'Not Admin!';
}// if
else {
$this->content->text = 'Secret Message to Admins!'
}// else
return $this->content;

This method is very useful when you want to display different values to the user depending on which capabilities they have access to.

Hiding a block based on capabilities

In many cases, we are only going to want to display the block if the user has a particular capability. By performing some simple restructuring, our get_content() function provides this functionality. By moving the creation of the $this object and its return value into the if statement, we remove the block display if the user doesn't have the moodle/site:doanything capability:

$context = get_context_instance(CONTEXT_SYSTEM);
if (has_capability('moodle/site:doanything', $context)){
$this->content = new stdClass;
$this->content->text = 'Secret Message to Admins!';
return $this->content;
}// if

This method leads to a much cleaner page display, and maximizes the data displayed to the user on any given screen.

Adding your own capability

Let's add a capability, by creating a folder called db within our module. Inside the folder, we create a file called access.php. This file is then used to define your capabilities. Here is an example of a simple read capability definition. Capabilities are defined as arrays. Note that the key assignment is the name of the capability block/helloworld:view. The other values in the array assignment are used to specify which context the capability applies to, the type of capability, and finally default values for legacy roles.

<?php
$block_helloworld_capabilities = array(
'block/helloworld:view' => array(
'captype' => 'read',
'contextlevel' => CONTEXT_SYSTEM,
'legacy' => array(
'guest' => CAP_PREVENT,
'student' => CAP_PREVENT,
'teacher' => CAP_PREVENT,
'editingteacher' => CAP_PREVENT,
'coursecreator' => CAP_PREVENT,
'admin' => CAP_ALLOW
)
)
);
?>

In order to make this change take effect, we need to increment our version value in the block_helloworld.php file. The format for Moodle version numbers is an integer value of the date (year + month + day) plus two digits to indicate the micro version. The higher the number, the newer the version of the module. Let's set the date of our module to year 2009, month 05, and day 07. This also happens to be the third update to the code for today, so we add a micro version of 03. The following code illustrates the assigning of this version number:

$this->version = 2009050703;

Note that, as a result of these changes, we should also add some additional strings, as follows, to our language file:

$string['helloworld:view'] = 'View Hello World Block';
$string['blockname'] = 'HelloWorld';

Let's have a look at the results of these changes, by viewing a role definition in the following screenshot:

Adding your own capability

Checking for our new capability

Now that we have added our new capability, we can use it in our block code instead of the moodle/site:doanything capability. In this new section of code, the line testing the capability is changed as follows, to use the new one that we created:

function get_content() {
if ($this->content !== NULL) {
return $this->content;
}//if
$context = get_context_instance(CONTEXT_SYSTEM);
if (has_capability('block/helloworld:view', $context)) {
$this->content = new stdClass;
$this->content->text = 'Hello World!';
return $this->content;
} //if

Note that this new capability will work anywhere that we might apply a block: on the front page, on the administration page, in the My Moodle page, within course pages, and so on. However, because we have defined the capability in CONTEXT_SYSTEM only users with a role assigned at the site level will be able to view this block.

In testing, we will find that this block is visible to administrative users, because we set the admin legacy role to have CAP_ALLOW in our access.php file. However, any other built-in roles, even if assigned at the site level, will not see this block, because they have received the CAP_PREVENT permission—unless we manually change their role definition.

We can find further details on the latest methods for programming access permissions at http://docs.moodle.org/en/Development:Roles#Programming_Interface.

主站蜘蛛池模板: 抚松县| 耿马| 九龙坡区| 永新县| 田东县| 安顺市| 盐源县| 会东县| 聊城市| 衡南县| 资兴市| 柳河县| 东城区| 宜阳县| 板桥市| 玉林市| 封开县| 邓州市| 文水县| 宁南县| 通榆县| 屯昌县| 容城县| 措美县| 云霄县| 乌鲁木齐县| 弥渡县| 中卫市| 双柏县| 长岭县| 南昌县| 汉中市| 基隆市| 彩票| 交城县| 吉林省| 泽州县| 炎陵县| 罗甸县| 千阳县| 堆龙德庆县|