Skip to content

Commit

Permalink
If one enables to store roles in the database for the first time, mig…
Browse files Browse the repository at this point in the history
…rate them

This prevents the admin from breaking Icinga Web with one checkbox.
  • Loading branch information
Al2Klimov committed Aug 7, 2024
1 parent 287cfaa commit b786e0c
Showing 1 changed file with 121 additions and 2 deletions.
123 changes: 121 additions & 2 deletions application/controllers/ConfigController.php
Original file line number Diff line number Diff line change
Expand Up @@ -3,8 +3,13 @@

namespace Icinga\Controllers;

use DateTime;
use Exception;
use Icinga\Application\Version;
use Icinga\Common\Database;
use Icinga\Forms\Security\RoleForm;
use Icinga\Model\Role;
use Icinga\Util\StringHelper;
use InvalidArgumentException;
use Icinga\Application\Config;
use Icinga\Application\Icinga;
Expand All @@ -23,12 +28,18 @@
use Icinga\Web\Notification;
use Icinga\Web\Url;
use Icinga\Web\Widget;
use ipl\Sql\Connection;
use ipl\Sql\Insert;
use ipl\Sql\Select;
use ipl\Sql\Update;

/**
* Application and module configuration
*/
class ConfigController extends Controller
{
use Database;

/**
* Create and return the tabs to display when showing application configuration
*/
Expand Down Expand Up @@ -99,13 +110,21 @@ public function generalAction()
$form->setOnSuccess(function (GeneralConfigForm $form) {
$config = Config::app();
$useStrictCsp = (bool) $config->get('security', 'use_strict_csp', false);
$storeRolesInDb = (bool) $config->get('global', 'store_roles_in_db', false);
if ($form->onSuccess() === false) {
return false;
}

$appConfigForm = $form->getSubForm('form_config_general_application');
if ($appConfigForm && (bool) $appConfigForm->getValue('security_use_strict_csp') !== $useStrictCsp) {
$this->getResponse()->setReloadWindow(true);

if ($appConfigForm) {
if ((bool) $appConfigForm->getValue('security_use_strict_csp') !== $useStrictCsp) {
$this->getResponse()->setReloadWindow(true);
}

if (! $storeRolesInDb && $appConfigForm->getValue('global_store_roles_in_db')) {
$this->migrateRolesToFreshDb();
}
}
})->handleRequest();

Expand All @@ -114,6 +133,106 @@ public function generalAction()
$this->createApplicationTabs()->activate('general');
}

/**
* Migrate roles.ini to database if the latter contains no roles
*/
private function migrateRolesToFreshDb(): void
{
$roles = Config::app('roles');
$now = (new DateTime())->getTimestamp() * 1000;

$this->getDb()->transaction(function (Connection $db) use ($roles, $now) {
if (Role::on($db)->columns('id')->first()) {
return;
}

foreach ($roles as $name => $role) {
$db->prepexec(
(new Insert())
->into('icingaweb_role')
->columns(['name', 'unrestricted', 'ctime'])
->values([$name, $role->unrestricted ? 'y' : 'n', $now])
);

$id = $db->lastInsertId();

Check failure on line 157 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 8.2 on ubuntu-latest

Call to an undefined method ipl\Sql\Connection::lastInsertId().

Check failure on line 157 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 7.4 on ubuntu-latest

Call to an undefined method ipl\Sql\Connection::lastInsertId().

Check failure on line 157 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 7.3 on ubuntu-latest

Call to an undefined method ipl\Sql\Connection::lastInsertId().

Check failure on line 157 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 8.3 on ubuntu-latest

Call to an undefined method ipl\Sql\Connection::lastInsertId().

Check failure on line 157 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 8.0 on ubuntu-latest

Call to an undefined method ipl\Sql\Connection::lastInsertId().

Check failure on line 157 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 7.2 on ubuntu-latest

Call to an undefined method ipl\Sql\Connection::lastInsertId().

Check failure on line 157 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 8.1 on ubuntu-latest

Call to an undefined method ipl\Sql\Connection::lastInsertId().
$permissions = StringHelper::trimSplit($role->permissions);

Check failure on line 158 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 8.2 on ubuntu-latest

Parameter #1 $value of static method Icinga\Util\StringHelper::trimSplit() expects string, mixed given.

Check failure on line 158 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 7.4 on ubuntu-latest

Parameter #1 $value of static method Icinga\Util\StringHelper::trimSplit() expects string, mixed given.

Check failure on line 158 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 7.3 on ubuntu-latest

Parameter #1 $value of static method Icinga\Util\StringHelper::trimSplit() expects string, mixed given.

Check failure on line 158 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 8.3 on ubuntu-latest

Parameter #1 $value of static method Icinga\Util\StringHelper::trimSplit() expects string, mixed given.

Check failure on line 158 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 8.0 on ubuntu-latest

Parameter #1 $value of static method Icinga\Util\StringHelper::trimSplit() expects string, mixed given.

Check failure on line 158 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 7.2 on ubuntu-latest

Parameter #1 $value of static method Icinga\Util\StringHelper::trimSplit() expects string, mixed given.

Check failure on line 158 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 8.1 on ubuntu-latest

Parameter #1 $value of static method Icinga\Util\StringHelper::trimSplit() expects string, mixed given.
$refusals = StringHelper::trimSplit($role->refusals);

Check failure on line 159 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 8.2 on ubuntu-latest

Parameter #1 $value of static method Icinga\Util\StringHelper::trimSplit() expects string, mixed given.

Check failure on line 159 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 7.4 on ubuntu-latest

Parameter #1 $value of static method Icinga\Util\StringHelper::trimSplit() expects string, mixed given.

Check failure on line 159 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 7.3 on ubuntu-latest

Parameter #1 $value of static method Icinga\Util\StringHelper::trimSplit() expects string, mixed given.

Check failure on line 159 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 8.3 on ubuntu-latest

Parameter #1 $value of static method Icinga\Util\StringHelper::trimSplit() expects string, mixed given.

Check failure on line 159 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 8.0 on ubuntu-latest

Parameter #1 $value of static method Icinga\Util\StringHelper::trimSplit() expects string, mixed given.

Check failure on line 159 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 7.2 on ubuntu-latest

Parameter #1 $value of static method Icinga\Util\StringHelper::trimSplit() expects string, mixed given.

Check failure on line 159 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 8.1 on ubuntu-latest

Parameter #1 $value of static method Icinga\Util\StringHelper::trimSplit() expects string, mixed given.
$permissionsAndRefusals = [];

foreach (StringHelper::trimSplit($role->users) as $user) {

Check failure on line 162 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 8.2 on ubuntu-latest

Parameter #1 $value of static method Icinga\Util\StringHelper::trimSplit() expects string, mixed given.

Check failure on line 162 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 7.4 on ubuntu-latest

Parameter #1 $value of static method Icinga\Util\StringHelper::trimSplit() expects string, mixed given.

Check failure on line 162 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 7.3 on ubuntu-latest

Parameter #1 $value of static method Icinga\Util\StringHelper::trimSplit() expects string, mixed given.

Check failure on line 162 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 8.3 on ubuntu-latest

Parameter #1 $value of static method Icinga\Util\StringHelper::trimSplit() expects string, mixed given.

Check failure on line 162 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 8.0 on ubuntu-latest

Parameter #1 $value of static method Icinga\Util\StringHelper::trimSplit() expects string, mixed given.

Check failure on line 162 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 7.2 on ubuntu-latest

Parameter #1 $value of static method Icinga\Util\StringHelper::trimSplit() expects string, mixed given.

Check failure on line 162 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 8.1 on ubuntu-latest

Parameter #1 $value of static method Icinga\Util\StringHelper::trimSplit() expects string, mixed given.
$db->prepexec(
(new Insert())
->into('icingaweb_role_user')
->columns(['role_id', 'user_name'])
->values([$id, $user])
);
}

foreach (StringHelper::trimSplit($role->groups) as $group) {

Check failure on line 171 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 8.2 on ubuntu-latest

Parameter #1 $value of static method Icinga\Util\StringHelper::trimSplit() expects string, mixed given.

Check failure on line 171 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 7.4 on ubuntu-latest

Parameter #1 $value of static method Icinga\Util\StringHelper::trimSplit() expects string, mixed given.

Check failure on line 171 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 7.3 on ubuntu-latest

Parameter #1 $value of static method Icinga\Util\StringHelper::trimSplit() expects string, mixed given.

Check failure on line 171 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 8.3 on ubuntu-latest

Parameter #1 $value of static method Icinga\Util\StringHelper::trimSplit() expects string, mixed given.

Check failure on line 171 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 8.0 on ubuntu-latest

Parameter #1 $value of static method Icinga\Util\StringHelper::trimSplit() expects string, mixed given.

Check failure on line 171 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 7.2 on ubuntu-latest

Parameter #1 $value of static method Icinga\Util\StringHelper::trimSplit() expects string, mixed given.

Check failure on line 171 in application/controllers/ConfigController.php

View workflow job for this annotation

GitHub Actions / phpstan / Static analysis with phpstan and php 8.1 on ubuntu-latest

Parameter #1 $value of static method Icinga\Util\StringHelper::trimSplit() expects string, mixed given.
$db->prepexec(
(new Insert())
->into('icingaweb_role_group')
->columns(['role_id', 'group_name'])
->values([$id, $group])
);
}

foreach ([$permissions, $refusals] as $permissionsOrRefusals) {
foreach ($permissionsOrRefusals as $permissionOrRefusal) {
$permissionsAndRefusals[$permissionOrRefusal] = ['allowed' => 'n', 'denied' => 'n'];
}
}

foreach ($permissions as $permission) {
$permissionsAndRefusals[$permission]['allowed'] = 'y';
}

foreach ($refusals as $refusal) {
$permissionsAndRefusals[$refusal]['denied'] = 'y';
}

foreach ($permissionsAndRefusals as $permission => $authz) {
$db->prepexec(
(new Insert())
->into('icingaweb_role_permission')
->columns(['role_id', 'permission', 'allowed', 'denied'])
->values([$id, $permission, $authz['allowed'], $authz['denied']])
);
}

foreach (RoleForm::collectProvidedPrivileges()[1] as $restrictionList) {
foreach ($restrictionList as $restriction => $_) {
if (isset($role->$restriction)) {
$db->prepexec(
(new Insert())
->into('icingaweb_role_restriction')
->columns(['role_id', 'restriction', 'filter'])
->values([$id, $restriction, $role->$restriction])
);
}
}
}
}

foreach ($roles as $name => $role) {
if (isset($role->parent)) {
$db->prepexec(
(new Update())
->table('icingaweb_role')
->set([
'parent_id' => (new Select())
->from('icingaweb_role')
->where(['name = ?' => $role->parent])
->columns(['id'])
,
])
->where(['name = ?' => $name])
);
}
}
});
}

/**
* Display the list of all modules
*/
Expand Down

0 comments on commit b786e0c

Please sign in to comment.