/** * Return <code>true</code> if the specified Principal has the specified security role, within the * context of this Realm; otherwise return <code>false</code>. * * <p>Since the Principal, in the JaasSecurityManager, has been stored in its cache using the * JOSSO Single Sign-On Session Identifier Principal (see isValid method), when roles are checked * , the Principal to be submitted to the overriden operation is not the user principal but the * JOSSO Session Id Principal. * * @param principal Principal for whom the role is to be checked * @param role Security role to be checked */ public boolean hasRole(Principal principal, String role) { boolean hasRole = false; try { Context securityCtx = null; securityCtx = prepareENC(); if (securityCtx == null) { logger.error("No security context for authenticate(String, String)"); return false; } logger.debug("hasRole(" + principal + "," + role + ")"); // Get the JBoss security manager from the ENC context SubjectSecurityManager securityMgr = (SubjectSecurityManager) securityCtx.lookup("securityMgr"); if (!isSSODomain(securityMgr.getSecurityDomain())) { // This is not a SSO Security domain, let JBoss realm handle this ... return super.hasRole(principal, role); } Subject activeSubject = securityMgr.getActiveSubject(); logger.debug("Authenticated Subject: " + activeSubject); CatalinaSSOUser ssoUser = CatalinaSSOUser.newInstance(this, activeSubject); hasRole = super.hasRole(ssoUser, role); } catch (NamingException e) { principal = null; logger.error("Error during authenticate", e); } return hasRole; }
/** * Return the Principal associated with the specified username and credentials, if there is one; * otherwise return null. * * <p>The method was completely rewritten since the overriden operation, on succesfull * authentication, sets as the authenticated Principal a SimplePrincipal instantiated using the * provided username. The problem is that in JOSSO the username is a SSO Session Id, not a * username. So we need to set the SSOUser returned by the Gateway as the authenticatd Principal. * Since the JaasSecurityManager caches the authenticated user using the Principal referring to a * JOSSO Session Id, we will need to map, for example when roles are checked against the realm, a * user Principal back to its JOSSO Session Identifier Principal. This way the the user and its * roles can be retrieved correctly by the JaasSecurityManager. * * @param username Username of the Principal to look up * @param credentials Password or other credentials to use in authenticating this username */ public Principal authenticate(String username, String credentials) { logger.debug("Begin authenticate, username="******"No security context for authenticate(String, String)"); return null; } // Get the JBoss security manager from the ENC context SubjectSecurityManager securityMgr = (SubjectSecurityManager) securityCtx.lookup("securityMgr"); if (!isSSODomain(securityMgr.getSecurityDomain())) { // This is not a SSO Security domain, let JBoss realm handle this ... return super.authenticate(username, credentials); } principal = new SimplePrincipal(username); char[] passwordChars = null; if (credentials != null) passwordChars = credentials.toCharArray(); String requester = ""; // Check for nulls ? SSOAgentRequest request = AbstractSSOAgent._currentRequest.get(); if (request == null) logger.error( "No SSO Agent request found in thread local variable, can't identify requester!"); SSOAgent agent = Lookup.getInstance().lookupSSOAgent(); SSOIdentityManagerService im = request.getConfig(agent).getIdentityManagerService(); if (im == null) im = agent.getSSOIdentityManager(); requester = request.getRequester(); ssoUser = im.findUserInSession(requester, username); if (ssoUser != null) { logger.debug("User: "******" is authenticated"); Subject subject = new Subject(); subject.getPrincipals().add(ssoUser); logger.warn("WARN Cannot identify requester!"); SSORole[] ssoRolePrincipals = im.findRolesBySSOSessionId(requester, username); Group targetGrp = new BaseRoleImpl("Roles"); for (int i = 0; i < ssoRolePrincipals.length; i++) { subject.getPrincipals().add(ssoRolePrincipals[i]); targetGrp.addMember(ssoRolePrincipals[i]); // Add user role to "Roles" group } // Add the "Roles" group to the Subject so that JBoss can fetch user roles. subject.getPrincipals().add(targetGrp); logger.debug("Authenticated Subject: " + subject); // Make the cache aware of the user-session association so that // it can handle correctly cache entry lookups. // _cachePolicy.attachSessionToUser(principal, ssoUser); // Instead of associating the Principal used for authenticating (which is a // session id), sets the authenticated principal to the SSOUser part of the // Subject returned by the Gateway. JBossSecurityAssociationActions.setPrincipalInfo(ssoUser, passwordChars, subject); // Get the CallerPrincipal mapping RealmMapping rm = (RealmMapping) securityCtx.lookup("realmMapping"); Principal oldPrincipal = ssoUser; principal = rm.getPrincipal(oldPrincipal); logger.debug("Mapped from input principal: " + oldPrincipal + " to: " + principal); if (!principal.equals(oldPrincipal)) { _userPrincipalMap.put(principal, oldPrincipal); } } else { principal = null; logger.debug("User: "******" is NOT authenticated"); } } catch (NamingException e) { principal = null; logger.error("Error during authenticate", e); } catch (SSOIdentityException e) { // Ignore this ... (user does not exist for this session) if (logger.isDebugEnabled()) { logger.debug(e.getMessage()); } principal = null; } catch (Exception e) { logger.error("Session authentication failed : " + username, e); throw new RuntimeException("Fatal error authenticating session : " + e); } logger.debug("End authenticate, principal=" + ssoUser); return ssoUser; }