Skip to content

Commit

Permalink
MDL-64777 analytics: Add ability to restore missing default models
Browse files Browse the repository at this point in the history
The patch introduces a new page restoredefault.php that allows the user
to select missing models to be restored.
  • Loading branch information
mudrd8mz committed Apr 15, 2019
1 parent 7dba0c2 commit 76ef661
Show file tree
Hide file tree
Showing 8 changed files with 593 additions and 6 deletions.
29 changes: 27 additions & 2 deletions admin/tool/analytics/classes/output/models_list.php
Expand Up @@ -62,8 +62,33 @@ public function export_for_template(\renderer_base $output) {
global $PAGE;

$data = new \stdClass();
$data->importmodelurl = new \moodle_url('/admin/tool/analytics/importmodel.php');
$data->createmodelurl = new \moodle_url('/admin/tool/analytics/createmodel.php');

$newmodelmenu = new \action_menu();
$newmodelmenu->set_menu_trigger(get_string('newmodel', 'tool_analytics'), 'btn btn-default');
$newmodelmenu->set_alignment(\action_menu::TL, \action_menu::BL);

$newmodelmenu->add(new \action_menu_link(
new \moodle_url('/admin/tool/analytics/createmodel.php'),
new \pix_icon('i/edit', ''),
get_string('createmodel', 'tool_analytics'),
false
));

$newmodelmenu->add(new \action_menu_link(
new \moodle_url('/admin/tool/analytics/importmodel.php'),
new \pix_icon('i/import', ''),
get_string('importmodel', 'tool_analytics'),
false
));

$newmodelmenu->add(new \action_menu_link(
new \moodle_url('/admin/tool/analytics/restoredefault.php'),
new \pix_icon('i/reload', ''),
get_string('restoredefault', 'tool_analytics'),
false
));

$data->newmodelmenu = $newmodelmenu->export_for_template($output);

$onlycli = get_config('analytics', 'onlycli');
if ($onlycli === false) {
Expand Down
142 changes: 142 additions & 0 deletions admin/tool/analytics/classes/output/restorable_models.php
@@ -0,0 +1,142 @@
<?php
// This file is part of Moodle - https://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/>.

/**
* Provides {@link \tool_analytics\output\restorable_models} class.
*
* @package tool_analytics
* @category output
* @copyright 2019 David Mudrák <david@moodle.com>
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/

namespace tool_analytics\output;

defined('MOODLE_INTERNAL') || die();

/**
* Represents the list of default models that can be eventually restored.
*
* @copyright 2019 David Mudrák <david@moodle.com>
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
class restorable_models implements \renderable, \templatable {

/** @var array */
protected $models;

/**
* Instantiate an object of this class.
*
* @param array $models List of models as returned by {@link \core_analytics\manager::load_default_models_for_all_components()}
*/
public function __construct(array $models) {

$this->models = $models;
}

/**
* Export the list of models to be rendered.
*
* @param renderer_base $output
* @return string
*/
public function export_for_template(\renderer_base $output) {

$components = [];

foreach ($this->models as $componentname => $modelslist) {
$component = [
'name' => $this->component_name($componentname),
'component' => $componentname,
'models' => [],
];

foreach ($modelslist as $definition) {
list($target, $indicators) = \core_analytics\manager::get_declared_target_and_indicators_instances($definition);

if (\core_analytics\model::exists($target, $indicators)) {
continue;
}

$targetnamelangstring = $target->get_name();

$model = [
'defid' => \core_analytics\manager::model_declaration_identifier($definition),
'targetname' => $targetnamelangstring,
'targetclass' => $definition['target'],
'indicatorsnum' => count($definition['indicators']),
'indicators' => [],
];

if (get_string_manager()->string_exists($targetnamelangstring->get_identifier().'_help',
$targetnamelangstring->get_component())) {
$helpicon = new \help_icon($targetnamelangstring->get_identifier(), $targetnamelangstring->get_component());
$model['targethelp'] = $helpicon->export_for_template($output);
}

foreach ($indicators as $indicator) {
$indicatornamelangstring = $indicator->get_name();
$indicatordata = [
'name' => $indicatornamelangstring,
'classname' => $indicator->get_id(),
];

if (get_string_manager()->string_exists($indicatornamelangstring->get_identifier().'_help',
$indicatornamelangstring->get_component())) {
$helpicon = new \help_icon($indicatornamelangstring->get_identifier(),
$indicatornamelangstring->get_component());
$indicatordata['indicatorhelp'] = $helpicon->export_for_template($output);
}

$model['indicators'][] = $indicatordata;
}

$component['models'][] = $model;
}

if (!empty($component['models'])) {
$components[] = $component;
}
}

$result = [
'hasdata' => !empty($components),
'components' => array_values($components),
'submiturl' => new \moodle_url('/admin/tool/analytics/restoredefault.php'),
'backurl' => new \moodle_url('/admin/tool/analytics/index.php'),
'sesskey' => sesskey(),
];

return $result;
}

/**
* Return a human readable name for the given frankenstyle component.
*
* @param string $component Frankenstyle component such as 'core', 'core_analytics' or 'mod_workshop'
* @return string Human readable name of the component
*/
protected function component_name(string $component): string {

if ($component === 'core' || strpos($component, 'core_')) {
return get_string('componentcore', 'tool_analytics');

} else {
return get_string('pluginname', $component);
}
}
}
12 changes: 12 additions & 0 deletions admin/tool/analytics/lang/en/tool_analytics.php
Expand Up @@ -36,6 +36,10 @@
$string['clienablemodel'] = 'You can enable the model by selecting a time-splitting method by its ID. Note that you can also enable it later using the web interface (\'none\' to exit).';
$string['clievaluationandpredictions'] = 'A scheduled task iterates through enabled models and gets predictions. Models evaluation via the web interface is disabled. You can allow these processes to be executed manually via the web interface by disabling the <a href="{$a}">\'onlycli\'</a> analytics setting.';
$string['clievaluationandpredictionsnoadmin'] = 'A scheduled task iterates through enabled models and gets predictions. Models evaluation via the web interface is disabled. It may be enabled by a site administrator.';
$string['component'] = 'Component';
$string['componentcore'] = 'Core';
$string['componentselect'] = 'Select all models provided by the component \'{$a}\'';
$string['componentselectnone'] = 'Unselect all';
$string['createmodel'] = 'Create model';
$string['currenttimesplitting'] = 'Current time-splitting method';
$string['delete'] = 'Delete';
Expand Down Expand Up @@ -81,6 +85,7 @@
$string['indicators'] = 'Indicators';
$string['indicators_help'] = 'The indicators are what you think will lead to an accurate prediction of the target.';
$string['indicators_link'] = 'Indicators';
$string['indicatorsnum'] = 'Number of indicators: {$a}';
$string['info'] = 'Info';
$string['ignoreversionmismatches'] = 'Ignore version mismatches';
$string['ignoreversionmismatchescheckbox'] = 'Ignore the differences between this site version and the original site version.';
Expand All @@ -98,6 +103,7 @@
$string['modelinvalidanalysables'] = 'Invalid analysable elements for "{$a}" model';
$string['modelresults'] = '{$a} results';
$string['modeltimesplitting'] = 'Time splitting';
$string['newmodel'] = 'New model';
$string['nextpage'] = 'Next page';
$string['nodatatoevaluate'] = 'There is no data to evaluate the model';
$string['nodatatopredict'] = 'No new elements to get predictions for';
Expand All @@ -110,6 +116,12 @@
$string['predictorresultsin'] = 'Predictor logged information in {$a} directory';
$string['predictionprocessfinished'] = 'Prediction process finished';
$string['previouspage'] = 'Previous page';
$string['restoredefault'] = 'Restore default models';
$string['restoredefaultempty'] = 'Please select models to be restored.';
$string['restoredefaultinfo'] = 'These default models are missing or have changed since being installed. You can restore selected default models.';
$string['restoredefaultnone'] = 'All default models provided by the Moodle core and installed plugins have been already created. No new models were found, there is nothing to restore.';
$string['restoredefaultsome'] = 'Succesfully re-created {$a->count} new model(s).';
$string['restoredefaultsubmit'] = 'Restore selected';
$string['samestartdate'] = 'Current start date is good';
$string['sameenddate'] = 'Current end date is good';
$string['selecttimesplittingforevaluation'] = 'Select the time-splitting method you want to use to evaluate the model configuration.';
Expand Down
79 changes: 79 additions & 0 deletions admin/tool/analytics/restoredefault.php
@@ -0,0 +1,79 @@
<?php
// This file is part of Moodle - https://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/>.

/**
* Check and create missing default prediction models.
*
* @package tool_analytics
* @copyright 2019 David Mudrák <david@moodle.com>
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/

require_once(__DIR__ . '/../../../config.php');

require_login();
\core_analytics\manager::check_can_manage_models();

$confirmed = optional_param('confirmed', false, PARAM_BOOL);
$restoreids = optional_param_array('restoreid', [], PARAM_ALPHANUM);

$returnurl = new \moodle_url('/admin/tool/analytics/index.php');
$myurl = new \moodle_url('/admin/tool/analytics/restoredefault.php');

\tool_analytics\output\helper::set_navbar(get_string('restoredefault', 'tool_analytics'), $myurl);

if (data_submitted()) {
require_sesskey();

if (empty($restoreids)) {
$message = get_string('restoredefaultempty', 'tool_analytics');
$type = \core\output\notification::NOTIFY_WARNING;
redirect($myurl, $message, null, $type);
}

$numcreated = 0;

foreach (\core_analytics\manager::load_default_models_for_all_components() as $componentname => $modelslist) {
foreach ($modelslist as $definition) {
if (!in_array(\core_analytics\manager::model_declaration_identifier($definition), $restoreids)) {
// This model has not been selected by the user.
continue;
}

list($target, $indicators) = \core_analytics\manager::get_declared_target_and_indicators_instances($definition);

if (\core_analytics\model::exists($target, $indicators)) {
// This model exists (normally this should not happen as we do not show such models in the UI to select).
continue;
}

\core_analytics\manager::create_declared_model($definition);
$numcreated++;
}
}

$message = get_string('restoredefaultsome', 'tool_analytics', ['count' => $numcreated]);
$type = \core\output\notification::NOTIFY_SUCCESS;

redirect($returnurl, $message, null, $type);
}

$models = \core_analytics\manager::load_default_models_for_all_components();
$ui = new \tool_analytics\output\restorable_models($models);

echo $OUTPUT->header();
echo $PAGE->get_renderer('tool_analytics')->render($ui);
echo $OUTPUT->footer();
5 changes: 3 additions & 2 deletions admin/tool/analytics/templates/models_list.mustache
Expand Up @@ -111,8 +111,9 @@

<div class="box">
<div class="top-nav d-flex">
<a href="{{createmodelurl}}" class="btn btn-secondary mr-2">{{#str}}createmodel, tool_analytics{{/str}}</a>
<a href="{{importmodelurl}}" class="btn btn-secondary">{{#str}}importmodel, tool_analytics{{/str}}</a>
{{#newmodelmenu}}
{{>core/action_menu}}
{{/newmodelmenu}}
</div>
<table class="generaltable fullwidth">
<caption>{{#str}}analyticmodels, tool_analytics{{/str}}</caption>
Expand Down

0 comments on commit 76ef661

Please sign in to comment.