/** * Copyright (c) 2014 Red Hat, Inc. * * This software is licensed to you under the GNU General Public License, * version 2 (GPLv2). There is NO WARRANTY for this software, express or * implied, including the implied warranties of MERCHANTABILITY or FITNESS * FOR A PARTICULAR PURPOSE. You should have received a copy of GPLv2 * along with this software; if not, see * http://www.gnu.org/licenses/old-licenses/gpl-2.0.txt. * * Red Hat trademarks are not licensed under GPLv2. No permission is * granted to use or replicate Red Hat trademarks that are incorporated * in this software or its documentation. */ package com.redhat.rhn.frontend.xmlrpc.user.external; import java.util.HashSet; import java.util.List; import java.util.Set; import com.redhat.rhn.domain.common.SatConfigFactory; import com.redhat.rhn.domain.org.Org; import com.redhat.rhn.domain.org.usergroup.OrgUserExtGroup; import com.redhat.rhn.domain.org.usergroup.UserExtGroup; import com.redhat.rhn.domain.org.usergroup.UserGroupFactory; import com.redhat.rhn.domain.role.Role; import com.redhat.rhn.domain.role.RoleFactory; import com.redhat.rhn.domain.server.ServerGroup; import com.redhat.rhn.domain.server.ServerGroupFactory; import com.redhat.rhn.domain.user.User; import com.redhat.rhn.domain.user.UserFactory; import com.redhat.rhn.frontend.xmlrpc.BaseHandler; import com.redhat.rhn.frontend.xmlrpc.ExternalGroupAlreadyExistsException; import com.redhat.rhn.frontend.xmlrpc.InvalidRoleException; import com.redhat.rhn.frontend.xmlrpc.InvalidServerGroupException; import com.redhat.rhn.frontend.xmlrpc.NoSuchExternalGroupToRoleMapException; import com.redhat.rhn.frontend.xmlrpc.NoSuchExternalGroupToServerGroupMapException; import com.redhat.rhn.frontend.xmlrpc.PermissionCheckFailureException; import org.apache.commons.lang.BooleanUtils; import org.apache.commons.lang.StringUtils; /** * UserHandler * @version $Rev$ * @xmlrpc.namespace user.external * @xmlrpc.doc If you are using IPA integration to allow authentication of users from * an external IPA server (rare) the users will still need to be created in the Satellite * database. Methods in this namespace allow you to configure some specifics of how this * happens, like what organization they are created in or what roles they will have. * These options can also be set in the web admin interface. */ public class UserExternalHandler extends BaseHandler { /** * Set the value of EXT_AUTH_KEEP_ROLES * @param loggedInUser The current user * @param keepRoles True if we should keep temporary roles between login sessions * @return 1 on success * @throws PermissionCheckFailureException if the user is not a Sat admin * * @xmlrpc.doc Set whether we should keeps roles assigned to users because of * their IPA groups even after they log in through a non-IPA method. Can only be * called by a satellite_admin. * @xmlrpc.param #param("string", "sessionKey") * @xmlrpc.param #param_desc("boolean", "keepRoles", "True if we should keep roles * after users log in through non-IPA method, false otherwise.") * @xmlrpc.returntype #return_int_success() */ public int setKeepTemporaryRoles(User loggedInUser, Boolean keepRoles) throws PermissionCheckFailureException { // Make sure we're logged in and a Sat Admin ensureSatAdmin(loggedInUser); if (SatConfigFactory.getSatConfigBooleanValue( SatConfigFactory.EXT_AUTH_KEEP_ROLES) && !BooleanUtils.toBoolean(keepRoles)) { // if the option was turned off, delete temporary roles // across the whole satellite UserGroupFactory.deleteTemporaryRoles(); } // store the value SatConfigFactory.setSatConfigBooleanValue(SatConfigFactory.EXT_AUTH_KEEP_ROLES, keepRoles); return 1; } /** * Get the value of EXT_AUTH_KEEP_ROLES * @param loggedInUser The current user * @return True if we should keep roles * after users log in through non-IPA method, false otherwise. * @throws PermissionCheckFailureException if the user is not a Sat admin * * @xmlrpc.doc Get whether we should keeps roles assigned to users because of * their IPA groups even after they log in through a non-IPA method. Can only be * called by a satellite_admin. * @xmlrpc.param #param("string", "sessionKey") * @xmlrpc.returntype boolean - True if we should keep roles * after users log in through non-IPA method, false otherwise. */ public boolean getKeepTemporaryRoles(User loggedInUser) throws PermissionCheckFailureException { // Make sure we're logged in and a Sat Admin ensureSatAdmin(loggedInUser); // get the value return SatConfigFactory .getSatConfigBooleanValue(SatConfigFactory.EXT_AUTH_KEEP_ROLES); } /** * Set the value of EXT_AUTH_USE_ORGUNIT * @param loggedInUser The current user * @param useOrgUnit True if we should keep pay attention to the Org Unit from IPA * @return 1 on success * @throws PermissionCheckFailureException if the user is not a Sat admin * * @xmlrpc.doc Set whether we place users into the organization that corresponds * to the "orgunit" set on the IPA server. The orgunit name must match exactly the * Satellite organization name. Can only be called by a satellite_admin. * @xmlrpc.param #param("string", "sessionKey") * @xmlrpc.param #param_desc("boolean", "useOrgUnit", "True if we should use the IPA * orgunit to determine which organization to create the user in, false otherwise.") * @xmlrpc.returntype #return_int_success() */ public int setUseOrgUnit(User loggedInUser, Boolean useOrgUnit) throws PermissionCheckFailureException { // Make sure we're logged in and a Sat Admin ensureSatAdmin(loggedInUser); // store the value SatConfigFactory.setSatConfigBooleanValue(SatConfigFactory.EXT_AUTH_USE_ORGUNIT, useOrgUnit); return 1; } /** * Get the value of EXT_AUTH_USE_ORGUNIT * @param loggedInUser The current user * @return True if we should use org unit * @throws PermissionCheckFailureException if the user is not a Sat admin * * @xmlrpc.doc Get whether we place users into the organization that corresponds * to the "orgunit" set on the IPA server. The orgunit name must match exactly the * Satellite organization name. Can only be called by a satellite_admin. * @xmlrpc.param #param("string", "sessionKey") * @xmlrpc.returntype boolean - True if we should use the IPA * orgunit to determine which organization to create the user in, false otherwise. */ public boolean getUseOrgUnit(User loggedInUser) throws PermissionCheckFailureException { // Make sure we're logged in and a Sat Admin ensureSatAdmin(loggedInUser); // get the value return SatConfigFactory .getSatConfigBooleanValue(SatConfigFactory.EXT_AUTH_USE_ORGUNIT); } /** * Set the value of EXT_AUTH_DEFAULT_ORGID * @param loggedInUser The current user * @param defaultOrg the orgId that we want to use as the default org * @return 1 on success * @throws PermissionCheckFailureException if the user is not a Sat admin * * @xmlrpc.doc Set the default org that users should be added in if orgunit from * IPA server isn't found or is disabled. Can only be called by a satellite_admin. * @xmlrpc.param #param("string", "sessionKey") * @xmlrpc.param #param_desc("int", "defaultOrg", "Id of the organization to set * as the default org. 0 if there should not be a default organization.") * @xmlrpc.returntype #return_int_success() */ public int setDefaultOrg(User loggedInUser, Integer defaultOrg) throws PermissionCheckFailureException { // Make sure we're logged in and a Sat Admin ensureSatAdmin(loggedInUser); if (defaultOrg != 0) { verifyOrgExists(defaultOrg); SatConfigFactory.setSatConfigValue(SatConfigFactory.EXT_AUTH_DEFAULT_ORGID, defaultOrg.toString()); } else { SatConfigFactory.setSatConfigValue(SatConfigFactory.EXT_AUTH_DEFAULT_ORGID, ""); } return 1; } /** * Get the value of EXT_AUTH_DEFAULT_ORGID * @param loggedInUser The current user * @return orgId of the default org * @throws PermissionCheckFailureException if the user is not a Sat admin * * @xmlrpc.doc Get the default org that users should be added in if orgunit from * IPA server isn't found or is disabled. Can only be called by a satellite_admin. * @xmlrpc.param #param("string", "sessionKey") * @xmlrpc.returntype int - Id of the default organization. 0 if there is no default. */ public int getDefaultOrg(User loggedInUser) throws PermissionCheckFailureException { // Make sure we're logged in and a Sat Admin ensureSatAdmin(loggedInUser); // get the value String org = SatConfigFactory.getSatConfigValue( SatConfigFactory.EXT_AUTH_DEFAULT_ORGID); if (org == null || StringUtils.isEmpty(org)) { return 0; } return Integer.parseInt(org); } /** * Create a new external user group * @param loggedInUser The current user * @param name The name of the new group * @param roles List of roles to set for this group * @return the newly created group * @throws PermissionCheckFailureException if the user is not a Sat admin * * @xmlrpc.doc Externally authenticated users may be members of external groups. You * can use these groups to assign additional roles to the users when they log in. * Can only be called by a satellite_admin. * @xmlrpc.param #param("string", "sessionKey") * @xmlrpc.param #param_desc("string", "name", "Name of the external group. Must be * unique.") * @xmlrpc.param #array_single("string", "role - Can be any of: * satellite_admin, org_admin (implies all other roles except for satellite_admin), * channel_admin, config_admin, system_group_admin, or * activation_key_admin.") * @xmlrpc.returntype $UserExtGroupSerializer */ public UserExtGroup createExternalGroupToRoleMap(User loggedInUser, String name, List<String> roles) { // Make sure we're logged in and a Sat Admin ensureSatAdmin(loggedInUser); if (UserGroupFactory.lookupExtGroupByLabel(name) != null) { throw new ExternalGroupAlreadyExistsException(name); } Set<Role> myRoles = new HashSet<Role>(); for (String role : roles) { Role myRole = RoleFactory.lookupByLabel(role); if (myRole == null) { throw new InvalidRoleException(role); } myRoles.add(myRole); } removeImpliedRoles(myRoles); UserExtGroup group = new UserExtGroup(); group.setLabel(name); group.setRoles(myRoles); UserGroupFactory.save(group); addImpliedRoles(group.getRoles()); return group; } /** * Get a external user group * @param loggedInUser The current user * @param name The name of the group * @return the group * @throws PermissionCheckFailureException if the user is not a Sat admin * * @xmlrpc.doc Get a representation of the role mapping for an external group. * Can only be called by a satellite_admin. * @xmlrpc.param #param("string", "sessionKey") * @xmlrpc.param #param_desc("string", "name", "Name of the external group.") * @xmlrpc.returntype $UserExtGroupSerializer */ public UserExtGroup getExternalGroupToRoleMap(User loggedInUser, String name) { // Make sure we're logged in and a Sat Admin ensureSatAdmin(loggedInUser); UserExtGroup group = UserGroupFactory.lookupExtGroupByLabel(name); if (group == null) { throw new NoSuchExternalGroupToRoleMapException(name); } addImpliedRoles(group.getRoles()); return group; } /** * update a external user group * @param loggedInUser The current user * @param name The name of the group * @param roles the roles to set * @return 1 if successful, error otherwise * * @xmlrpc.doc Update the roles for an external group. Replace previously set roles * with the ones passed in here. Can only be called by a satellite_admin. * @xmlrpc.param #param("string", "sessionKey") * @xmlrpc.param #param_desc("string", "name", "Name of the external group.") * @xmlrpc.param #array_single("string", "role - Can be any of: * satellite_admin, org_admin (implies all other roles except for satellite_admin), * channel_admin, config_admin, system_group_admin, or * activation_key_admin.") * @xmlrpc.returntype #return_int_success() */ public int setExternalGroupRoles(User loggedInUser, String name, List<String> roles) { // Make sure we're logged in and a Sat Admin ensureSatAdmin(loggedInUser); UserExtGroup group = UserGroupFactory.lookupExtGroupByLabel(name); if (group == null) { throw new NoSuchExternalGroupToRoleMapException(name); } Set<Role> myRoles = new HashSet<Role>(); for (String role : roles) { Role myRole = RoleFactory.lookupByLabel(role); if (myRole == null) { throw new InvalidRoleException(role); } myRoles.add(myRole); } removeImpliedRoles(myRoles); group.setRoles(myRoles); UserGroupFactory.save(group); return 1; } /** * delete an external user group * @param loggedInUser The current user * @param name The name of the group * @return 1 if successful, error otherwise * @throws PermissionCheckFailureException if the user is not a Sat admin * * @xmlrpc.doc Delete the role map for an external group. Can only be called * by a satellite_admin. * @xmlrpc.param #param("string", "sessionKey") * @xmlrpc.param #param_desc("string", "name", "Name of the external group.") * @xmlrpc.returntype #return_int_success() */ public int deleteExternalGroupToRoleMap(User loggedInUser, String name) { // Make sure we're logged in and a Sat Admin ensureSatAdmin(loggedInUser); UserExtGroup group = UserGroupFactory.lookupExtGroupByLabel(name); if (group == null) { throw new NoSuchExternalGroupToRoleMapException(name); } UserGroupFactory.delete(group); return 1; } /** * delete an external user group * @param loggedInUser The current user * @return the external groups * @throws PermissionCheckFailureException if the user is not a Sat admin * * @xmlrpc.doc List role mappings for all known external groups. Can only be called * by a satellite_admin. * @xmlrpc.param #param("string", "sessionKey") * @xmlrpc.returntype * #array() * $UserExtGroupSerializer * #array_end() */ public List<UserExtGroup> listExternalGroupToRoleMaps(User loggedInUser) { // Make sure we're logged in and a Sat Admin ensureSatAdmin(loggedInUser); List<UserExtGroup> groups = UserGroupFactory.listExtAuthGroups(loggedInUser); for (UserExtGroup group : groups) { addImpliedRoles(group.getRoles()); } return UserGroupFactory.listExtAuthGroups(loggedInUser); } // remove all the implied roles if we're adding org_admin (for storing to db) private void removeImpliedRoles(Set<Role> roles) { if (roles.contains(RoleFactory.ORG_ADMIN)) { roles.removeAll(UserFactory.IMPLIEDROLES); } } /** * add in the implied roles for org_admin (for displaying to user) * @param roles The roles the current group has */ private void addImpliedRoles(Set<Role> roles) { if (roles.contains(RoleFactory.ORG_ADMIN)) { roles.addAll(UserFactory.IMPLIEDROLES); } } /** * Create a new external user group * @param loggedInUser The current user * @param name The name of the new group * @param groupNames List of system groups to set for this group * @return the newly created group * * @xmlrpc.doc Externally authenticated users may be members of external groups. You * can use these groups to give access to server groups to the users when they log in. * Can only be called by an org_admin. * @xmlrpc.param #param("string", "sessionKey") * @xmlrpc.param #param_desc("string", "name", "Name of the external group. Must be * unique.") * @xmlrpc.param #array_single("string", "groupName - The names of the server * groups to grant access to.") * @xmlrpc.returntype $OrgUserExtGroupSerializer */ public OrgUserExtGroup createExternalGroupToSystemGroupMap(User loggedInUser, String name, List<String> groupNames) { ensureOrgAdmin(loggedInUser); Org org = loggedInUser.getOrg(); OrgUserExtGroup group = UserGroupFactory.lookupOrgExtGroupByLabelAndOrg(name, org); if (group != null) { throw new ExternalGroupAlreadyExistsException(name); } Set<ServerGroup> sgs = new HashSet<ServerGroup>(); for (String sg : groupNames) { ServerGroup myGroup = ServerGroupFactory.lookupByNameAndOrg(sg, org); if (myGroup == null) { throw new InvalidServerGroupException(sg); } sgs.add(myGroup); } group = new OrgUserExtGroup(org); group.setLabel(name); group.setServerGroups(sgs); UserGroupFactory.save(group); return group; } /** * Get a external user group * @param loggedInUser The current user * @param name The name of the group * @return the group * * @xmlrpc.doc Get a representation of the server group mapping for an external * group. Can only be called by an org_admin. * @xmlrpc.param #param("string", "sessionKey") * @xmlrpc.param #param_desc("string", "name", "Name of the external group.") * @xmlrpc.returntype $OrgUserExtGroupSerializer */ public OrgUserExtGroup getExternalGroupToSystemGroupMap(User loggedInUser, String name) { ensureOrgAdmin(loggedInUser); return UserGroupFactory.lookupOrgExtGroupByLabelAndOrg(name, loggedInUser.getOrg()); } /** * update a external user group * @param loggedInUser The current user * @param name The name of the group * @param groupNames the groups to set * @return 1 if successful, error otherwise * * @xmlrpc.doc Update the server groups for an external group. Replace previously set * server groups with the ones passed in here. Can only be called by an org_admin. * @xmlrpc.param #param("string", "sessionKey") * @xmlrpc.param #param_desc("string", "name", "Name of the external group.") * @xmlrpc.param #array_single("string", "groupName - The names of the * server groups to grant access to.") * @xmlrpc.returntype #return_int_success() */ public int setExternalGroupSystemGroups(User loggedInUser, String name, List<String> groupNames) { ensureOrgAdmin(loggedInUser); Org org = loggedInUser.getOrg(); OrgUserExtGroup group = UserGroupFactory.lookupOrgExtGroupByLabelAndOrg(name, org); if (group == null) { throw new NoSuchExternalGroupToServerGroupMapException(name); } Set<ServerGroup> sgs = new HashSet<ServerGroup>(); for (String sg : groupNames) { ServerGroup myGroup = ServerGroupFactory.lookupByNameAndOrg(sg, org); if (myGroup == null) { throw new InvalidServerGroupException(sg); } sgs.add(myGroup); } group.setServerGroups(sgs); UserGroupFactory.save(group); return 1; } /** * delete an external user group * @param loggedInUser The current user * @param name The name of the group * @return 1 if successful, error otherwise * * @xmlrpc.doc Delete the server group map for an external group. Can only be called * by an org_admin. * @xmlrpc.param #param("string", "sessionKey") * @xmlrpc.param #param_desc("string", "name", "Name of the external group.") * @xmlrpc.returntype #return_int_success() */ public int deleteExternalGroupToSystemGroupMap(User loggedInUser, String name) { ensureOrgAdmin(loggedInUser); Org org = loggedInUser.getOrg(); OrgUserExtGroup group = UserGroupFactory.lookupOrgExtGroupByLabelAndOrg(name, org); if (group == null) { throw new NoSuchExternalGroupToServerGroupMapException(name); } UserGroupFactory.delete(group); return 1; } /** * delete an external user group * @param loggedInUser The current user * @return the external groups * @throws PermissionCheckFailureException if the user is not an Org admin * * @xmlrpc.doc List server group mappings for all known external groups. Can only be * called by an org_admin. * @xmlrpc.param #param("string", "sessionKey") * @xmlrpc.returntype * #array() * $OrgUserExtGroupSerializer * #array_end() */ public List<OrgUserExtGroup> listExternalGroupToSystemGroupMaps(User loggedInUser) { ensureOrgAdmin(loggedInUser); return UserGroupFactory.listExtAuthOrgGroups(loggedInUser); } }