3

I know that roles in WordPress are not hierarchical, but I'm wondering if there is any type of capability to "assign users to roles". All I can see if being able to add users or not.

The real kicker here is, I've used Justin Tadlock's Members plugin to create a new role, called "Clients" which removes all the stuff they should either not need to see, or shouldn't be able to control - which works great.
But, if I give them the ability to create a new user, they can also choose my "super admin" role, which can see everything. So, in a way, they kinda cheat the system a little bit.

Is there anyway to "hide" a certain role from showing up in what a user can set a new user/edit a user to? Or, possibly remove the role identifier from the add/edit user screen based on their role?
I know it sounds a bit off of what WordPress is mean to do for user permissions, but from an administrative stand-point, it sounds useful - at least in my head ;)

Thanks!

2
  • Does this one sound a little too crazy? ;)
    – Zach
    Nov 8, 2011 at 15:54
  • No, absolutely not :)
    – kaiser
    May 29, 2012 at 22:26

2 Answers 2

7

The UI select element

On user-edit.php, you see the drop-down in the UI. The drop down <select> wrapper is hard coded.

Then the admin interface does a nifty thing 1) according to the inline comment: // Get the highest/primary role for this user. In fact it is getting the first role, that was assigned to the user (this we have to keep in mind).

Then there's basically only a call to wp_dropdown_roles(). This function doesn't do anything else, than looping through the available roles and wrapping them inside <option> elements. But, there's one kool thing it does: It uses the roles retrieved by get_editable_roles(). And here comes the magic! A filter, for the global $wp_roles->roles. By default this returns all roles, but you can jump in and simply unset whatever you want.

// Add this as mu-plugin
function wpse32738_get_editable_roles( $editable_roles )
{
    if ( current_user_can( 'client' ) )
        // unset whatever you need here.

    return $editable_roles;
}
add_filter( 'editable_roles', 'wpse32738_get_editable_roles' );

1) Roles are a "flat" system. A role can have capabilities that overrule other capabilities.

3
  • 1
    Nice! I'll give this a shot and report back. Thanks for the detailed explanation!
    – Zach
    May 30, 2012 at 16:01
  • Tried the following without success: pastebin.com/1GPMcWD9 Anything I'm missing? Thanks!
    – Zach
    Jun 4, 2012 at 19:16
  • Ah -- $role_names needed to be $editable_roles. Thanks!
    – Zach
    Jun 4, 2012 at 19:49
1

I've followed Kaiser's instructions and written the following code that allows me to grant user-management capabilities to a specific role and prevent privilege escalation to any built-in role (my code should be tweaked if you define custom intermediary roles).

// add user-management capabilities
add_action('admin_init', function() {
  $role = get_role( 'editor' );

  $role->add_cap( 'list_users' );
  $role->add_cap( 'create_users' );
  $role->add_cap( 'edit_users' );
  $role->add_cap( 'delete_users' );
});

// prevent privilege escalation
add_filter( 'editable_roles', function( $editable_roles ) {
  if ( ! current_user_can( 'promote_users' ) ) {
    // always remove admin roles
    if ( isset($editable_roles['super_admin']) ) {
      unset( $editable_roles['super_admin'] );
    }
    unset( $editable_roles['administrator'] );

    // remove other roles conditionnaly to prevent escalation
    if ( ! current_user_can( 'editor' ) ) {
      unset( $editable_roles['editor'] );

      if ( ! current_user_can( 'author' ) ) {
        unset( $editable_roles['author'] );

        if ( ! current_user_can( 'contributor' ) ) {
          unset( $editable_roles['contributor'] );
        }
      }
    }
  }

  return $editable_roles;
});

With this code, a contributor can be granted user-management capabilities, and he/she should only be able to create other contributors or subscribers.

BEWARE: this is a hacky solution, it hasn't been tested in network mode and no validation of input is made: a malicious user could still escalate privileges!

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.

Not the answer you're looking for? Browse other questions tagged or ask your own question.