/** * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER. * * Copyright (c) 2006 Sun Microsystems Inc. All Rights Reserved * * The contents of this file are subject to the terms * of the Common Development and Distribution License * (the License). You may not use this file except in * compliance with the License. * * You can obtain a copy of the License at * https://opensso.dev.java.net/public/CDDLv1.0.html or * opensso/legal/CDDLv1.0.txt * See the License for the specific language governing * permission and limitations under the License. * * When distributing Covered Code, include this CDDL * Header Notice in each file and include the License file * at opensso/legal/CDDLv1.0.txt. * If applicable, add the following below the CDDL Header, * with the fields enclosed by brackets [] replaced by * your own identifying information: * "Portions Copyrighted [year] [name of copyright owner]" * * $Id: AuthenticateToServiceCondition.java,v 1.7 2009/05/05 18:29:01 mrudul_uchil Exp $ * */ /* * Portions Copyright 2014 ForgeRock AS */ package com.sun.identity.policy.plugins; import com.sun.identity.authentication.util.AMAuthUtils; import com.sun.identity.policy.interfaces.Condition; import com.sun.identity.policy.ConditionDecision; import com.sun.identity.policy.PolicyManager; import com.sun.identity.policy.PolicyException; import com.sun.identity.policy.ResBundleUtils; import com.sun.identity.policy.Syntax; import com.iplanet.sso.SSOToken; import com.iplanet.sso.SSOException; import com.sun.identity.shared.debug.Debug; import java.util.Map; import java.util.HashMap; import java.util.Set; import java.util.HashSet; import java.util.Iterator; import java.util.List; import java.util.ArrayList; import java.util.Locale; import java.util.Collections; /** * The class AuthenticateToServiceCondition is a plugin * implementation of Condition that lets you specify * the service to which user should authenticate for the policy to apply * * @deprecated See {@link org.forgerock.openam.entitlement.conditions.environment.AuthenticateToServiceCondition} * instead. */ @Deprecated public class AuthenticateToServiceCondition implements Condition { private static final Debug DEBUG = Debug.getInstance(PolicyManager.POLICY_DEBUG_NAME); private Map properties; private String authenticateToService = null; private boolean realmEmpty = false; private static List propertyNames = new ArrayList(1); static { propertyNames.add(AUTHENTICATE_TO_SERVICE); } /** No argument constructor */ public AuthenticateToServiceCondition() { } /** * Returns a list of property names for the condition. * * @return list of property names */ public List getPropertyNames() { return (new ArrayList(propertyNames)); } /** * Returns the syntax for a property name * @see com.sun.identity.policy.Syntax * * @param property property name * * @return Syntax for the property name */ public Syntax getPropertySyntax(String property) { return Syntax.NONE; } /** * Returns the display name for the property name. * The locale variable could be used by the plugin to * customize the display name for the given locale. * The locale variable could be null, in which * case the plugin must use the default locale. * * @param property property name * @param locale locale for which the property name must be customized * @return display name for the property name * @throws PolicyException if unable to get display name */ public String getDisplayName(String property, Locale locale) throws PolicyException { return property; } /** * Returns a set of valid values given the property name. This method * is called if the property Syntax is either the SINGLE_CHOICE or * MULTIPLE_CHOICE. * * @param property property name * @return Set of valid values for the property. * @throws PolicyException if unable to get valid values */ public Set getValidValues(String property) throws PolicyException { return Collections.EMPTY_SET; } /** Sets the properties of the condition. * Evaluation of ConditionDecision is influenced by these * properties. * @param properties the properties of the condition that governs * whether a policy applies. The properties should * define value for the key AUTHENTICATE_TO_SERVICE. * The value * should be a Set with only one element. The element should be * a String, the realm name for which * the user should authenticate * for the policy to apply. Please note that * properties is not cloned by the method. * * @throws PolicyException if properties is null * or does not contain * value for the key AUTHENTICATE_TO_SERVICE or * the value of the key is not a Set with one * String element * * @see #REQUEST_AUTHENTICATED_TO_SERVICES */ public void setProperties(Map properties) throws PolicyException { this.properties = properties; validateProperties(); } /** Returns the properties of the condition. * @return unmodifiable map view of properties that govern the * evaluation of the condition. * Please note that properties is not cloned before returning * @see #setProperties(Map) */ public Map getProperties() { return (properties == null) ? null : Collections.unmodifiableMap(properties); } /** * Returns the decision computed by this condition object, based on the * map of environment parameters * * @param token single sign on token of the user * * @param env request specific environment map of key/value pairs * AuthenticateToServiceCondition looks for value of key * REQUEST_AUTHENTICATED_TO_SERVICES in the map. * The value should be a Set with String * elements. * If the env parameter is null or does not * define the value for * REQUEST_AUTHENTICATED_TO_SERVICES, value for * REQUEST_AUTHENTICATED_TO_SERVICES is computed * from sso token. * * @return the condition decision. The condition decision encapsulates * whether a policy applies for the request and advice messages * generated by the condition. * * Policy framework continues evaluating a policy only if it applies * to the request as indicated by the ConditionDecision. * Otherwise, further evaluation of the policy is skipped. * However, the advice messages encapsulated in the * ConditionDecision are aggregated and passed up, encapsulated * in the policy decision. * * @throws PolicyException if the condition has not been initialized with a * successful call to setProperties(Map) and/or the * value of REQUEST_AUTHENTICATED_TO_SERVICES * could not be determined. * @throws SSOException if the token is invalid * * @see #setProperties(Map) * @see #AUTHENTICATE_TO_SERVICE * @see #REQUEST_AUTHENTICATED_TO_SERVICES * @see com.sun.identity.policy.ConditionDecision */ public ConditionDecision getConditionDecision(SSOToken token, Map env) throws PolicyException, SSOException { boolean allowed = false; Set requestAuthnServices = new HashSet(); if ( (env != null) && (env.get(REQUEST_AUTHENTICATED_TO_SERVICES) != null) ) { try { requestAuthnServices = (Set) env.get( REQUEST_AUTHENTICATED_TO_SERVICES); if ( DEBUG.messageEnabled()) { DEBUG.message("At AuthenticateToServiceCondition." + "getConditionDecision(): " + "requestAuthnServices from request = " + requestAuthnServices); } } catch (ClassCastException e) { String args[] = { REQUEST_AUTHENTICATED_TO_SERVICES }; throw new PolicyException( ResBundleUtils.rbName, "property_is_not_a_Set", args, e); } } else { if (token != null) { Set authenticatedServices = AMAuthUtils.getRealmQualifiedAuthenticatedServices( token); if (authenticatedServices != null) { requestAuthnServices.addAll(authenticatedServices); } if ( DEBUG.messageEnabled()) { DEBUG.message("At AuthenticateToServiceCondition." + "getConditionDecision(): " + "requestAuthnServices from ssoToken = " + requestAuthnServices); } } } Set adviceMessages = new HashSet(1); if (requestAuthnServices.contains(authenticateToService)) { allowed = true; } else if (realmEmpty){ for (Iterator iter = requestAuthnServices.iterator(); iter.hasNext(); ) { String requestAuthnService = (String)iter.next(); String service = AMAuthUtils.getDataFromRealmQualifiedData( requestAuthnService); if (authenticateToService.equals(service)) { allowed = true; break; } } } if (!allowed) { adviceMessages.add(authenticateToService); if ( DEBUG.messageEnabled()) { DEBUG.message("At AuthenticateToServiceCondition." + "getConditionDecision():" + "authenticateToService not satisfied = " + authenticateToService); } } if ( DEBUG.messageEnabled()) { DEBUG.message("At AuthenticateToServiceCondition." +"getConditionDecision():authenticateToService = " + authenticateToService + "," + " requestAuthnServices = " + requestAuthnServices + ", " + " allowed = " + allowed); } Map advices = new HashMap(); if (!allowed) { advices.put(AUTHENTICATE_TO_SERVICE_CONDITION_ADVICE, adviceMessages); } return new ConditionDecision(allowed, advices); } /** * Returns a copy of this object. * * @return a copy of this object */ public Object clone() { AuthenticateToServiceCondition theClone = null; try { theClone = (AuthenticateToServiceCondition) super.clone(); } catch (CloneNotSupportedException e) { // this should never happen throw new InternalError(); } if (properties != null) { theClone.properties = new HashMap(); Iterator it = properties.keySet().iterator(); while (it.hasNext()) { Object o = it.next(); Set values = new HashSet(); values.addAll((Set) properties.get(o)); theClone.properties.put(o, values); } theClone.authenticateToService = authenticateToService; theClone.realmEmpty = realmEmpty; } return theClone; } /** * Checks the properties set using setProperties() method for * validity like, not null, presence of AUTHENTICATE_TO_SERVICE property, * and no other invalid property. */ private boolean validateProperties() throws PolicyException { if ( (properties == null) || ( properties.keySet() == null) ) { throw new PolicyException( ResBundleUtils.rbName, "properties_can_not_be_null_or_empty", null, null); } Set keySet = properties.keySet(); //Check if the required key(s) are defined if ( !keySet.contains(AUTHENTICATE_TO_SERVICE) ) { String args[] = { AUTHENTICATE_TO_SERVICE }; throw new PolicyException( ResBundleUtils.rbName,"property_value_not_defined", args, null); } //Check if all the keys are valid Iterator keys = keySet.iterator(); while ( keys.hasNext()) { String key = (String) keys.next(); if ( !AUTHENTICATE_TO_SERVICE.equals(key) ) { String args[] = {key}; throw new PolicyException( ResBundleUtils.rbName, "attempt_to_set_invalid_property ", args, null); } } //validate AUTHENTICATE_TO_SERVICE Set authnToServiceSet = null; try { authnToServiceSet = (Set) properties.get(AUTHENTICATE_TO_SERVICE); } catch (ClassCastException e) { String args[] = { REQUEST_AUTHENTICATED_TO_SERVICES }; throw new PolicyException( ResBundleUtils.rbName, "property_is_not_a_Set", args, e); } if ( authnToServiceSet != null ) { validateAuthnToServices(authnToServiceSet); } return true; } /** * Validates the module chain names provided to the setProperties() * call for the AUTHENTICATE_TO_SERVICE key. Checks for null and throws * Exception if null or not a String. */ private boolean validateAuthnToServices(Set authnToServiceSet) throws PolicyException { if ( authnToServiceSet.isEmpty() ) { String args[] = { AUTHENTICATE_TO_SERVICE }; throw new PolicyException( ResBundleUtils.rbName, "property_does_not_allow_empty_values", args, null); } authenticateToService = null; Iterator authnToServiceSetIter = authnToServiceSet.iterator(); try { authenticateToService = (String) authnToServiceSetIter.next(); } catch (ClassCastException e) { String args[] = { AUTHENTICATE_TO_SERVICE }; throw new PolicyException( ResBundleUtils.rbName,"property_is_not_a_String", args, null); } if (authenticateToService != null) { String realm = AMAuthUtils.getRealmFromRealmQualifiedData( authenticateToService); if ((realm == null) || (realm.length() == 0)) { realmEmpty = true; } } return true; } }