@Override public void loginUser( HttpSession session, String username, String password, Long domainId, String domainPath, String loginIpAddress, Map<String, Object[]> requestParameters) throws CloudAuthenticationException { // We will always use domainId first. If that does not exist, we will use domain name. If THAT // doesn't exist // we will default to ROOT if (domainId == null) { if (domainPath == null || domainPath.trim().length() == 0) { domainId = Domain.ROOT_DOMAIN; } else { Domain domainObj = _domainMgr.findDomainByPath(domainPath); if (domainObj != null) { domainId = domainObj.getId(); } else { // if an unknown path is passed in, fail the login call throw new CloudAuthenticationException( "Unable to find the domain from the path " + domainPath); } } } UserAccount userAcct = _accountMgr.authenticateUser( username, password, domainId, loginIpAddress, requestParameters); if (userAcct != null) { String timezone = userAcct.getTimezone(); float offsetInHrs = 0f; if (timezone != null) { TimeZone t = TimeZone.getTimeZone(timezone); s_logger.info("Current user logged in under " + timezone + " timezone"); java.util.Date date = new java.util.Date(); long longDate = date.getTime(); float offsetInMs = (t.getOffset(longDate)); offsetInHrs = offsetInMs / (1000 * 60 * 60); s_logger.info("Timezone offset from UTC is: " + offsetInHrs); } Account account = _accountMgr.getAccount(userAcct.getAccountId()); // set the userId and account object for everyone session.setAttribute("userid", userAcct.getId()); UserVO user = (UserVO) _accountMgr.getActiveUser(userAcct.getId()); if (user.getUuid() != null) { session.setAttribute("user_UUID", user.getUuid()); } session.setAttribute("username", userAcct.getUsername()); session.setAttribute("firstname", userAcct.getFirstname()); session.setAttribute("lastname", userAcct.getLastname()); session.setAttribute("accountobj", account); session.setAttribute("account", account.getAccountName()); session.setAttribute("domainid", account.getDomainId()); DomainVO domain = (DomainVO) _domainMgr.getDomain(account.getDomainId()); if (domain.getUuid() != null) { session.setAttribute("domain_UUID", domain.getUuid()); } session.setAttribute("type", Short.valueOf(account.getType()).toString()); session.setAttribute("registrationtoken", userAcct.getRegistrationToken()); session.setAttribute("registered", new Boolean(userAcct.isRegistered()).toString()); if (timezone != null) { session.setAttribute("timezone", timezone); session.setAttribute("timezoneoffset", Float.valueOf(offsetInHrs).toString()); } // (bug 5483) generate a session key that the user must submit on every request to prevent // CSRF, add that // to the login response so that session-based authenticators know to send the key back SecureRandom sesssionKeyRandom = new SecureRandom(); byte sessionKeyBytes[] = new byte[20]; sesssionKeyRandom.nextBytes(sessionKeyBytes); String sessionKey = Base64.encodeBase64String(sessionKeyBytes); session.setAttribute("sessionkey", sessionKey); return; } throw new CloudAuthenticationException( "Failed to authenticate user " + username + " in domain " + domainId + "; please provide valid credentials"); }
@Test public void testAuthenticate() throws Exception { SAML2LoginAPIAuthenticatorCmd cmd = Mockito.spy(new SAML2LoginAPIAuthenticatorCmd()); Field apiServerField = SAML2LoginAPIAuthenticatorCmd.class.getDeclaredField("_apiServer"); apiServerField.setAccessible(true); apiServerField.set(cmd, apiServer); Field managerField = SAML2LoginAPIAuthenticatorCmd.class.getDeclaredField("_samlAuthManager"); managerField.setAccessible(true); managerField.set(cmd, samlAuthManager); Field accountServiceField = BaseCmd.class.getDeclaredField("_accountService"); accountServiceField.setAccessible(true); accountServiceField.set(cmd, accountService); Field domainMgrField = SAML2LoginAPIAuthenticatorCmd.class.getDeclaredField("_domainMgr"); domainMgrField.setAccessible(true); domainMgrField.set(cmd, domainMgr); Field userAccountDaoField = SAML2LoginAPIAuthenticatorCmd.class.getDeclaredField("_userAccountDao"); userAccountDaoField.setAccessible(true); userAccountDaoField.set(cmd, userAccountDao); String spId = "someSPID"; String url = "someUrl"; KeyPair kp = SAMLUtils.generateRandomKeyPair(); X509Certificate cert = SAMLUtils.generateRandomX509Certificate(kp); SAMLProviderMetadata providerMetadata = new SAMLProviderMetadata(); providerMetadata.setEntityId("random"); providerMetadata.setSigningCertificate(cert); providerMetadata.setEncryptionCertificate(cert); providerMetadata.setKeyPair(kp); providerMetadata.setSsoUrl("http://test.local"); providerMetadata.setSloUrl("http://test.local"); Mockito.when(session.getAttribute(Mockito.anyString())).thenReturn(null); Mockito.when(domain.getId()).thenReturn(1L); Mockito.when(domainMgr.getDomain(Mockito.anyString())).thenReturn(domain); UserAccountVO user = new UserAccountVO(); user.setId(1000L); Mockito.when(userAccountDao.getUserAccount(Mockito.anyString(), Mockito.anyLong())) .thenReturn(user); Mockito.when(apiServer.verifyUser(Mockito.anyLong())).thenReturn(false); Mockito.when(samlAuthManager.getSPMetadata()).thenReturn(providerMetadata); Mockito.when(samlAuthManager.getIdPMetadata(Mockito.anyString())).thenReturn(providerMetadata); Map<String, Object[]> params = new HashMap<String, Object[]>(); // SSO redirection test cmd.authenticate( "command", params, session, InetAddress.getByName("127.0.0.1"), HttpUtils.RESPONSE_TYPE_JSON, new StringBuilder(), req, resp); Mockito.verify(resp, Mockito.times(1)).sendRedirect(Mockito.anyString()); // SSO SAMLResponse verification test, this should throw ServerApiException for auth failure params.put(SAMLPluginConstants.SAML_RESPONSE, new String[] {"Some String"}); Mockito.stub(cmd.processSAMLResponse(Mockito.anyString())).toReturn(buildMockResponse()); try { cmd.authenticate( "command", params, session, InetAddress.getByName("127.0.0.1"), HttpUtils.RESPONSE_TYPE_JSON, new StringBuilder(), req, resp); } catch (ServerApiException ignored) { } Mockito.verify(userAccountDao, Mockito.times(0)) .getUserAccount(Mockito.anyString(), Mockito.anyLong()); Mockito.verify(apiServer, Mockito.times(0)).verifyUser(Mockito.anyLong()); }
@Override public Long fetchDomainId(String domainUUID) { return _domainMgr.getDomain(domainUUID).getId(); }
@Override public List<SecurityGroupRulesVO> searchForSecurityGroupRules(ListSecurityGroupsCmd cmd) throws PermissionDeniedException, InvalidParameterValueException { Account caller = UserContext.current().getCaller(); Long domainId = cmd.getDomainId(); String accountName = cmd.getAccountName(); Long instanceId = cmd.getVirtualMachineId(); String securityGroup = cmd.getSecurityGroupName(); Long id = cmd.getId(); Long accountId = null; if (instanceId != null) { UserVmVO userVM = _userVMDao.findById(instanceId); if (userVM == null) { throw new InvalidParameterValueException( "Unable to list network groups for virtual machine instance " + instanceId + "; instance not found."); } _accountMgr.checkAccess(caller, null, userVM); return listSecurityGroupRulesByVM(instanceId.longValue()); } if (_accountMgr.isAdmin(caller.getType())) { if (domainId != null) { Domain domain = _domainMgr.getDomain(domainId); if (domain == null) { throw new InvalidParameterValueException("Unable to find domain by id " + domainId); } _accountMgr.checkAccess(caller, domain); if (accountName != null) { Account account = _accountMgr.getActiveAccountByName(accountName, domainId); if (account == null) { throw new InvalidParameterValueException( "Unable to find account " + accountName + " in domain " + domainId); } _accountMgr.checkAccess(caller, null, account); accountId = account.getId(); } } } else { // regular user can see only his own security groups accountId = caller.getId(); } List<SecurityGroupRulesVO> securityRulesList = new ArrayList<SecurityGroupRulesVO>(); Filter searchFilter = new Filter(SecurityGroupVO.class, "id", true, cmd.getStartIndex(), cmd.getPageSizeVal()); Object keyword = cmd.getKeyword(); SearchBuilder<SecurityGroupVO> sb = _securityGroupDao.createSearchBuilder(); sb.and("id", sb.entity().getId(), SearchCriteria.Op.EQ); sb.and("accountId", sb.entity().getAccountId(), SearchCriteria.Op.EQ); sb.and("name", sb.entity().getName(), SearchCriteria.Op.EQ); sb.and("domainId", sb.entity().getDomainId(), SearchCriteria.Op.EQ); // only do a recursive domain search if the search is not limited by account or instance if ((accountId == null) && (instanceId == null) && (caller.getType() == Account.ACCOUNT_TYPE_DOMAIN_ADMIN)) { SearchBuilder<DomainVO> domainSearch = _domainDao.createSearchBuilder(); domainSearch.and("path", domainSearch.entity().getPath(), SearchCriteria.Op.LIKE); sb.join( "domainSearch", domainSearch, sb.entity().getDomainId(), domainSearch.entity().getId(), JoinBuilder.JoinType.INNER); } SearchCriteria<SecurityGroupVO> sc = sb.create(); if (id != null) { sc.setParameters("id", id); } if (securityGroup != null) { sc.setParameters("name", securityGroup); } if (accountId != null) { sc.setParameters("accountId", accountId); } // only do a recursive domain search if the search is not limited by account or instance if ((accountId == null) && (instanceId == null) && (caller.getType() == Account.ACCOUNT_TYPE_DOMAIN_ADMIN)) { DomainVO domain = _domainDao.findById(caller.getDomainId()); sc.setJoinParameters("domainSearch", "path", domain.getPath() + "%"); } if (keyword != null) { SearchCriteria<SecurityGroupRulesVO> ssc = _securityGroupRulesDao.createSearchCriteria(); ssc.addOr("name", SearchCriteria.Op.LIKE, "%" + keyword + "%"); ssc.addOr("description", SearchCriteria.Op.LIKE, "%" + keyword + "%"); sc.addAnd("name", SearchCriteria.Op.SC, ssc); } List<SecurityGroupVO> securityGroups = _securityGroupDao.search(sc, searchFilter); for (SecurityGroupVO group : securityGroups) { securityRulesList.addAll(_securityGroupRulesDao.listSecurityRulesByGroupId(group.getId())); } return securityRulesList; }