]> git.argeo.org Git - lgpl/argeo-commons.git/blobdiff - security/runtime/org.argeo.security.core/src/main/java/org/argeo/security/OsAuthenticationToken.java
Introduce OSAuthentication
[lgpl/argeo-commons.git] / security / runtime / org.argeo.security.core / src / main / java / org / argeo / security / OsAuthenticationToken.java
diff --git a/security/runtime/org.argeo.security.core/src/main/java/org/argeo/security/OsAuthenticationToken.java b/security/runtime/org.argeo.security.core/src/main/java/org/argeo/security/OsAuthenticationToken.java
new file mode 100644 (file)
index 0000000..9fba6f0
--- /dev/null
@@ -0,0 +1,157 @@
+package org.argeo.security;
+
+import java.security.AccessController;
+import java.security.Principal;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Collections;
+import java.util.List;
+import java.util.Set;
+
+import javax.security.auth.Subject;
+
+import org.argeo.ArgeoException;
+import org.argeo.OperatingSystem;
+import org.springframework.security.Authentication;
+import org.springframework.security.GrantedAuthority;
+import org.springframework.security.GrantedAuthorityImpl;
+import org.springframework.security.userdetails.UserDetails;
+
+/** Abstracts principals provided by com.sun.security.auth.module login modules. */
+public class OsAuthenticationToken implements Authentication {
+       private static final long serialVersionUID = -7544626794250917244L;
+
+       final Class<? extends Principal> osUserPrincipalClass;
+       final Class<? extends Principal> osUserIdPrincipalClass;
+       final Class<? extends Principal> osGroupIdPrincipalClass;
+
+       private List<GrantedAuthority> grantedAuthorities;
+
+       private UserDetails details;
+
+       /** Request */
+       public OsAuthenticationToken(GrantedAuthority[] grantedAuthorities) {
+               this.grantedAuthorities = grantedAuthorities != null ? Arrays
+                               .asList(grantedAuthorities) : null;
+               ClassLoader cl = getClass().getClassLoader();
+               switch (OperatingSystem.os) {
+               case OperatingSystem.WINDOWS:
+                       osUserPrincipalClass = getPrincipalClass(cl,
+                                       "com.sun.security.auth.NTUserPrincipal");
+                       osUserIdPrincipalClass = getPrincipalClass(cl,
+                                       "com.sun.security.auth.NTSidUserPrincipal");
+                       osGroupIdPrincipalClass = getPrincipalClass(cl,
+                                       "com.sun.security.auth.NTSidGroupPrincipal");
+                       break;
+               case OperatingSystem.NIX:
+                       osUserPrincipalClass = getPrincipalClass(cl,
+                                       "com.sun.security.auth.UnixPrincipal");
+                       osUserIdPrincipalClass = getPrincipalClass(cl,
+                                       "com.sun.security.auth.UnixNumericUserPrincipal");
+                       osGroupIdPrincipalClass = getPrincipalClass(cl,
+                                       "com.sun.security.auth.UnixNumericGroupPrincipal");
+                       break;
+               case OperatingSystem.SOLARIS:
+                       osUserPrincipalClass = getPrincipalClass(cl,
+                                       "com.sun.security.auth.SolarisPrincipal");
+                       osUserIdPrincipalClass = getPrincipalClass(cl,
+                                       "com.sun.security.auth.SolarisNumericUserPrincipal");
+                       osGroupIdPrincipalClass = getPrincipalClass(cl,
+                                       "com.sun.security.auth.SolarisNumericGroupPrincipal");
+                       break;
+
+               default:
+                       throw new ArgeoException("Unsupported operating system "
+                                       + OperatingSystem.os);
+               }
+
+       }
+
+       /** Authenticated */
+       public OsAuthenticationToken() {
+               this(null);
+       }
+
+       public String getName() {
+               return getUser().getName();
+       }
+
+       public GrantedAuthority[] getAuthorities() {
+               // grantedAuthorities should not be null at this stage
+               List<GrantedAuthority> gas = new ArrayList<GrantedAuthority>(
+                               grantedAuthorities);
+               for (Principal groupPrincipal : getGroupsIds()) {
+                       gas.add(new GrantedAuthorityImpl("OSGROUP_"
+                                       + groupPrincipal.getName()));
+               }
+               return gas.toArray(new GrantedAuthority[gas.size()]);
+       }
+
+       public UserDetails getDetails() {
+               return details;
+       }
+
+       public void setDetails(UserDetails details) {
+               this.details = details;
+       }
+
+       public boolean isAuthenticated() {
+               return grantedAuthorities != null;
+       }
+
+       public void setAuthenticated(boolean isAuthenticated)
+                       throws IllegalArgumentException {
+               if (grantedAuthorities != null)
+                       grantedAuthorities.clear();
+               grantedAuthorities = null;
+       }
+
+       @SuppressWarnings("unchecked")
+       protected static Class<? extends Principal> getPrincipalClass(
+                       ClassLoader cl, String className) {
+               try {
+                       return (Class<? extends Principal>) cl.loadClass(className);
+               } catch (ClassNotFoundException e) {
+                       throw new ArgeoException("Cannot load principal class", e);
+               }
+       }
+
+       public Object getPrincipal() {
+               return getUser();
+       }
+
+       public Principal getUser() {
+               Subject subject = Subject.getSubject(AccessController.getContext());
+               Set<? extends Principal> userPrincipals = subject
+                               .getPrincipals(osUserPrincipalClass);
+               if (userPrincipals == null || userPrincipals.size() == 0)
+                       throw new ArgeoException("No OS principal");
+               if (userPrincipals.size() > 1)
+                       throw new ArgeoException("More than one OS principal");
+               Principal user = userPrincipals.iterator().next();
+               return user;
+       }
+
+       public Principal getUserId() {
+               Subject subject = Subject.getSubject(AccessController.getContext());
+               Set<? extends Principal> userIdsPrincipals = subject
+                               .getPrincipals(osUserIdPrincipalClass);
+               if (userIdsPrincipals == null || userIdsPrincipals.size() == 0)
+                       throw new ArgeoException("No user id principal");
+               if (userIdsPrincipals.size() > 1)
+                       throw new ArgeoException("More than one user id principal");
+               Principal userId = userIdsPrincipals.iterator().next();
+               return userId;
+       }
+
+       public Set<? extends Principal> getGroupsIds() {
+               Subject subject = Subject.getSubject(AccessController.getContext());
+               return (Set<? extends Principal>) subject
+                               .getPrincipals(osGroupIdPrincipalClass);
+       }
+
+       public Object getCredentials() {
+               return "";
+       }
+
+}