/** * 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: DefaultAttributeMapper.java,v 1.4 2009/09/22 23:04:36 exu Exp $ * */ package com.sun.identity.saml.plugins; import com.sun.identity.shared.xml.XMLUtils; import com.sun.identity.plugin.datastore.DataStoreProvider; import com.sun.identity.plugin.datastore.DataStoreProviderException; import com.sun.identity.plugin.datastore.DataStoreProviderManager; import com.sun.identity.saml.assertion.Assertion; import com.sun.identity.saml.assertion.Attribute; import com.sun.identity.saml.assertion.AttributeDesignator; import com.sun.identity.saml.assertion.SubjectConfirmation; import com.sun.identity.saml.common.SAMLConstants; import com.sun.identity.saml.common.SAMLException; import com.sun.identity.saml.common.SAMLServiceManager; import com.sun.identity.saml.common.SAMLUtils; import com.sun.identity.saml.protocol.AttributeQuery; import java.util.ArrayList; import java.util.HashSet; import java.util.Iterator; import java.util.List; import java.util.Map; import java.util.MissingResourceException; import java.util.Set; import java.util.StringTokenizer; import org.w3c.dom.Element; import org.w3c.dom.Node; import org.w3c.dom.NodeList; import com.sun.identity.plugin.session.SessionException; import com.sun.identity.common.SystemConfigurationUtil; /** * The class DefaultAttributeMapper provide a default * implementation of the AttributeMapper interface. */ public class DefaultAttributeMapper implements AttributeMapper { /** * Default Constructor */ public DefaultAttributeMapper() {} /** * This method exams the SubjectConfirmation of the Subject in the * AttributeQuery. If it has only one ConfirmationMethod, and this * ConfirmationMethod equals to "urn:com:sun:identity"; and its * SubjectConfirmationData contains TEXT node only, then the method * returns the concatenated string of all the TEXT nodes. Otherwise, * it returns null. *

* @param query the AttributeQuery object. * @see com.sun.identity.saml.plugins.AttributeMapper#getSSOTokenID */ public String getSSOTokenID(AttributeQuery query) { if (query == null) { return null; } SubjectConfirmation sc = query.getSubject().getSubjectConfirmation(); if (sc == null) { return null; } if (!SAMLUtils.isCorrectConfirmationMethod(sc)) { return null; } Element scData = sc.getSubjectConfirmationData(); return XMLUtils.getElementString(scData); } /** * This method exams the SubjectConfirmationData of the Subject in the * AttributeQuery. It returns the first Assertion that contains at least * one AuthenticationStatement. *

* @see com.sun.identity.saml.plugins.AttributeMapper#getSSOAssertion */ public Assertion getSSOAssertion(AttributeQuery query) { if (query == null) { return null; } SubjectConfirmation sc = query.getSubject().getSubjectConfirmation(); if (sc == null) { return null; } Element scData = sc.getSubjectConfirmationData(); if (scData == null) { return null; } Assertion assertion = null; try { NodeList nl = scData.getChildNodes(); Node child = null; for (int i = 0, length = nl.getLength(); i < length; i++) { child = nl.item(i); if (child.getNodeType() == Node.ELEMENT_NODE ) { try { assertion = new Assertion((Element) child); if (SAMLUtils.isAuthNAssertion(assertion)) { return assertion; } } catch (SAMLException se) { if (SAMLUtils.debug.messageEnabled()) { SAMLUtils.debug.message("DefaultAttributeMapper: " + "SAMLException when trying to obtain Assertion:" + se); } } } } } catch (Exception e) { SAMLUtils.debug.error("DefaultAttributeMapper: Exception when " + "parsing the SubjectConfirmationData:", e); } return null; } /** * This method first mapps the Subject in the query to a local site * account using the AccountMapper defined in the SAML Service. * The source ID is used to find the appropriate AccountMapper. * It then calls the User Management API to obtain the attribute value * using the Session and the attribute name in the AttributeDesignator(s) * of the query. If there is no AttributeDesignator in the query, * attributes of services specified as userServiceNameList in * amSAML.properties will be returned. *

* * @param query the AttributeQuery object. * @param sourceID the Source Identifier. * @param token User Session * @throws SAMLException if there is an error. */ public List getAttributes(AttributeQuery query, String sourceID, Object token) throws SAMLException { if ((query == null) || (sourceID == null) || (token == null)) { SAMLUtils.debug.message("DefaultAttributeMapper: null input."); throw new SAMLException(SAMLUtils.bundle.getString("nullInput")); } Map entries = (Map) SAMLServiceManager.getAttribute( SAMLConstants.PARTNER_URLS); SAMLServiceManager.SOAPEntry destSite = (SAMLServiceManager.SOAPEntry) entries.get(sourceID); String name = null; PartnerAccountMapper paMapper = destSite.getPartnerAccountMapper(); if (paMapper != null) { Map map = paMapper.getUser(query, sourceID); name = (String) map.get(PartnerAccountMapper.NAME); } if (name == null) { if (SAMLUtils.debug.messageEnabled()) { SAMLUtils.debug.message("DefaultAttributeMapper: couldn't " + "map the subject to a local user."); } throw new SAMLException( SAMLUtils.bundle.getString("cannotMapSubject")); } if (SAMLUtils.debug.messageEnabled()) { SAMLUtils.debug.message("user=" + name); } // assume user in default root realm DataStoreProvider provider = null; try { provider = DataStoreProviderManager.getInstance(). getDataStoreProvider(SAMLConstants.SAML); } catch (DataStoreProviderException de) { if (SAMLUtils.debug.messageEnabled()) { SAMLUtils.debug.message("DefaultAttributeMapper.getAttribute:", de); } throw new SAMLException( SAMLUtils.bundle.getString("cannotMapSubject")); } List attributes = new ArrayList(); Attribute attribute = null; List attrValues = null; String attrValueString = null; String attrName = null; Set valueSet = null; Iterator valueIter = null; List designators = query.getAttributeDesignator(); if ((designators == null) || (designators.isEmpty())) { String userAttrName = SystemConfigurationUtil.getProperty( "userAttributeNameList"); if ((userAttrName == null ) || (userAttrName.length() == 0)) { if (SAMLUtils.debug.messageEnabled()) { SAMLUtils.debug.message("DefaultAttributeMapper: " + "userAttributeNameList is not defined " + "or empty."); } return attributes; } Set attrNames = new HashSet(); StringTokenizer stk = new StringTokenizer(userAttrName, ","); while (stk.hasMoreTokens()) { attrNames.add(stk.nextToken().trim()); } Map valueMap = null; try { valueMap = provider.getAttributes(name, attrNames); } catch (DataStoreProviderException ie) { if (SAMLUtils.debug.messageEnabled()) { SAMLUtils.debug.message("DefaultAttributeMapper: " + "DataStoreProviderException:", ie); } throw new SAMLException(ie.getMessage()); } Set keySet = valueMap.keySet(); String keyName = null; Iterator keyIter = keySet.iterator(); while (keyIter.hasNext()) { keyName = (String) keyIter.next(); valueSet = (Set) valueMap.get(keyName); valueIter = valueSet.iterator(); attrValues = new ArrayList(); while (valueIter.hasNext()) { attrValueString = SAMLUtils.makeStartElementTagXML( "AttributeValue", true, true) + ((String) valueIter.next()) + SAMLUtils.makeEndElementTagXML( "AttributeValue", true); attrValues.add(XMLUtils.toDOMDocument(attrValueString, SAMLUtils.debug).getDocumentElement()); } if (!attrValues.isEmpty()) { attribute = new Attribute(keyName, SAMLConstants.ATTR_NAME_SPACE, attrValues); attributes.add(attribute); } } } else { Iterator iter = designators.iterator(); AttributeDesignator designator = null; while (iter.hasNext()) { designator = (AttributeDesignator) iter.next(); attrName = (String) designator.getAttributeName(); try { valueSet = provider.getAttribute(name, attrName); } catch (DataStoreProviderException ie) { if (SAMLUtils.debug.messageEnabled()) { SAMLUtils.debug.message("DefaultAttributeMapper: " + "DataStoreProviderException:", ie); } throw new SAMLException(ie.getMessage()); } valueIter = valueSet.iterator(); attrValues = new ArrayList(); while (valueIter.hasNext()) { attrValueString = SAMLUtils.makeStartElementTagXML( "AttributeValue", true, true) + ((String) valueIter.next()) + SAMLUtils.makeEndElementTagXML("AttributeValue",true); attrValues.add(XMLUtils.toDOMDocument(attrValueString, SAMLUtils.debug).getDocumentElement()); } if (!attrValues.isEmpty()) { attribute = new Attribute(attrName, designator.getAttributeNamespace(), attrValues); attributes.add(attribute); } } } return attributes; } }