mirror of
https://github.com/moodle/moodle.git
synced 2025-04-27 11:23:06 +02:00
Merge branch 'MDL-56902-master' of git://github.com/damyon/moodle
This commit is contained in:
commit
44c3d0775c
@ -234,12 +234,18 @@ class block_manager {
|
||||
return false;
|
||||
}
|
||||
|
||||
$undeletableblocks = self::get_undeletable_block_types();
|
||||
foreach ($this->blockinstances as $region) {
|
||||
foreach ($region as $instance) {
|
||||
if (empty($instance->instance->blockname)) {
|
||||
continue;
|
||||
}
|
||||
if ($instance->instance->blockname == $blockname) {
|
||||
if ($instance->instance->requiredbytheme) {
|
||||
if (!in_array($block->name, $undeletableblocks)) {
|
||||
continue;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
}
|
||||
@ -579,6 +585,20 @@ class block_manager {
|
||||
return;
|
||||
}
|
||||
|
||||
// Exclude auto created blocks if they are not undeletable in this theme.
|
||||
$undeletable = $this->get_undeletable_block_types();
|
||||
$undeletablecheck = '';
|
||||
$undeletableparams = array();
|
||||
$undeletablenotparams = array();
|
||||
if (!empty($undeletable)) {
|
||||
list($testsql, $undeletableparams) = $DB->get_in_or_equal($undeletable, SQL_PARAMS_NAMED, 'undeletable');
|
||||
list($testnotsql, $undeletablenotparams) = $DB->get_in_or_equal($undeletable, SQL_PARAMS_NAMED, 'deletable', false);
|
||||
$undeletablecheck = 'AND ((bi.blockname ' . $testsql . ' AND bi.requiredbytheme = 1) OR ' .
|
||||
' (bi.blockname ' . $testnotsql . ' AND bi.requiredbytheme = 0))';
|
||||
} else {
|
||||
$undeletablecheck = 'AND (bi.requiredbytheme = 0)';
|
||||
}
|
||||
|
||||
if (is_null($includeinvisible)) {
|
||||
$includeinvisible = $this->page->user_is_editing();
|
||||
}
|
||||
@ -626,6 +646,7 @@ class block_manager {
|
||||
bi.parentcontextid,
|
||||
bi.showinsubcontexts,
|
||||
bi.pagetypepattern,
|
||||
bi.requiredbytheme,
|
||||
bi.subpagepattern,
|
||||
bi.defaultregion,
|
||||
bi.defaultweight,
|
||||
@ -649,12 +670,15 @@ class block_manager {
|
||||
AND (bi.subpagepattern IS NULL OR bi.subpagepattern = :subpage2)
|
||||
$visiblecheck
|
||||
AND b.visible = 1
|
||||
$undeletablecheck
|
||||
|
||||
ORDER BY
|
||||
COALESCE(bp.region, bi.defaultregion),
|
||||
COALESCE(bp.weight, bi.defaultweight),
|
||||
bi.id";
|
||||
$blockinstances = $DB->get_recordset_sql($sql, $params + $parentcontextparams + $pagetypepatternparams);
|
||||
|
||||
$allparams = $params + $parentcontextparams + $pagetypepatternparams + $undeletableparams + $undeletablenotparams;
|
||||
$blockinstances = $DB->get_recordset_sql($sql, $allparams);
|
||||
|
||||
$this->birecordsbyregion = $this->prepare_per_region_arrays();
|
||||
$unknown = array();
|
||||
@ -957,6 +981,10 @@ class block_manager {
|
||||
* load_blocks. This is used, for example, to ensure that all blocks get a
|
||||
* chance to initialise themselves via the {@link block_base::specialize()}
|
||||
* method, before any output is done.
|
||||
*
|
||||
* It is also used to create any blocks that are "undeletable" by the current theme.
|
||||
* These blocks that are auto-created have requiredbytheme set on the block instance
|
||||
* so they are only visible on themes that require them.
|
||||
*/
|
||||
public function create_all_block_instances() {
|
||||
global $PAGE;
|
||||
@ -977,7 +1005,7 @@ class block_manager {
|
||||
}
|
||||
}
|
||||
if (!$found) {
|
||||
$this->add_block_at_end_of_default_region($forced);
|
||||
$this->add_block_required_by_theme($forced);
|
||||
$missing = true;
|
||||
}
|
||||
}
|
||||
@ -993,6 +1021,45 @@ class block_manager {
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Add a block that is required by the current theme but has not been
|
||||
* created yet. This is a special type of block that only shows in themes that
|
||||
* require it (by listing it in undeletable_block_types).
|
||||
*
|
||||
* @param string $blockname the name of the block type.
|
||||
*/
|
||||
protected function add_block_required_by_theme($blockname) {
|
||||
global $DB;
|
||||
|
||||
if (empty($this->birecordsbyregion)) {
|
||||
// No blocks or block regions exist yet.
|
||||
return;
|
||||
}
|
||||
|
||||
$systemcontext = context_system::instance();
|
||||
$defaultregion = $this->get_default_region();
|
||||
// Add a special system wide block instance only for themes that require it.
|
||||
$blockinstance = new stdClass;
|
||||
$blockinstance->blockname = $blockname;
|
||||
$blockinstance->parentcontextid = $systemcontext->id;
|
||||
$blockinstance->showinsubcontexts = true;
|
||||
$blockinstance->requiredbytheme = true;
|
||||
$blockinstance->pagetypepattern = '*';
|
||||
$blockinstance->subpagepattern = null;
|
||||
$blockinstance->defaultregion = $defaultregion;
|
||||
$blockinstance->defaultweight = 0;
|
||||
$blockinstance->configdata = '';
|
||||
$blockinstance->id = $DB->insert_record('block_instances', $blockinstance);
|
||||
|
||||
// Ensure the block context is created.
|
||||
context_block::instance($blockinstance->id);
|
||||
|
||||
// If the new instance was created, allow it to do additional setup.
|
||||
if ($block = block_instance($blockname, $blockinstance)) {
|
||||
$block->instance_create();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Return an array of content objects from a set of block instances
|
||||
*
|
||||
|
3
lib/db/install.xml
Normal file → Executable file
3
lib/db/install.xml
Normal file → Executable file
@ -1,5 +1,5 @@
|
||||
<?xml version="1.0" encoding="UTF-8" ?>
|
||||
<XMLDB PATH="lib/db" VERSION="20160804" COMMENT="XMLDB file for core Moodle tables"
|
||||
<XMLDB PATH="lib/db" VERSION="20161119" COMMENT="XMLDB file for core Moodle tables"
|
||||
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xsi:noNamespaceSchemaLocation="../../lib/xmldb/xmldb.xsd"
|
||||
>
|
||||
@ -2459,6 +2459,7 @@
|
||||
<FIELD NAME="blockname" TYPE="char" LENGTH="40" NOTNULL="true" SEQUENCE="false" COMMENT="The type of block this is. Foreign key, references block.name."/>
|
||||
<FIELD NAME="parentcontextid" TYPE="int" LENGTH="10" NOTNULL="true" SEQUENCE="false" COMMENT="The context within which this block appears. Foreign key, references context.id."/>
|
||||
<FIELD NAME="showinsubcontexts" TYPE="int" LENGTH="4" NOTNULL="true" SEQUENCE="false" COMMENT="If 1, this block appears on all matching pages in subcontexts of parentcontextid, as well in pages belonging to parentcontextid."/>
|
||||
<FIELD NAME="requiredbytheme" TYPE="int" LENGTH="4" NOTNULL="true" DEFAULT="0" SEQUENCE="false" COMMENT="If 1, this block was created because it was required by the theme and did not exist."/>
|
||||
<FIELD NAME="pagetypepattern" TYPE="char" LENGTH="64" NOTNULL="true" SEQUENCE="false" COMMENT="The types of page this block appears on. Either an exact page type like mod-quiz-view, or a pattern like mod-quiz-* or course-view-*. Note that course-view-* will match course-view."/>
|
||||
<FIELD NAME="subpagepattern" TYPE="char" LENGTH="16" NOTNULL="false" SEQUENCE="false" COMMENT="Further restrictions on where this block appears. In some places, e.g. during a quiz or lesson attempt, different pages have different subpage ids. If this field is not null, the block only appears on that particular subpage."/>
|
||||
<FIELD NAME="defaultregion" TYPE="char" LENGTH="16" NOTNULL="true" SEQUENCE="false" COMMENT="Which block region this block should appear in on each page, in the absence of a specific position in the block_positions table."/>
|
||||
|
@ -2406,5 +2406,32 @@ function xmldb_main_upgrade($oldversion) {
|
||||
upgrade_main_savepoint(true, 2016110600.00);
|
||||
}
|
||||
|
||||
if ($oldversion < 2016112200.01) {
|
||||
|
||||
// Define field requiredbytheme to be added to block_instances.
|
||||
$table = new xmldb_table('block_instances');
|
||||
$field = new xmldb_field('requiredbytheme', XMLDB_TYPE_INTEGER, '4', null, XMLDB_NOTNULL, null, '0', 'showinsubcontexts');
|
||||
|
||||
// Conditionally launch add field requiredbytheme.
|
||||
if (!$dbman->field_exists($table, $field)) {
|
||||
$dbman->add_field($table, $field);
|
||||
}
|
||||
|
||||
// Main savepoint reached.
|
||||
upgrade_main_savepoint(true, 2016112200.01);
|
||||
}
|
||||
if ($oldversion < 2016112200.02) {
|
||||
|
||||
// Change the existing site level admin and settings blocks to be requiredbytheme which means they won't show in boost.
|
||||
$context = context_system::instance();
|
||||
$params = array('blockname' => 'settings', 'parentcontextid' => $context->id);
|
||||
$DB->set_field('block_instances', 'requiredbytheme', 1, $params);
|
||||
|
||||
$params = array('blockname' => 'navigation', 'parentcontextid' => $context->id);
|
||||
$DB->set_field('block_instances', 'requiredbytheme', 1, $params);
|
||||
// Main savepoint reached.
|
||||
upgrade_main_savepoint(true, 2016112200.02);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
@ -542,6 +542,58 @@ class core_blocklib_testcase extends advanced_testcase {
|
||||
context_block::instance($tokeep); // Would throw an exception if it was deleted.
|
||||
}
|
||||
|
||||
public function test_create_all_block_instances() {
|
||||
global $CFG, $PAGE, $DB;
|
||||
|
||||
$this->resetAfterTest();
|
||||
$regionname = 'side-pre';
|
||||
$context = context_system::instance();
|
||||
|
||||
$PAGE->reset_theme_and_output();
|
||||
$CFG->theme = 'boost';
|
||||
|
||||
list($page, $blockmanager) = $this->get_a_page_and_block_manager(array($regionname),
|
||||
$context, 'page-type');
|
||||
$blockmanager->load_blocks();
|
||||
$blockmanager->create_all_block_instances();
|
||||
$blocks = $blockmanager->get_blocks_for_region($regionname);
|
||||
$this->assertEmpty($blocks);
|
||||
// There should be no blocks in the DB.
|
||||
|
||||
$PAGE->reset_theme_and_output();
|
||||
// Change to a theme with undeletable blocks.
|
||||
$CFG->theme = 'clean';
|
||||
|
||||
list($page, $blockmanager) = $this->get_a_page_and_block_manager(array($regionname),
|
||||
$context, 'page-type');
|
||||
$blockmanager->load_blocks();
|
||||
$blockmanager->create_all_block_instances();
|
||||
$blocks = $blockmanager->get_blocks_for_region($regionname);
|
||||
$this->assertCount(2, $blocks);
|
||||
|
||||
$undeletable = block_manager::get_undeletable_block_types();
|
||||
foreach ($undeletable as $blockname) {
|
||||
$instance = $DB->get_record('block_instances', array('blockname' => $blockname));
|
||||
$this->assertEquals(1, $instance->requiredbytheme);
|
||||
}
|
||||
|
||||
// Switch back and those auto blocks should not be returned.
|
||||
$PAGE->reset_theme_and_output();
|
||||
$CFG->theme = 'boost';
|
||||
|
||||
list($page, $blockmanager) = $this->get_a_page_and_block_manager(array($regionname),
|
||||
$context, 'page-type');
|
||||
$blockmanager->load_blocks();
|
||||
$blockmanager->create_all_block_instances();
|
||||
$blocks = $blockmanager->get_blocks_for_region($regionname);
|
||||
$this->assertEmpty($blocks);
|
||||
// But they should exist in the DB.
|
||||
foreach ($undeletable as $blockname) {
|
||||
$count = $DB->count_records('block_instances', array('blockname' => $blockname));
|
||||
$this->assertEquals(1, $count);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -29,7 +29,7 @@
|
||||
|
||||
defined('MOODLE_INTERNAL') || die();
|
||||
|
||||
$version = 2016112200.00; // YYYYMMDD = weekly release date of this DEV branch.
|
||||
$version = 2016112200.02; // YYYYMMDD = weekly release date of this DEV branch.
|
||||
// RR = release increments - 00 in DEV branches.
|
||||
// .XX = incremental changes.
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user