diff options
author | Dries Buytaert <dries@buytaert.net> | 2008-05-07 19:34:24 +0000 |
---|---|---|
committer | Dries Buytaert <dries@buytaert.net> | 2008-05-07 19:34:24 +0000 |
commit | b9f1018ea4fe429656de0fad91fcde51d9507e50 (patch) | |
tree | 20648c37c14f84c119f13c49ce75c97f02c07336 /modules/user/user.module | |
parent | 48e293a6b3d647d79b7b3ce58ab467f9c3fd6de7 (diff) | |
download | brdo-b9f1018ea4fe429656de0fad91fcde51d9507e50.tar.gz brdo-b9f1018ea4fe429656de0fad91fcde51d9507e50.tar.bz2 |
- Patch #73874 by pwolanin: normalize the permissions table and wrote simpletests for the (new) permission handling. At last.
Diffstat (limited to 'modules/user/user.module')
-rw-r--r-- | modules/user/user.module | 65 |
1 files changed, 59 insertions, 6 deletions
diff --git a/modules/user/user.module b/modules/user/user.module index 3fa75e296..b7ea58c8d 100644 --- a/modules/user/user.module +++ b/modules/user/user.module @@ -434,6 +434,59 @@ function user_password($length = 10) { } /** + * Determine the permissions for one or more roles. + * + * @param $roles + * An array whose keys are the role IDs of interest, such as $user->roles. + * @param $reset + * Optional parameter - if TRUE data in the static variable is rebuilt. + * + * @return + * An array indexed by role ID. Each value is an array whose keys are the + * permission strings for the given role ID. + */ +function user_role_permissions($roles = array(), $reset = FALSE) { + static $stored_permissions = array(); + + if ($reset) { + // Clear the data cached in the static variable. + $stored_permissions = array(); + } + + $role_permissions = $fetch = array(); + + if ($roles) { + foreach ($roles as $rid => $name) { + if (isset($stored_permissions[$rid])) { + $role_permissions[$rid] = $stored_permissions[$rid]; + } + else { + // Add this rid to the list of those needing to be fetched. + $fetch[] = $rid; + // Prepare in case no permissions are returned. + $stored_permissions[$rid] = array(); + } + } + + if ($fetch) { + // Get from the database permissions that were not in the static variable. + // Only role IDs with at least one permission assigned will return rows. + $result = db_query("SELECT r.rid, p.permission FROM {role} r INNER JOIN {role_permission} p ON p.rid = r.rid WHERE r.rid IN (" . db_placeholders($fetch) . ")", $fetch); + + while ($row = db_fetch_array($result)) { + $stored_permissions[$row['rid']][$row['permission']] = TRUE; + } + foreach ($fetch as $rid) { + // For every rid, we know we at least assigned an empty array. + $role_permissions[$rid] = $stored_permissions[$rid]; + } + } + } + + return $role_permissions; +} + +/** * Determine whether the user has a given privilege. * * @param $string @@ -472,11 +525,11 @@ function user_access($string, $account = NULL, $reset = FALSE) { // To reduce the number of SQL queries, we cache the user's permissions // in a static variable. if (!isset($perm[$account->uid])) { - $result = db_query("SELECT p.perm FROM {role} r INNER JOIN {permission} p ON p.rid = r.rid WHERE r.rid IN (" . db_placeholders($account->roles) . ")", array_keys($account->roles)); + $role_permissions = user_role_permissions($account->roles, $reset); $perms = array(); - while ($row = db_fetch_object($result)) { - $perms += array_flip(explode(', ', $row->perm)); + foreach ($role_permissions as $one_role) { + $perms += $one_role; } $perm[$account->uid] = $perms; } @@ -1590,7 +1643,7 @@ function user_roles($membersonly = FALSE, $permission = NULL) { ); if (!empty($permission)) { - $result = db_query("SELECT r.* FROM {role} r INNER JOIN {permission} p ON r.rid = p.rid WHERE p.perm LIKE '%%%s%%' ORDER BY r.name", $permission); + $result = db_query("SELECT r.* FROM {role} r INNER JOIN {role_permission} p ON r.rid = p.rid WHERE p.permission = '%s' ORDER BY r.name", $permission); } else { $result = db_query('SELECT * FROM {role} ORDER BY name'); @@ -1854,8 +1907,8 @@ function user_filters() { ksort($options); $filters['permission'] = array( 'title' => t('permission'), - 'join' => 'LEFT JOIN {permission} p ON ur.rid = p.rid', - 'where' => " ((p.perm IS NOT NULL AND p.perm LIKE '%%%s%%') OR u.uid = 1) ", + 'join' => 'LEFT JOIN {role_permission} p ON ur.rid = p.rid', + 'where' => " (p.permission = '%s' OR u.uid = 1) ", 'options' => $options, ); |