3
3
4
4
namespace Icinga \Controllers ;
5
5
6
+ use DateTime ;
6
7
use Exception ;
7
8
use Icinga \Application \Version ;
9
+ use Icinga \Common \Database ;
10
+ use Icinga \Forms \Security \RoleForm ;
11
+ use Icinga \Model \Role ;
12
+ use Icinga \Util \StringHelper ;
8
13
use InvalidArgumentException ;
9
14
use Icinga \Application \Config ;
10
15
use Icinga \Application \Icinga ;
23
28
use Icinga \Web \Notification ;
24
29
use Icinga \Web \Url ;
25
30
use Icinga \Web \Widget ;
31
+ use ipl \Sql \Connection ;
32
+ use ipl \Sql \Insert ;
33
+ use ipl \Sql \Select ;
34
+ use ipl \Sql \Update ;
26
35
27
36
/**
28
37
* Application and module configuration
29
38
*/
30
39
class ConfigController extends Controller
31
40
{
41
+ use Database;
42
+
32
43
/**
33
44
* Create and return the tabs to display when showing application configuration
34
45
*/
@@ -99,13 +110,21 @@ public function generalAction()
99
110
$ form ->setOnSuccess (function (GeneralConfigForm $ form ) {
100
111
$ config = Config::app ();
101
112
$ useStrictCsp = (bool ) $ config ->get ('security ' , 'use_strict_csp ' , false );
113
+ $ storeRolesInDb = (bool ) $ config ->get ('global ' , 'store_roles_in_db ' , false );
102
114
if ($ form ->onSuccess () === false ) {
103
115
return false ;
104
116
}
105
117
106
118
$ appConfigForm = $ form ->getSubForm ('form_config_general_application ' );
107
- if ($ appConfigForm && (bool ) $ appConfigForm ->getValue ('security_use_strict_csp ' ) !== $ useStrictCsp ) {
108
- $ this ->getResponse ()->setReloadWindow (true );
119
+
120
+ if ($ appConfigForm ) {
121
+ if ((bool ) $ appConfigForm ->getValue ('security_use_strict_csp ' ) !== $ useStrictCsp ) {
122
+ $ this ->getResponse ()->setReloadWindow (true );
123
+ }
124
+
125
+ if (! $ storeRolesInDb && $ appConfigForm ->getValue ('global_store_roles_in_db ' )) {
126
+ $ this ->migrateRolesToFreshDb ();
127
+ }
109
128
}
110
129
})->handleRequest ();
111
130
@@ -114,6 +133,106 @@ public function generalAction()
114
133
$ this ->createApplicationTabs ()->activate ('general ' );
115
134
}
116
135
136
+ /**
137
+ * Migrate roles.ini to database if the latter contains no roles
138
+ */
139
+ private function migrateRolesToFreshDb (): void
140
+ {
141
+ $ roles = Config::app ('roles ' );
142
+ $ now = (new DateTime ())->getTimestamp () * 1000 ;
143
+
144
+ $ this ->getDb ()->transaction (function (Connection $ db ) use ($ roles , $ now ) {
145
+ if (Role::on ($ db )->columns ('id ' )->first ()) {
146
+ return ;
147
+ }
148
+
149
+ foreach ($ roles as $ name => $ role ) {
150
+ $ db ->prepexec (
151
+ (new Insert ())
152
+ ->into ('icingaweb_role ' )
153
+ ->columns (['name ' , 'unrestricted ' , 'ctime ' ])
154
+ ->values ([$ name , $ role ->unrestricted ? 'y ' : 'n ' , $ now ])
155
+ );
156
+
157
+ $ id = $ db ->lastInsertId ();
158
+ $ permissions = StringHelper::trimSplit ($ role ->permissions );
159
+ $ refusals = StringHelper::trimSplit ($ role ->refusals );
160
+ $ permissionsAndRefusals = [];
161
+
162
+ foreach (StringHelper::trimSplit ($ role ->users ) as $ user ) {
163
+ $ db ->prepexec (
164
+ (new Insert ())
165
+ ->into ('icingaweb_role_user ' )
166
+ ->columns (['role_id ' , 'user_name ' ])
167
+ ->values ([$ id , $ user ])
168
+ );
169
+ }
170
+
171
+ foreach (StringHelper::trimSplit ($ role ->groups ) as $ group ) {
172
+ $ db ->prepexec (
173
+ (new Insert ())
174
+ ->into ('icingaweb_role_group ' )
175
+ ->columns (['role_id ' , 'group_name ' ])
176
+ ->values ([$ id , $ group ])
177
+ );
178
+ }
179
+
180
+ foreach ([$ permissions , $ refusals ] as $ permissionsOrRefusals ) {
181
+ foreach ($ permissionsOrRefusals as $ permissionOrRefusal ) {
182
+ $ permissionsAndRefusals [$ permissionOrRefusal ] = ['allowed ' => 'n ' , 'denied ' => 'n ' ];
183
+ }
184
+ }
185
+
186
+ foreach ($ permissions as $ permission ) {
187
+ $ permissionsAndRefusals [$ permission ]['allowed ' ] = 'y ' ;
188
+ }
189
+
190
+ foreach ($ refusals as $ refusal ) {
191
+ $ permissionsAndRefusals [$ refusal ]['denied ' ] = 'y ' ;
192
+ }
193
+
194
+ foreach ($ permissionsAndRefusals as $ permission => $ authz ) {
195
+ $ db ->prepexec (
196
+ (new Insert ())
197
+ ->into ('icingaweb_role_permission ' )
198
+ ->columns (['role_id ' , 'permission ' , 'allowed ' , 'denied ' ])
199
+ ->values ([$ id , $ permission , $ authz ['allowed ' ], $ authz ['denied ' ]])
200
+ );
201
+ }
202
+
203
+ foreach (RoleForm::collectProvidedPrivileges ()[1 ] as $ restrictionList ) {
204
+ foreach ($ restrictionList as $ restriction => $ _ ) {
205
+ if (isset ($ role ->$ restriction )) {
206
+ $ db ->prepexec (
207
+ (new Insert ())
208
+ ->into ('icingaweb_role_restriction ' )
209
+ ->columns (['role_id ' , 'restriction ' , 'filter ' ])
210
+ ->values ([$ id , $ restriction , $ role ->$ restriction ])
211
+ );
212
+ }
213
+ }
214
+ }
215
+ }
216
+
217
+ foreach ($ roles as $ name => $ role ) {
218
+ if (isset ($ role ->parent )) {
219
+ $ db ->prepexec (
220
+ (new Update ())
221
+ ->table ('icingaweb_role ' )
222
+ ->set ([
223
+ 'parent_id ' => (new Select ())
224
+ ->from ('icingaweb_role ' )
225
+ ->where (['name = ? ' => $ role ->parent ])
226
+ ->columns (['id ' ])
227
+ ,
228
+ ])
229
+ ->where (['name = ? ' => $ name ])
230
+ );
231
+ }
232
+ }
233
+ });
234
+ }
235
+
117
236
/**
118
237
* Display the list of all modules
119
238
*/
0 commit comments