package org.dcache.auth; import org.springframework.beans.factory.annotation.Required; import javax.security.auth.Subject; import java.security.Principal; import java.util.Collections; import java.util.Set; import java.util.regex.Matcher; import java.util.regex.Pattern; import diskCacheV111.util.CacheException; import org.dcache.auth.attributes.LoginAttribute; /** * Anonymous login strategy, used on the xrootd door when * no authentication is specified. The behaviour follows the old door * behaviour - depending on configuration, a NOBODY user, a ROOT user or a * user based on the configured uid/gid is returned as a result of the * login operation. * * @author tzangerl */ public class AnonymousLoginStrategy implements LoginStrategy { public static final String USER_ROOT = "root"; public static final String USER_NOBODY = "nobody"; public static final Pattern USER_PATTERN = Pattern.compile("(\\d+):((\\d+)(,(\\d+))*)"); private static final Set<LoginAttribute> NO_ATTRIBUTES = Collections.emptySet(); private Subject _subject; public AnonymousLoginStrategy() { } @Override public LoginReply login(Subject subject) throws CacheException { return new LoginReply(_subject, NO_ATTRIBUTES); } @Override public Principal map(Principal principal) throws CacheException { return null; } @Override public Set<Principal> reverseMap(Principal principal) throws CacheException { return null; } /** * Parses a string on the form UID:GID(,GID)* and returns a * corresponding Subject. */ private Subject parseUidGidList(String user) { Matcher matcher = USER_PATTERN.matcher(user); if (!matcher.matches()) { throw new IllegalArgumentException("Invalid user string"); } Subject subject = new Subject(); int uid = Integer.parseInt(matcher.group(1)); Set<Principal> principals = subject.getPrincipals(); principals.add(new UidPrincipal(uid)); boolean primary = true; for (String group: matcher.group(2).split(",")) { int gid = Integer.parseInt(group); principals.add(new GidPrincipal(gid, primary)); primary = false; } subject.setReadOnly(); return subject; } @Required public void setUser(String user) { switch (user) { case USER_ROOT: _subject = Subjects.ROOT; break; case USER_NOBODY: _subject = Subjects.NOBODY; break; default: _subject = parseUidGidList(user); break; } } }