org.cloudfoundry.identity.uaa.scim.bootstrap.ScimGroupBootstrap Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of cloudfoundry-identity-scim Show documentation
Show all versions of cloudfoundry-identity-scim Show documentation
Cloud Foundry User Account and Authentication
/*******************************************************************************
* Cloud Foundry
* Copyright (c) [2009-2014] Pivotal Software, Inc. All Rights Reserved.
*
* This product is licensed to you under the Apache License, Version 2.0 (the "License").
* You may not use this product except in compliance with the License.
*
* This product includes a number of subcomponents with
* separate copyright notices and license terms. Your use of these
* subcomponents is subject to the terms and conditions of the
* subcomponent's license, as noted in the LICENSE file.
*******************************************************************************/
package org.cloudfoundry.identity.uaa.scim.bootstrap;
import java.util.ArrayList;
import java.util.Collections;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.cloudfoundry.identity.uaa.scim.ScimCore;
import org.cloudfoundry.identity.uaa.scim.ScimGroup;
import org.cloudfoundry.identity.uaa.scim.ScimGroupMember;
import org.cloudfoundry.identity.uaa.scim.ScimGroupMembershipManager;
import org.cloudfoundry.identity.uaa.scim.ScimGroupProvisioning;
import org.cloudfoundry.identity.uaa.scim.ScimUser;
import org.cloudfoundry.identity.uaa.scim.ScimUserProvisioning;
import org.cloudfoundry.identity.uaa.scim.exception.MemberAlreadyExistsException;
import org.cloudfoundry.identity.uaa.scim.exception.ScimResourceAlreadyExistsException;
import org.cloudfoundry.identity.uaa.zone.IdentityZoneHolder;
import org.springframework.beans.factory.InitializingBean;
import org.springframework.util.StringUtils;
public class ScimGroupBootstrap implements InitializingBean {
private Set groups;
private Map> groupMembers;
private Map> groupAdmins;
private final ScimGroupProvisioning scimGroupProvisioning;
private final ScimGroupMembershipManager membershipManager;
private final ScimUserProvisioning scimUserProvisioning;
private static final String USER_BY_NAME_FILTER = "username eq \"%s\"";
private static final String GROUP_BY_NAME_FILTER = "displayName eq \"%s\"";
private final Log logger = LogFactory.getLog(getClass());
public ScimGroupBootstrap(ScimGroupProvisioning scimGroupProvisioning, ScimUserProvisioning scimUserProvisioning,
ScimGroupMembershipManager membershipManager) {
this.scimGroupProvisioning = scimGroupProvisioning;
this.scimUserProvisioning = scimUserProvisioning;
this.membershipManager = membershipManager;
groups = new HashSet();
groupMembers = new HashMap>();
groupAdmins = new HashMap>();
}
/**
* Specify the list of groups to create as a comma-separated list of
* group-names
*
* @param groups
*/
public void setGroups(String groups) {
this.groups = StringUtils.commaDelimitedListToSet(groups);
}
/**
* Specify the membership info as a list of strings, where each string takes
* the format -
* {@code |[|write]}
* the optional 'write' field in the end marks the users as admins of the
* group
*
* @param membershipInfo
*/
public void setGroupMembers(List membershipInfo) {
for (String line : membershipInfo) {
String[] fields = line.split("\\|");
if (fields.length < 2) {
continue;
}
Set users = StringUtils.commaDelimitedListToSet(fields[1]);
String groupName = fields[0];
groups.add(groupName);
boolean groupAdmin = (3 <= fields.length && "write".equalsIgnoreCase(fields[2])) ? true : false;
if (groupAdmin) {
groupAdmins.put(groupName, users);
} else {
groupMembers.put(groupName, users);
}
}
logger.debug("groups: " + groups);
logger.debug("admins: " + groupAdmins + ", members: " + groupMembers);
}
@Override
public void afterPropertiesSet() throws Exception {
for (String g : groups) {
addGroup(g);
}
for (String g : groups) {
addMembers(g);
}
}
private void addMembers(String g) {
ScimGroup group = getGroup(g);
if (group == null) {
addGroup(g);
}
List members = getMembers(groupMembers.get(g), ScimGroupMember.GROUP_MEMBER);
members.addAll(getMembers(groupAdmins.get(g), ScimGroupMember.GROUP_ADMIN));
logger.debug("adding members: " + members + " into group: " + g);
for (ScimGroupMember member : members) {
try {
membershipManager.addMember(group.getId(), member);
} catch (MemberAlreadyExistsException ex) {
logger.debug(member.getMemberId() + " already is member of group " + g);
}
}
}
private List getMembers(Set names, List auth) {
if (names == null || names.isEmpty()) {
return Collections. emptyList();
}
List members = new ArrayList();
for (String name : names) {
ScimCore member = getScimResourceId(name);
if (member != null) {
members.add(
new ScimGroupMember(
member.getId(),
(member instanceof ScimGroup) ? ScimGroupMember.Type.GROUP : ScimGroupMember.Type.USER,
auth
)
);
}
}
return members;
}
private ScimCore getScimResourceId(String name) {
ScimCore res = getUser(name);
if (res != null) {
return res;
}
logger.debug("user " + name + " does not exist, checking in groups...");
return getGroup(name);
}
private ScimUser getUser(String name) {
List user = scimUserProvisioning.query(String.format(USER_BY_NAME_FILTER, name));
if (user != null && !user.isEmpty()) {
return user.get(0);
}
return null;
}
ScimGroup getGroup(String name) {
List g = scimGroupProvisioning.query(String.format(GROUP_BY_NAME_FILTER, name));
if (g != null && !g.isEmpty()) {
ScimGroup gr = g.get(0);
gr.setMembers(membershipManager.getMembers(gr.getId()));
return gr;
}
logger.debug("could not find group with name");
return null;
}
private void addGroup(String name) {
if (name.isEmpty()) {
return;
}
logger.debug("adding group: " + name);
ScimGroup g = new ScimGroup(null,name,IdentityZoneHolder.get().getId());
try {
scimGroupProvisioning.create(g);
} catch (ScimResourceAlreadyExistsException ex) {
logger.debug("group " + g + " already exists, ignoring...");
}
}
}