dolibarr  13.0.2
perms.php
Go to the documentation of this file.
1 <?php
2 /* Copyright (C) 2002-2005 Rodolphe Quiedeville <rodolphe@quiedeville.org>
3  * Copyright (C) 2002-2003 Jean-Louis Bergamo <jlb@j1b.org>
4  * Copyright (C) 2004-2020 Laurent Destailleur <eldy@users.sourceforge.net>
5  * Copyright (C) 2004 Eric Seigne <eric.seigne@ryxeo.com>
6  * Copyright (C) 2005-2017 Regis Houssin <regis.houssin@inodbox.com>
7  * Copyright (C) 2012 Juanjo Menent <jmenent@2byte.es>
8  * Copyright (C) 2020 Tobias Sekan <tobias.sekan@startmail.com>
9  *
10  * This program is free software; you can redistribute it and/or modify
11  * it under the terms of the GNU General Public License as published by
12  * the Free Software Foundation; either version 3 of the License, or
13  * (at your option) any later version.
14  *
15  * This program is distributed in the hope that it will be useful,
16  * but WITHOUT ANY WARRANTY; without even the implied warranty of
17  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18  * GNU General Public License for more details.
19  *
20  * You should have received a copy of the GNU General Public License
21  * along with this program. If not, see <https://www.gnu.org/licenses/>.
22  */
23 
29 if (!defined('CSRFCHECK_WITH_TOKEN')) define('CSRFCHECK_WITH_TOKEN', '1'); // Force use of CSRF protection with tokens even for GET
30 
31 require '../main.inc.php';
32 require_once DOL_DOCUMENT_ROOT.'/core/lib/usergroups.lib.php';
33 require_once DOL_DOCUMENT_ROOT.'/core/lib/functions2.lib.php';
34 require_once DOL_DOCUMENT_ROOT.'/core/lib/admin.lib.php';
35 
36 // Load translation files required by page
37 $langs->loadLangs(array('users', 'admin'));
38 
39 $id = GETPOST('id', 'int');
40 $action = GETPOST('action', 'aZ09');
41 $confirm = GETPOST('confirm', 'alpha');
42 $module = GETPOST('module', 'alpha');
43 $rights = GETPOST('rights', 'int');
44 $contextpage = GETPOST('contextpage', 'aZ') ?GETPOST('contextpage', 'aZ') : 'userperms'; // To manage different context of search
45 
46 if (!isset($id) || empty($id)) accessforbidden();
47 
48 // Define if user can read permissions
49 $canreaduser = ($user->admin || $user->rights->user->user->lire);
50 // Define if user can modify other users and permissions
51 $caneditperms = ($user->admin || $user->rights->user->user->creer);
52 // Advanced permissions
53 if (!empty($conf->global->MAIN_USE_ADVANCED_PERMS))
54 {
55  $canreaduser = ($user->admin || ($user->rights->user->user->lire && $user->rights->user->user_advance->readperms));
56  $caneditselfperms = ($user->id == $id && $user->rights->user->self_advance->writeperms);
57  $caneditperms = (($caneditperms || $caneditselfperms) ? 1 : 0);
58 }
59 
60 // Security check
61 $socid = 0;
62 if (isset($user->socid) && $user->socid > 0) $socid = $user->socid;
63 $feature2 = (($socid && $user->rights->user->self->creer) ? '' : 'user');
64 // A user can always read its own card if not advanced perms enabled, or if he has advanced perms, except for admin
65 if ($user->id == $id && (!empty($conf->global->MAIN_USE_ADVANCED_PERMS) && empty($user->rights->user->self_advance->readperms) && empty($user->admin)))
66 {
68 }
69 
70 $result = restrictedArea($user, 'user', $id, 'user&user', $feature2);
71 if ($user->id <> $id && !$canreaduser) accessforbidden();
72 
73 $object = new User($db);
74 $object->fetch($id, '', '', 1);
75 $object->getrights();
76 
77 $entity = $conf->entity;
78 
79 // Initialize technical object to manage hooks of page. Note that conf->hooks_modules contains array of hook context
80 $hookmanager->initHooks(array('usercard', 'userperms', 'globalcard'));
81 
82 
83 /*
84  * Actions
85  */
86 
87 $parameters = array('id'=>$socid);
88 $reshook = $hookmanager->executeHooks('doActions', $parameters, $object, $action); // Note that $action and $object may have been modified by some hooks
89 if ($reshook < 0) setEventMessages($hookmanager->error, $hookmanager->errors, 'errors');
90 
91 if (empty($reshook)) {
92  if ($action == 'addrights' && $caneditperms && $confirm == 'yes') {
93  $edituser = new User($db);
94  $edituser->fetch($object->id);
95  $result = $edituser->addrights($rights, $module, '', $entity);
96  if ($result < 0)
97  {
98  setEventMessages($edituser->error, $edituser->errors, 'errors');
99  }
100 
101  // If we are changing our own permissions, we reload
102  if ($object->id == $user->id) {
103  $user->clearrights();
104  $user->getrights();
105  $menumanager->loadMenu();
106  }
107 
108  $object->clearrights();
109  $object->getrights();
110  }
111 
112  if ($action == 'delrights' && $caneditperms && $confirm == 'yes') {
113  $edituser = new User($db);
114  $edituser->fetch($object->id);
115  $result = $edituser->delrights($rights, $module, '', $entity);
116  if ($result < 0)
117  {
118  setEventMessages($edituser->error, $edituser->errors, 'errors');
119  }
120 
121  // If we are changing our own permissions, we reload
122  if ($object->id == $user->id) {
123  $user->clearrights();
124  $user->getrights();
125  $menumanager->loadMenu();
126  }
127 
128  $object->clearrights();
129  $object->getrights();
130  }
131 }
132 
133 
134 /*
135  * View
136  */
137 
138 $form = new Form($db);
139 
140 llxHeader('', $langs->trans("Permissions"));
141 
142 $head = user_prepare_head($object);
143 
144 $title = $langs->trans("User");
145 print dol_get_fiche_head($head, 'rights', $title, -1, 'user');
146 
147 
148 $db->begin();
149 
150 // Search all modules with permission and reload permissions def.
151 $modules = array();
152 $modulesdir = dolGetModulesDirs();
153 
154 foreach ($modulesdir as $dir)
155 {
156  $handle = @opendir(dol_osencode($dir));
157  if (is_resource($handle))
158  {
159  while (($file = readdir($handle)) !== false)
160  {
161  if (is_readable($dir.$file) && substr($file, 0, 3) == 'mod' && substr($file, dol_strlen($file) - 10) == '.class.php')
162  {
163  $modName = substr($file, 0, dol_strlen($file) - 10);
164 
165  if ($modName)
166  {
167  include_once $dir.$file;
168  $objMod = new $modName($db);
169 
170  // Load all lang files of module
171  if (isset($objMod->langfiles) && is_array($objMod->langfiles))
172  {
173  foreach ($objMod->langfiles as $domain)
174  {
175  $langs->load($domain);
176  }
177  }
178  // Load all permissions
179  if ($objMod->rights_class)
180  {
181  $ret = $objMod->insert_permissions(0, $entity);
182  $modules[$objMod->rights_class] = $objMod;
183  //print "modules[".$objMod->rights_class."]=$objMod;";
184  }
185  }
186  }
187  }
188  }
189 }
190 
191 $db->commit();
192 
193 // Read permissions of user
194 $permsuser = array();
195 
196 $sql = "SELECT DISTINCT ur.fk_id";
197 $sql .= " FROM ".MAIN_DB_PREFIX."user_rights as ur";
198 $sql .= " WHERE ur.entity = ".$entity;
199 $sql .= " AND ur.fk_user = ".$object->id;
200 
201 dol_syslog("get user perms", LOG_DEBUG);
202 $result = $db->query($sql);
203 if ($result)
204 {
205  $num = $db->num_rows($result);
206  $i = 0;
207  while ($i < $num)
208  {
209  $obj = $db->fetch_object($result);
210  array_push($permsuser, $obj->fk_id);
211  $i++;
212  }
213  $db->free($result);
214 } else {
215  dol_print_error($db);
216 }
217 
218 // Lecture des droits groupes
219 $permsgroupbyentity = array();
220 
221 $sql = "SELECT DISTINCT gr.fk_id, gu.entity";
222 $sql .= " FROM ".MAIN_DB_PREFIX."usergroup_rights as gr,";
223 $sql .= " ".MAIN_DB_PREFIX."usergroup_user as gu";
224 $sql .= " WHERE gr.entity = ".$entity;
225 $sql .= " AND gr.fk_usergroup = gu.fk_usergroup";
226 $sql .= " AND gu.fk_user = ".$object->id;
227 
228 dol_syslog("get user perms", LOG_DEBUG);
229 $result = $db->query($sql);
230 if ($result)
231 {
232  $num = $db->num_rows($result);
233  $i = 0;
234  while ($i < $num)
235  {
236  $obj = $db->fetch_object($result);
237  if (!isset($permsgroupbyentity[$obj->entity]))
238  $permsgroupbyentity[$obj->entity] = array();
239  array_push($permsgroupbyentity[$obj->entity], $obj->fk_id);
240  $i++;
241  }
242  $db->free($result);
243 } else {
244  dol_print_error($db);
245 }
246 
247 
248 /*
249  * Part to add/remove permissions
250  */
251 
252 $linkback = '';
253 
254 if ($user->rights->user->user->lire || $user->admin) {
255  $linkback = '<a href="'.DOL_URL_ROOT.'/user/list.php?restore_lastsearch_values=1">'.$langs->trans("BackToList").'</a>';
256 }
257 
258 dol_banner_tab($object, 'id', $linkback, $user->rights->user->user->lire || $user->admin);
259 
260 
261 print '<div class="underbanner clearboth"></div>';
262 
263 if ($user->admin) print info_admin($langs->trans("WarningOnlyPermissionOfActivatedModules"));
264 // Show warning about external users
265 if (empty($user->socid)) print info_admin(showModulesExludedForExternal($modules))."\n";
266 
267 $parameters = array('permsgroupbyentity'=>$permsgroupbyentity);
268 $reshook = $hookmanager->executeHooks('insertExtraHeader', $parameters, $object, $action); // Note that $action and $object may have been modified by some hooks
269 if ($reshook < 0) setEventMessages($hookmanager->error, $hookmanager->errors, 'errors');
270 
271 
272 print "\n";
273 print '<div class="div-table-responsive-no-min">';
274 print '<table class="noborder centpercent">';
275 
276 print '<tr class="liste_titre">';
277 print '<td>'.$langs->trans("Module").'</td>';
278 if (($caneditperms && empty($objMod->rights_admin_allowed)) || empty($object->admin))
279 {
280  if ($caneditperms)
281  {
282  print '<td class="center nowrap">';
283  print '<a class="reposition commonlink" title="'.dol_escape_htmltag($langs->trans("All")).'" alt="'.dol_escape_htmltag($langs->trans("All")).'" href="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'&amp;action=addrights&amp;entity='.$entity.'&amp;module=allmodules&amp;confirm=yes&amp;token='.newToken().'">'.$langs->trans("All")."</a>";
284  print ' / ';
285  print '<a class="reposition commonlink" title="'.dol_escape_htmltag($langs->trans("None")).'" alt="'.dol_escape_htmltag($langs->trans("None")).'" href="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'&amp;action=delrights&amp;entity='.$entity.'&amp;module=allmodules&amp;confirm=yes&amp;token='.newToken().'">'.$langs->trans("None")."</a>";
286  print '</td>';
287  }
288  print '<td class="center" width="24">&nbsp;</td>';
289 }
290 print '<td>'.$langs->trans("Permissions").'</td>';
291 if ($user->admin) print '<td class="right">'.$langs->trans("ID").'</td>';
292 print '</tr>'."\n";
293 
294 //print "xx".$conf->global->MAIN_USE_ADVANCED_PERMS;
295 $sql = "SELECT r.id, r.libelle as label, r.module, r.perms, r.subperms, r.module_position";
296 $sql .= " FROM ".MAIN_DB_PREFIX."rights_def as r";
297 $sql .= " WHERE r.libelle NOT LIKE 'tou%'"; // On ignore droits "tous"
298 $sql .= " AND r.entity = ".$entity;
299 if (empty($conf->global->MAIN_USE_ADVANCED_PERMS)) $sql .= " AND r.perms NOT LIKE '%_advance'"; // Hide advanced perms if option is not enabled
300 $sql .= " ORDER BY r.family_position, r.module_position, r.module, r.id";
301 
302 $result = $db->query($sql);
303 if ($result)
304 {
305  $num = $db->num_rows($result);
306  $i = 0;
307  $oldmod = '';
308 
309  while ($i < $num)
310  {
311  $obj = $db->fetch_object($result);
312 
313  // If line is for a module that doe snot existe anymore (absent of includes/module), we ignore it
314  if (empty($modules[$obj->module]))
315  {
316  $i++;
317  continue;
318  }
319 
320  // Save field module_position in database if value is still zero
321  if (empty($obj->module_position))
322  {
323  if (is_object($modules[$obj->module]) && ($modules[$obj->module]->module_position > 0))
324  {
325  // TODO Define familyposition
326  $family = $modules[$obj->module]->family_position;
327  $familyposition = 0;
328  $sqlupdate = 'UPDATE '.MAIN_DB_PREFIX."rights_def SET module_position = ".((int) $modules[$obj->module]->module_position).",";
329  $sqlupdate .= " family_position = ".((int) $familyposition);
330  $sqlupdate .= " WHERE module_position = 0 AND module = '".$db->escape($obj->module)."'";
331  $db->query($sqlupdate);
332  }
333  }
334 
335  if (isset($obj->module) && ($oldmod <> $obj->module))
336  {
337  $oldmod = $obj->module;
338 
339  // Break detected, we get objMod
340  $objMod = $modules[$obj->module];
341  $picto = ($objMod->picto ? $objMod->picto : 'generic');
342 
343  // Show break line
344  print '<tr class="oddeven trforbreak">';
345  print '<td class="maxwidthonsmartphone tdoverflowonsmartphone">';
346  print img_object('', $picto, 'class="pictoobjectwidth paddingright"').' '.$objMod->getName();
347  print '<a name="'.$objMod->getName().'"></a>';
348  print '</td>';
349  if (($caneditperms && empty($objMod->rights_admin_allowed)) || empty($object->admin))
350  {
351  if ($caneditperms)
352  {
353  print '<td class="center nowrap">';
354  print '<a class="reposition" title="'.dol_escape_htmltag($langs->trans("All")).'" alt="'.dol_escape_htmltag($langs->trans("All")).'" href="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'&amp;action=addrights&amp;entity='.$entity.'&amp;module='.$obj->module.'&amp;confirm=yes&amp;token='.newToken().'">'.$langs->trans("All")."</a>";
355  print ' / ';
356  print '<a class="reposition" title="'.dol_escape_htmltag($langs->trans("None")).'" alt="'.dol_escape_htmltag($langs->trans("None")).'" href="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'&amp;action=delrights&amp;entity='.$entity.'&amp;module='.$obj->module.'&amp;confirm=yes&amp;token='.newToken().'">'.$langs->trans("None")."</a>";
357  print '</td>';
358  }
359  print '<td>&nbsp;</td>';
360  } else {
361  if ($caneditperms)
362  {
363  print '<td>&nbsp;</td>';
364  }
365  print '<td>&nbsp;</td>';
366  }
367  print '<td>&nbsp;</td>';
368 
369  // Permission id
370  if ($user->admin) print '<td class="right"></td>';
371 
372  print '</tr>'."\n";
373  }
374 
375  print '<!-- '.$obj->module.'->'.$obj->perms.($obj->subperms ? '->'.$obj->subperms : '').' -->'."\n";
376  print '<tr class="oddeven">';
377 
378  // Picto and label of module
379  print '<td class="maxwidthonsmartphone tdoverflowonsmartphone">';
380  //print img_object('', $picto, 'class="pictoobjectwidth"').' '.$objMod->getName();
381  print '</td>';
382 
383  // Permission and tick
384  if (!empty($object->admin) && !empty($objMod->rights_admin_allowed)) // Permission granted because admin
385  {
386  if ($caneditperms)
387  {
388  print '<td class="center">'.img_picto($langs->trans("Administrator"), 'star').'</td>';
389  }
390  print '<td class="center nowrap">';
391  print img_picto($langs->trans("Active"), 'tick');
392  print '</td>';
393  } elseif (in_array($obj->id, $permsuser)) // Permission granted by user
394  {
395  if ($caneditperms)
396  {
397  print '<td class="center"><a class="reposition" href="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'&amp;action=delrights&amp;entity='.$entity.'&amp;rights='.$obj->id.'&amp;confirm=yes&amp;token='.newToken().'">';
398  //print img_edit_remove($langs->trans("Remove"));
399  print img_picto($langs->trans("Remove"), 'switch_on');
400  print '</a></td>';
401  }
402  print '<td class="center nowrap">';
403  print img_picto($langs->trans("Active"), 'tick');
404  print '</td>';
405  } elseif (is_array($permsgroupbyentity[$entity]))
406  {
407  if (in_array($obj->id, $permsgroupbyentity[$entity])) // Permission granted by group
408  {
409  if ($caneditperms)
410  {
411  print '<td class="center">';
412  print $form->textwithtooltip($langs->trans("Inherited"), $langs->trans("PermissionInheritedFromAGroup"));
413  print '</td>';
414  }
415  print '<td class="center nowrap">';
416  print img_picto($langs->trans("Active"), 'tick');
417  print '</td>';
418  } else {
419  // Do not own permission
420  if ($caneditperms)
421  {
422  print '<td class="center"><a class="reposition" href="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'&amp;action=addrights&amp;entity='.$entity.'&amp;rights='.$obj->id.'&amp;confirm=yes&amp;token='.newToken().'">';
423  //print img_edit_add($langs->trans("Add"));
424  print img_picto($langs->trans("Add"), 'switch_off');
425  print '</a></td>';
426  }
427  print '<td>&nbsp</td>';
428  }
429  } else {
430  // Do not own permission
431  if ($caneditperms)
432  {
433  print '<td class="center"><a class="reposition" href="'.$_SERVER["PHP_SELF"].'?id='.$object->id.'&amp;action=addrights&amp;entity='.$entity.'&amp;rights='.$obj->id.'&amp;confirm=yes&amp;token='.newToken().'">';
434  //print img_edit_add($langs->trans("Add"));
435  print img_picto($langs->trans("Add"), 'switch_off');
436  print '</a></td>';
437  }
438  print '<td>&nbsp</td>';
439  }
440 
441  // Label of permission
442  $permlabel = (!empty($conf->global->MAIN_USE_ADVANCED_PERMS) && ($langs->trans("PermissionAdvanced".$obj->id) != ("PermissionAdvanced".$obj->id)) ? $langs->trans("PermissionAdvanced".$obj->id) : (($langs->trans("Permission".$obj->id) != ("Permission".$obj->id)) ? $langs->trans("Permission".$obj->id) : $langs->trans($obj->label)));
443  print '<td class="maxwidthonsmartphone">';
444  print $permlabel;
445  if (!empty($conf->global->MAIN_USE_ADVANCED_PERMS)) {
446  if (preg_match('/_advance$/', $obj->perms)) {
447  print ' <span class="opacitymedium">('.$langs->trans("AdvancedModeOnly").')</span>';
448  }
449  }
450  print '</td>';
451 
452  // Permission id
453  if ($user->admin) print '<td class="right"><span class="opacitymedium">'.$obj->id.'</span></td>';
454 
455  print '</tr>'."\n";
456 
457  $i++;
458  }
459 } else dol_print_error($db);
460 print '</table>';
461 print '</div>';
462 
463 $parameters = array();
464 $reshook = $hookmanager->executeHooks('insertExtraFooter', $parameters, $object, $action); // Note that $action and $object may have been modified by some hooks
465 if ($reshook < 0) setEventMessages($hookmanager->error, $hookmanager->errors, 'errors');
466 
467 
469 
470 // End of page
471 llxFooter();
472 $db->close();
dol_osencode($str)
Return a string encoded into OS filesystem encoding.
GETPOST($paramname, $check= 'alphanohtml', $method=0, $filter=null, $options=null, $noreplace=0)
Return value of a param into GET or POST supervariable.
user_prepare_head($object)
Prepare array with list of tabs.
dolGetModulesDirs($subdir= '')
Return list of modules directories.
Class to manage Dolibarr users.
Definition: user.class.php:44
showModulesExludedForExternal($modules)
Show array with constants to edit.
Definition: admin.lib.php:1676
llxHeader()
Empty header.
Definition: wrapper.php:45
setEventMessages($mesg, $mesgs, $style= 'mesgs', $messagekey= '')
Set event messages in dol_events session object.
Class to manage generation of HTML components Only common components must be here.
dol_strlen($string, $stringencoding= 'UTF-8')
Make a strlen call.
img_picto($titlealt, $picto, $moreatt= '', $pictoisfullpath=false, $srconly=0, $notitle=0, $alt= '', $morecss= '', $marginleftonlyshort=2)
Show picto whatever it&#39;s its name (generic function)
dol_syslog($message, $level=LOG_INFO, $ident=0, $suffixinfilename= '', $restricttologhandler= '', $logcontext=null)
Write log message into outputs.
img_object($titlealt, $picto, $moreatt= '', $pictoisfullpath=false, $srconly=0, $notitle=0)
Show a picto called object_picto (generic function)
restrictedArea($user, $features, $objectid=0, $tableandshare= '', $feature2= '', $dbt_keyfield= 'fk_soc', $dbt_select= 'rowid', $isdraft=0)
Check permissions of a user to show a page and an object.
accessforbidden($message= '', $printheader=1, $printfooter=1, $showonlymessage=0, $params=null)
Show a message to say access is forbidden and stop program Calling this function terminate execution ...
loadMenu($forcemainmenu= '', $forceleftmenu= '')
Load this-&gt;tabMenu.
print $_SERVER["PHP_SELF"]
Edit parameters.
dol_get_fiche_head($links=array(), $active= '', $title= '', $notab=0, $picto= '', $pictoisfullpath=0, $morehtmlright= '', $morecss= '', $limittoshow=0, $moretabssuffix= '')
Show tabs of a record.
print
Draft customers invoices.
Definition: index.php:89
dol_print_error($db= '', $error= '', $errors=null)
Displays error message system with all the information to facilitate the diagnosis and the escalation...
newToken()
Return the value of token currently saved into session with name &#39;newtoken&#39;.
dol_get_fiche_end($notab=0)
Return tab footer of a card.
dol_banner_tab($object, $paramid, $morehtml= '', $shownav=1, $fieldid= 'rowid', $fieldref= 'ref', $morehtmlref= '', $moreparam= '', $nodbprefix=0, $morehtmlleft= '', $morehtmlstatus= '', $onlybanner=0, $morehtmlright= '')
Show tab footer of a card.
llxFooter()
Empty footer.
Definition: wrapper.php:59
info_admin($text, $infoonimgalt=0, $nodiv=0, $admin= '1', $morecss= '', $textfordropdown= '')
Show information for admin users or standard users.
dol_escape_htmltag($stringtoescape, $keepb=0, $keepn=0, $keepmoretags= '', $escapeonlyhtmltags=0)
Returns text escaped for inclusion in HTML alt or title tags, or into values of HTML input fields...