ApplicationManager.java revision 25be0ff4f1d3a0aba597af3cebce429c72ba4203
bee2440354b4bc8796e1de0b6cbd60e1f68deba0Phill Cunnington/*
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster *
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * Copyright (c) 2009 Sun Microsystems Inc. All Rights Reserved
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster *
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * The contents of this file are subject to the terms
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * of the Common Development and Distribution License
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * (the License). You may not use this file except in
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * compliance with the License.
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster *
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * You can obtain a copy of the License at
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * https://opensso.dev.java.net/public/CDDLv1.0.html or
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * opensso/legal/CDDLv1.0.txt
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * See the License for the specific language governing
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * permission and limitations under the License.
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster *
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * When distributing Covered Code, include this CDDL
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * Header Notice in each file and include the License file
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * at opensso/legal/CDDLv1.0.txt.
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * If applicable, add the following below the CDDL Header,
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * with the fields enclosed by brackets [] replaced by
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * your own identifying information:
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * "Portions Copyrighted [year] [name of copyright owner]"
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster *
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * $Id: ApplicationManager.java,v 1.11 2010/01/13 23:41:57 veiming Exp $
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster *
bee2440354b4bc8796e1de0b6cbd60e1f68deba0Phill Cunnington * Portions Copyrighted 2013-2015 ForgeRock AS.
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster */
8af80418ba1ec431c8027fa9668e5678658d3611Allan Fosterpackage com.sun.identity.entitlement;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster
8af80418ba1ec431c8027fa9668e5678658d3611Allan Fosterimport com.sun.identity.entitlement.util.SearchFilter;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Fosterimport com.sun.identity.entitlement.util.SearchFilter.Operator;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Fosterimport com.sun.identity.shared.debug.Debug;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Fosterimport org.forgerock.guice.core.InjectorHolder;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Fosterimport org.forgerock.openam.entitlement.PolicyConstants;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Fosterimport org.forgerock.openam.entitlement.service.ResourceTypeService;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Fosterimport org.forgerock.openam.utils.CollectionUtils;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Fosterimport org.forgerock.openam.utils.StringUtils;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Fosterimport org.forgerock.util.annotations.VisibleForTesting;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster
8af80418ba1ec431c8027fa9668e5678658d3611Allan Fosterimport javax.security.auth.Subject;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Fosterimport java.lang.reflect.Constructor;
9d1321897216c79ea0639b6d8e0f92d0565876b6Jason Lemayimport java.lang.reflect.InvocationTargetException;
bee2440354b4bc8796e1de0b6cbd60e1f68deba0Phill Cunningtonimport java.security.Principal;
bee2440354b4bc8796e1de0b6cbd60e1f68deba0Phill Cunningtonimport java.util.Collections;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Fosterimport java.util.Date;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Fosterimport java.util.HashSet;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Fosterimport java.util.Map;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Fosterimport java.util.Set;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Fosterimport java.util.concurrent.ConcurrentHashMap;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Fosterimport java.util.concurrent.locks.ReentrantReadWriteLock;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster/**
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * Application Manager handles addition, deletion and listing of applications for each realm.
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster */
8af80418ba1ec431c8027fa9668e5678658d3611Allan Fosterpublic final class ApplicationManager {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster private static final Debug DEBUG = Debug.getInstance("Entitlement");
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster private static Map<String, Set<Application>> applications = new ConcurrentHashMap<String, Set<Application>>();
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster private static final ReentrantReadWriteLock readWriteLock = new ReentrantReadWriteLock();
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster private ApplicationManager() {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster }
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster /**
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * Returns the application names in a realm.
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster *
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * When performing the search using the Subject {@link PrivilegeManager#superAdminSubject},
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * the provided filters must not contain {@link Operator#LESS_THAN_OR_EQUAL_OPERATOR }
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * or {@link Operator#GREATER_THAN_OR_EQUAL_OPERATOR } as these are not supported by LDAP.
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster *
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * @param adminSubject Admin Subject who has the rights to access configuration datastore.
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * @param realm Realm name.
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * @param filters Search Filters
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * @return application names in a realm.
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster */
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster public static Set<String> search(Subject adminSubject, String realm, Set<SearchFilter> filters)
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster throws EntitlementException {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster if (adminSubject == PolicyConstants.SUPER_ADMIN_SUBJECT) {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster EntitlementConfiguration ec = EntitlementConfiguration.getInstance(adminSubject, realm);
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster return ec.searchApplicationNames(adminSubject, filters);
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster }
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster // Delegation to applications is currently not configurable, passing super admin (see AME-4959)
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster ApplicationPrivilegeManager apm =
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster ApplicationPrivilegeManager.getInstance(realm, PolicyConstants.SUPER_ADMIN_SUBJECT);
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster Set<String> applNames = apm.getApplications(ApplicationPrivilege.Action.READ);
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster return filterApplicationNames(realm, applNames, filters);
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster }
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster private static Set<String> filterApplicationNames(String realm, Set<String> applNames, Set<SearchFilter> filters) {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster Set<String> results = new HashSet<String>();
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster
bee2440354b4bc8796e1de0b6cbd60e1f68deba0Phill Cunnington if ((filters != null) && !filters.isEmpty()) {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster for (String name : applNames) {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster try {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster Application app = ApplicationManager.getApplication(
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster PolicyConstants.SUPER_ADMIN_SUBJECT, realm, name);
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster if (app != null) {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster if (match(filters, app)) {
bee2440354b4bc8796e1de0b6cbd60e1f68deba0Phill Cunnington results.add(name);
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster }
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster }
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster } catch (EntitlementException ex) {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster PolicyConstants.DEBUG.error("ApplicationManager.fitlerApplicationNames", ex);
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster }
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster }
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster } else {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster results.addAll(applNames);
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster }
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster return results;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster }
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster @VisibleForTesting
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster static boolean match(Set<SearchFilter> filters, Application app) {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster for (SearchFilter filter : filters) {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster if (Application.NAME_ATTRIBUTE.equals(filter.getName())) {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster if (!StringUtils.match(app.getName(), filter.getValue())) {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster return false;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster }
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster } else if (Application.DESCRIPTION_ATTRIBUTE.equals(filter.getName())) {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster if (!StringUtils.match(app.getDescription(), filter.getValue())) {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster return false;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster }
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster } else if (Application.CREATED_BY_ATTRIBUTE.equals(filter.getName())) {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster if (!StringUtils.match(app.getCreatedBy(), filter.getValue())) {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster return false;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster }
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster } else if (Application.LAST_MODIFIED_BY_ATTRIBUTE.equals(filter.getName())) {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster if (!StringUtils.match(app.getLastModifiedBy(), filter.getValue())) {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster return false;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster }
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster } else if (Application.CREATION_DATE_ATTRIBUTE.equals(filter.getName())) {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster if (!match(app.getCreationDate(), filter.getNumericValue(), filter.getOperator())) {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster return false;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster }
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster } else if (Application.LAST_MODIFIED_DATE_ATTRIBUTE.equals(filter.getName())){
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster if (!match(app.getLastModifiedDate(), filter.getNumericValue(), filter.getOperator())) {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster return false;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster }
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster }
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster }
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster return true;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster }
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster private static boolean match(long value, long pattern, Operator operator) {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster switch (operator) {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster case EQUALS_OPERATOR:
9d1321897216c79ea0639b6d8e0f92d0565876b6Jason Lemay return value == pattern;
9d1321897216c79ea0639b6d8e0f92d0565876b6Jason Lemay case GREATER_THAN_OPERATOR:
9d1321897216c79ea0639b6d8e0f92d0565876b6Jason Lemay return value > pattern;
9d1321897216c79ea0639b6d8e0f92d0565876b6Jason Lemay case GREATER_THAN_OR_EQUAL_OPERATOR:
9d1321897216c79ea0639b6d8e0f92d0565876b6Jason Lemay return value >= pattern;
9d1321897216c79ea0639b6d8e0f92d0565876b6Jason Lemay case LESS_THAN_OPERATOR:
9d1321897216c79ea0639b6d8e0f92d0565876b6Jason Lemay return value < pattern;
9d1321897216c79ea0639b6d8e0f92d0565876b6Jason Lemay case LESS_THAN_OR_EQUAL_OPERATOR:
9d1321897216c79ea0639b6d8e0f92d0565876b6Jason Lemay return value <= pattern;
9d1321897216c79ea0639b6d8e0f92d0565876b6Jason Lemay default:
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster return false;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster }
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster }
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster /**
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * Returns the application names in a realm.
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster *
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * @param adminSubject Admin Subject who has the rights to access
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * configuration datastore.
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * @param realm Realm name.
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * @return application names in a realm.
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster */
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster public static Set<String> getApplicationNames(
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster Subject adminSubject,
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster String realm
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster ) throws EntitlementException {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster Set<Application> appls = getApplications(adminSubject, realm);
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster Set<String> results = new HashSet<String>();
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster for (Application appl : appls) {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster results.add(appl.getName());
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster }
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster return results;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster }
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster private static Set<Application> getAllApplication(String realm)
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster throws EntitlementException {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster EntitlementConfiguration ec = EntitlementConfiguration.getInstance(
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster PolicyConstants.SUPER_ADMIN_SUBJECT, realm);
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster realm = ec.getRealmName(realm);
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster Set<Application> appls = applications.get(realm);
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster if (appls != null) {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster return appls;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster }
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster readWriteLock.writeLock().lock();
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster try {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster appls = ec.getApplications();
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster applications.put(realm, appls);
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster ReferredApplicationManager mgr = ReferredApplicationManager.getInstance();
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster Set<ReferredApplication> referredApplications = mgr.getReferredApplications(realm);
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster if (!"/".equals(realm) && (referredApplications == null || referredApplications.isEmpty())) {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster DEBUG.warning("No referred applications for sub-realm: " + realm);
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster }
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster appls.addAll(referredApplications);
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster return appls;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster } finally {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster readWriteLock.writeLock().unlock();
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster }
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster }
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster public static Set<Application> getApplications(Subject adminSubject,
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster String realm) throws EntitlementException {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster Set<Application> appls = getAllApplication(realm);
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster if (adminSubject == PolicyConstants.SUPER_ADMIN_SUBJECT) {
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster return appls;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster }
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster Set<Application> accessible = new HashSet<Application>();
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster // Delegation to applications is currently not configurable, passing super admin (see AME-4959)
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster ApplicationPrivilegeManager apm =
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster ApplicationPrivilegeManager.getInstance(realm, PolicyConstants.SUPER_ADMIN_SUBJECT);
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster Set<String> accessibleApplicationNames =
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster apm.getApplications(ApplicationPrivilege.Action.READ);
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster for (Application app : appls) {
bee2440354b4bc8796e1de0b6cbd60e1f68deba0Phill Cunnington String applicationName = app.getName();
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster Application cloned = app.clone();
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster if (accessibleApplicationNames.contains(applicationName)) {
9d1321897216c79ea0639b6d8e0f92d0565876b6Jason Lemay accessible.add(cloned);
9d1321897216c79ea0639b6d8e0f92d0565876b6Jason Lemay }
9d1321897216c79ea0639b6d8e0f92d0565876b6Jason Lemay }
9d1321897216c79ea0639b6d8e0f92d0565876b6Jason Lemay
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster return accessible;
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster }
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster /**
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * Returns application.
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster *
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * @param realm Realm name.
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * @param name Name of Application.
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster * @return application.
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster */
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster public static Application getApplicationForEvaluation(
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster String realm,
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster String name
9d1321897216c79ea0639b6d8e0f92d0565876b6Jason Lemay ) throws EntitlementException {
9d1321897216c79ea0639b6d8e0f92d0565876b6Jason Lemay return getApplication(PolicyConstants.SUPER_ADMIN_SUBJECT, realm,
8af80418ba1ec431c8027fa9668e5678658d3611Allan Foster name);
}
/**
* Returns application.
*
* @param adminSubject Admin Subject who has the rights to access
* configuration datastore.
* @param realm Realm name.
* @param name Name of Application.
* @return application.
*/
public static Application getApplication(
Subject adminSubject,
String realm,
String name
) throws EntitlementException {
if ((name == null) || (name.length() == 0)) {
name = ApplicationTypeManager.URL_APPLICATION_TYPE_NAME;
}
Set<Application> appls = getApplications(adminSubject, realm);
for (Application appl : appls) {
if (appl.getName().equals(name)) {
return appl;
}
}
// try again, to get application for sub realm.
clearCache(realm);
appls = getApplications(adminSubject, realm);
for (Application appl : appls) {
if (appl.getName().equals(name)) {
return appl;
}
}
return null;
}
/**
* Removes application.
*
* @param adminSubject Admin Subject who has the rights to access
* configuration datastore.
* @param realm Realm Name.
* @param name Application Name.
* @throws EntitlementException
*/
public static void deleteApplication(
Subject adminSubject,
String realm,
String name
) throws EntitlementException {
boolean allowed = (adminSubject == PolicyConstants.SUPER_ADMIN_SUBJECT);
if (!allowed) {
allowed = hasAccessToApplication(realm, adminSubject, name,
ApplicationPrivilege.Action.MODIFY);
}
if (!allowed) {
throw new EntitlementException(EntitlementException.PERMISSION_DENIED);
}
Application app = getApplication(adminSubject, realm, name);
if (app != null) {
if (!app.canBeDeleted(realm)) {
throw new EntitlementException(EntitlementException.APP_NOT_CREATED_POLICIES_EXIST);
}
EntitlementConfiguration ec = EntitlementConfiguration.getInstance(
adminSubject, realm);
ec.removeApplication(name);
clearCache(realm);
}
}
/**
* Saves application data.
*
* @param adminSubject Admin Subject who has the rights to access
* configuration datastore.
* @param realm Realm Name.
* @param application Application object.
*/
public static void saveApplication(
Subject adminSubject,
String realm,
Application application
) throws EntitlementException {
boolean allow = (adminSubject == PolicyConstants.SUPER_ADMIN_SUBJECT);
if (!allow) {
ApplicationPrivilegeManager apm =
ApplicationPrivilegeManager.getInstance(realm, adminSubject);
if (isNewApplication(realm, application)) {
allow = apm.canCreateApplication(realm);
} else {
allow = hasAccessToApplication(apm, application,
ApplicationPrivilege.Action.MODIFY);
}
}
if (!allow) {
throw new EntitlementException(326);
}
if (isReferredApplication(realm, application)) {
throw new EntitlementException(228);
}
if (CollectionUtils.isNotEmpty(application.getResourceTypeUuids())) {
Set<String> resourceTypeIds = application.getResourceTypeUuids();
// When this class is refactored (AME-6287) this dependency should be injected.
ResourceTypeService resourceTypeService = InjectorHolder.getInstance(ResourceTypeService.class);
for (String resourceTypeId : resourceTypeIds) {
if (!resourceTypeService.contains(adminSubject, realm, resourceTypeId)) {
throw new EntitlementException(EntitlementException.INVALID_RESOURCE_TYPE, resourceTypeId);
}
}
}
Date date = new Date();
Set<Principal> principals = adminSubject.getPrincipals();
String principalName = ((principals != null) && !principals.isEmpty()) ?
principals.iterator().next().getName() : null;
if (application.getCreationDate() == -1) {
long creationDate = getApplicationCreationDate(realm,
application.getName());
if (creationDate == -1) {
application.setCreationDate(date.getTime());
if (principalName != null) {
application.setCreatedBy(principalName);
}
} else {
application.setCreationDate(creationDate);
String createdBy = application.getCreatedBy();
if ((createdBy == null) || (createdBy.trim().length() == 0)) {
createdBy = getApplicationCreatedBy(realm,
application.getName());
if ((createdBy == null) || (createdBy.trim().length() == 0))
{
application.setCreatedBy(principalName);
} else {
application.setCreatedBy(createdBy);
}
}
}
}
application.setLastModifiedDate(date.getTime());
if (principalName != null) {
application.setLastModifiedBy(principalName);
}
EntitlementConfiguration ec = EntitlementConfiguration.getInstance(
adminSubject, realm);
ec.storeApplication(application);
clearCache(realm);
}
private static String getApplicationCreatedBy(
String realm,
String applName
) {
try {
Application appl = getApplication(PolicyConstants.SUPER_ADMIN_SUBJECT,
realm, applName);
return (appl == null) ? null : appl.getCreatedBy();
} catch (EntitlementException ex) {
// new application.
return null;
}
}
private static long getApplicationCreationDate(
String realm,
String applName
) {
try {
Application appl = getApplication(PolicyConstants.SUPER_ADMIN_SUBJECT,
realm, applName);
return (appl == null) ? -1 : appl.getCreationDate();
} catch (EntitlementException ex) {
// new application.
return -1;
}
}
private static boolean isReferredApplication(
String realm,
Application application) throws EntitlementException {
Set<ReferredApplication> referredAppls =
ReferredApplicationManager.getInstance().getReferredApplications(
realm);
for (ReferredApplication ra : referredAppls) {
if (ra.getName().equals(application.getName())) {
return true;
}
}
return false;
}
private static boolean hasAccessToApplication(
String realm,
Subject adminSubject,
String applicationName,
ApplicationPrivilege.Action action) {
ApplicationPrivilegeManager apm =
ApplicationPrivilegeManager.getInstance(realm,
adminSubject);
Set<String> applicationNames = apm.getApplications(action);
// applicationNames may be empty if the sub realm is removed.
// or the sub realm really do not have referral privilege assigned to
// it. In the latter case, clearing the cache for referral privilege
// should be ok.
return applicationNames.isEmpty() ||
applicationNames.contains(applicationName);
}
private static boolean hasAccessToApplication(
ApplicationPrivilegeManager apm,
Application application,
ApplicationPrivilege.Action action) {
Set<String> applNames = apm.getApplications(action);
return applNames.contains(application.getName());
}
private static boolean isNewApplication(
String realm,
Application application
) throws EntitlementException {
Set<Application> existingAppls = getAllApplication(realm);
String applName = application.getName();
for (Application app : existingAppls) {
if (app.getName().equals(applName)) {
return false;
}
}
return true;
}
/**
* Clears the cached applications. Must be called when notifications are
* received for changes to applications.
*/
public static void clearCache(String realm) {
for (String name : applications.keySet()) {
if (name.equalsIgnoreCase(realm)) {
applications.remove(name);
break;
}
}
}
/**
* Refers resources to another realm.
*
* @param adminSubject Admin Subject who has the rights to access
* configuration datastore.
* @param parentRealm Parent realm name.
* @param referRealm Referred realm name.
* @param applicationName Application name.
* @param resources Referred resources.
* @throws EntitlementException if resources cannot be referred.
*/
public static void referApplication(
Subject adminSubject,
String parentRealm,
String referRealm,
String applicationName,
Set<String> resources
) throws EntitlementException {
boolean allowed = (adminSubject == PolicyConstants.SUPER_ADMIN_SUBJECT);
if (!allowed) {
// Delegation to applications is currently not configurable, passing super admin (see AME-4959)
allowed = hasAccessToApplication(parentRealm, PolicyConstants.SUPER_ADMIN_SUBJECT,
applicationName, ApplicationPrivilege.Action.MODIFY);
}
if (!allowed) {
throw new EntitlementException(326);
}
Application appl = getApplication(PolicyConstants.SUPER_ADMIN_SUBJECT,
parentRealm, applicationName);
if (appl == null) {
Object[] params = {parentRealm, referRealm, applicationName};
throw new EntitlementException(280, params);
}
ReferredApplicationManager.getInstance().clearCache(referRealm);
}
/**
* Derefers resources from a realm.
*
* @param adminSubject Admin Subject who has the rights to access
* configuration datastore.
* @param referRealm Referred realm name,
* @param applicationName Application name.
* @param resources Resources to be dereferred.
* @throws EntitlementException if resources cannot be dereferred.
*/
public static void dereferApplication(
Subject adminSubject,
String referRealm,
String applicationName,
Set<String> resources
) throws EntitlementException {
boolean allowed = (adminSubject == PolicyConstants.SUPER_ADMIN_SUBJECT);
if (!allowed) {
// Delegation to applications is currently not configurable, passing super admin (see AME-4959)
allowed = hasAccessToApplication(referRealm, PolicyConstants.SUPER_ADMIN_SUBJECT,
applicationName, ApplicationPrivilege.Action.MODIFY);
}
if (!allowed) {
throw new EntitlementException(326);
}
ReferredApplicationManager.getInstance().clearCache(referRealm);
}
/**
* Returns referred resources for a realm.
*
* @param adminSubject Admin Subject who has the rights to access
* configuration datastore.
* @param realm Realm name
* @param applicationTypeName Application Type Name.
* @return referred resources for a realm.
* @throws EntitlementException if referred resources cannot be returned.
*/
public static Set<String> getReferredResources(
Subject adminSubject,
String realm,
String applicationTypeName
) throws EntitlementException {
boolean allowed = (adminSubject == PolicyConstants.SUPER_ADMIN_SUBJECT);
if (!allowed) {
// Delegation to applications is currently not configurable, passing super admin (see AME-4959)
allowed = hasAccessToApplication(realm, PolicyConstants.SUPER_ADMIN_SUBJECT,
applicationTypeName, ApplicationPrivilege.Action.READ);
}
if (!allowed) {
return Collections.EMPTY_SET;
}
PrivilegeIndexStore pis = PrivilegeIndexStore.getInstance(
adminSubject, realm);
return pis.getReferredResources(applicationTypeName);
}
/**
* Creates an application.
*
* @param name Name of application.
* @param applicationType application type.
* @throws EntitlementException if application class is not found.
*/
public static Application newApplication(String name, ApplicationType applicationType) throws EntitlementException {
Class clazz = applicationType.getApplicationClass();
Class[] parameterTypes = {String.class, ApplicationType.class};
Constructor constructor;
try {
constructor = clazz.getConstructor(parameterTypes);
Object[] parameters = {name, applicationType};
return (Application) constructor.newInstance(parameters);
} catch (NoSuchMethodException ex) {
throw new EntitlementException(6, ex);
} catch (SecurityException ex) {
throw new EntitlementException(6, ex);
} catch (InstantiationException ex) {
throw new EntitlementException(6, ex);
} catch (IllegalAccessException ex) {
throw new EntitlementException(6, ex);
} catch (IllegalArgumentException ex) {
throw new EntitlementException(6, ex);
} catch (InvocationTargetException ex) {
throw new EntitlementException(6, ex);
}
}
/**
* Replaces an existing application with a newer version of itself.
*
* @param oldApplication The application to update
* @param newApplication The updated version of the application
* @retun the new application
*/
public static void updateApplication(Application oldApplication, Application newApplication, Subject subject,
String realm)
throws EntitlementException {
readWriteLock.writeLock().lock();
try {
newApplication.setCreationDate(oldApplication.getCreationDate());
newApplication.setCreatedBy(oldApplication.getCreatedBy());
deleteApplication(subject, realm, oldApplication.getName());
saveApplication(subject, realm, newApplication);
} finally {
readWriteLock.writeLock().unlock();
}
}
}