Adding a User to a Group In Code

gourmet fare

Adding Users to Groups

Sometimes you need to add a user to a group on-the-fly to give him automatic access to protected resources. An example of when you would want to do this is immediately upon completion of a successful payment transaction. There are a couple of MODX API functions that make this a simple process.

sottwell asked...

I have a script that automatically adds the current user to a specified group, but he has to log out and log in again before his new privileges are applied. How can I add a user to a group, then have the user's SESSION re-loaded to have the new group information?

The Solution:

BobRay says...

Give this a try:

$context = 'web'; // or whatever
$targets = explode(',', $this->xpdo->getOption('principal_targets',
    null, 'modAccessContext,modAccessResourceGroup,modAccessCategory,sources.modAccessMediaSource'));
array_walk($targets, 'trim');
$modx->user->loadAttributes($targets, $context, true);

What's the Story?

To add a user to a group or groups, use the $modx->joinGroup('groupname') API function.


BobRay also says to make sure to use an int cast if using group ID numbers rather than group names:

$user->joinGroup( (int) $groupId, (int) $roleId);

So the final code to add a user to a group, and flush his permissions, looks like this:

$groupname = 'Group1';
if(!($modx->user->isMember($groupname))) {
  $userId = $modx->user->get('id');
  // fix for a bug in joinGroup()
  $context = 'web';
  // get the attributes to reload
  $targets = explode(',', $modx->getOption('principal_targets',
    null, 'modAccessContext,modAccessResourceGroup,modAccessCategory,sources.modAccessMediaSource'));
  array_walk($targets, 'trim');
  // reload the attributes
  $modx->user->loadAttributes($targets, $context, true);

The line about unsetting the SESSION's modx.user.{id}.userGroups field is because of a bug in the joinGroup() function. It unsets the modx.user.{id}.userGroupNames field, but not modx.user{id}.userGroups, so we have to take care of that to get both group IDs and group names updated in the SESSION.