import java.net.URI;
import java.net.URISyntaxException;
import java.util.ArrayList;
-import java.util.Arrays;
import java.util.Dictionary;
import java.util.LinkedHashMap;
import java.util.List;
import javax.naming.InvalidNameException;
import javax.naming.NamingEnumeration;
import javax.naming.directory.Attributes;
+import javax.naming.directory.BasicAttributes;
import javax.naming.ldap.LdapName;
+import javax.naming.ldap.Rdn;
+import org.osgi.framework.Filter;
+import org.osgi.framework.FrameworkUtil;
import org.osgi.framework.InvalidSyntaxException;
import org.osgi.service.useradmin.Authorization;
import org.osgi.service.useradmin.Role;
import org.osgi.service.useradmin.User;
-import org.osgi.service.useradmin.UserAdmin;
/** User admin implementation using LDIF file(s) as backend. */
-public class LdifUserAdmin implements UserAdmin {
+public class LdifUserAdmin extends AbstractLdapUserAdmin {
SortedMap<LdapName, LdifUser> users = new TreeMap<LdapName, LdifUser>();
SortedMap<LdapName, LdifGroup> groups = new TreeMap<LdapName, LdifGroup>();
- private final boolean isReadOnly;
- private final URI uri;
-
- private List<String> indexedUserProperties = Arrays.asList(new String[] {
- "uid", "mail", "cn" });
private Map<String, Map<String, LdifUser>> userIndexes = new LinkedHashMap<String, Map<String, LdifUser>>();
public LdifUserAdmin(String uri) {
}
public LdifUserAdmin(String uri, boolean isReadOnly) {
- this.isReadOnly = isReadOnly;
+ setReadOnly(isReadOnly);
try {
- this.uri = new URI(uri);
+ setUri(new URI(uri));
} catch (URISyntaxException e) {
throw new ArgeoUserAdminException("Invalid URI " + uri, e);
}
- if (!isReadOnly && !this.uri.getScheme().equals("file:"))
- throw new UnsupportedOperationException(this.uri.getScheme()
+ if (!isReadOnly && !getUri().getScheme().equals("file:"))
+ throw new UnsupportedOperationException(getUri().getScheme()
+ "not supported read-write.");
- try {
- load(this.uri.toURL().openStream());
- } catch (Exception e) {
- throw new ArgeoUserAdminException("Cannot open URL " + this.uri, e);
- }
}
public LdifUserAdmin(InputStream in) {
load(in);
- isReadOnly = true;
- this.uri = null;
+ setReadOnly(true);
+ setUri(null);
+ }
+
+ public void init() {
+ try {
+ load(getUri().toURL().openStream());
+ } catch (Exception e) {
+ throw new ArgeoUserAdminException("Cannot open URL " + getUri(), e);
+ }
}
protected void load(InputStream in) {
// optimise
for (LdifGroup group : groups.values())
- group.loadMembers(this);
+ loadMembers(group);
// indexes
- for (String attr : indexedUserProperties)
+ for (String attr : getIndexedUserProperties())
userIndexes.put(attr, new TreeMap<String, LdifUser>());
for (LdifUser user : users.values()) {
Dictionary<String, Object> properties = user.getProperties();
- for (String attr : indexedUserProperties) {
+ for (String attr : getIndexedUserProperties()) {
Object value = properties.get(attr);
if (value != null) {
LdifUser otherUser = userIndexes.get(attr).put(
if (otherUser != null)
throw new ArgeoUserAdminException("User " + user
+ " and user " + otherUser
- + " both habe property " + attr
+ + " both have property " + attr
+ " set to " + value);
}
}
@Override
public Role createRole(String name, int type) {
- throw new UnsupportedOperationException();
+ try {
+ LdapName dn = new LdapName(name);
+ if (users.containsKey(dn) || groups.containsKey(dn))
+ throw new ArgeoUserAdminException("Already a role " + name);
+
+ BasicAttributes attrs = new BasicAttributes();
+ attrs.put("dn", dn.toString());
+ Rdn nameRdn = dn.getRdn(dn.size() - 1);
+ // TODO deal with multiple attr RDN
+ attrs.put(nameRdn.getType(), nameRdn.getValue());
+ LdifUser newRole;
+ if (type == Role.USER) {
+ newRole = new LdifUser(dn, attrs);
+ users.put(dn, newRole);
+ } else if (type == Role.GROUP) {
+ newRole = new LdifGroup(dn, attrs);
+ groups.put(dn, (LdifGroup) newRole);
+ } else
+ throw new ArgeoUserAdminException("Unsupported type " + type);
+ return newRole;
+ } catch (InvalidNameException e) {
+ throw new ArgeoUserAdminException("Cannot create role " + name, e);
+ }
}
@Override
public boolean removeRole(String name) {
- throw new UnsupportedOperationException();
+ try {
+ LdapName dn = new LdapName(name);
+ LdifUser role = null;
+ if (users.containsKey(dn))
+ role = users.remove(dn);
+ else if (groups.containsKey(dn))
+ role = groups.remove(dn);
+ else
+ throw new ArgeoUserAdminException("There is no role " + name);
+ if (role == null)
+ return false;
+ for (LdifGroup group : role.directMemberOf) {
+ group.directMembers.remove(role);
+ group.getAttributes().get(group.getMemberAttrName())
+ .remove(dn.toString());
+ }
+ if (role instanceof LdifGroup) {
+ LdifGroup group = (LdifGroup) role;
+ for (Role user : group.directMembers) {
+ if (user instanceof LdifUser)
+ ((LdifUser) user).directMemberOf.remove(group);
+ }
+ }
+ return true;
+ } catch (InvalidNameException e) {
+ throw new ArgeoUserAdminException("Cannot create role " + name, e);
+ }
}
@Override
public Role[] getRoles(String filter) throws InvalidSyntaxException {
+ ArrayList<Role> res = new ArrayList<Role>();
if (filter == null) {
- ArrayList<Role> res = new ArrayList<Role>();
res.addAll(users.values());
res.addAll(groups.values());
- return res.toArray(new Role[res.size()]);
+ } else {
+ Filter f = FrameworkUtil.createFilter(filter);
+ for (LdifUser user : users.values())
+ if (f.match(user.getProperties()))
+ res.add(user);
+ for (LdifUser group : groups.values())
+ if (f.match(group.getProperties()))
+ res.add(group);
}
- throw new UnsupportedOperationException();
+ return res.toArray(new Role[res.size()]);
}
@Override
// Try all indexes
List<LdifUser> collectedUsers = new ArrayList<LdifUser>(
- indexedUserProperties.size());
+ getIndexedUserProperties().size());
// try dn
LdifUser user = null;
try {
// throw new UnsupportedOperationException();
}
- public boolean getIsReadOnly() {
- return isReadOnly;
+ protected void loadMembers(LdifGroup group) {
+ group.directMembers = new ArrayList<Role>();
+ for (LdapName ldapName : group.getMemberNames()) {
+ LdifUser role = null;
+ if (groups.containsKey(ldapName))
+ role = groups.get(ldapName);
+ else if (users.containsKey(ldapName))
+ role = users.get(ldapName);
+ else {
+ if (getExternalRoles() != null)
+ role = (LdifUser) getExternalRoles().getRole(
+ ldapName.toString());
+ if (role == null)
+ throw new ArgeoUserAdminException("No role found for "
+ + ldapName);
+ }
+ role.directMemberOf.add(group);
+ group.directMembers.add(role);
+ }
}
}