//------------------------------------------------------------ // Copyright (c) Microsoft Corporation. All rights reserved. //------------------------------------------------------------ using System; using System.Collections.Generic; using System.Diagnostics; using System.IdentityModel; using System.IdentityModel.Policy; using System.IdentityModel.Selectors; using System.IdentityModel.Tokens; using System.Security.Claims; using System.ServiceModel; using System.ServiceModel.Security; using System.ServiceModel.Security.Tokens; using System.Xml; namespace System.IdentityModel.Tokens { /// /// This class derives from System.IdentityModel.Selectors.SecurityTokenSerializer and wraps a collection of SecurityTokenHandlers. /// Any call to this serilaizer is delegated to the token handler and delegated to the base class if no token handler /// is registered to handle this particular token or KeyIdentifier. /// class SecurityTokenSerializerAdapter : SecurityTokenSerializer { SecurityTokenHandlerCollection _securityTokenHandlers; /// /// Initializes an instance of /// /// /// The containing the set of /// public SecurityTokenSerializerAdapter(SecurityTokenHandlerCollection securityTokenHandlerCollection) { if (securityTokenHandlerCollection == null) { throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgumentNull("securityTokenHandlerCollection"); } _securityTokenHandlers = securityTokenHandlerCollection; KeyInfoSerializer serializer = securityTokenHandlerCollection.KeyInfoSerializer as KeyInfoSerializer; if (serializer != null) { serializer.InnerSecurityTokenSerializer = this; } } /// /// Gets the SecurityTokenHandlerCollection. /// public SecurityTokenHandlerCollection SecurityTokenHandlers { get { return _securityTokenHandlers; } } /// /// Checks if one of the wrapped SecurityTokenHandlers or the base WSSecurityTokenSerializer /// can read the security token. /// /// Reader to a Security token. /// 'True' if the serializer can read the given Security Token. protected override bool CanReadTokenCore(XmlReader reader) { return _securityTokenHandlers.CanReadToken(reader); } /// /// Checks if one of the wrapped SecurityTokenHandlers or the base WSSecurityTokenSerializer /// can write the given security token. /// /// SecurityToken instance. /// 'True' if the serializer can write the given security token. protected override bool CanWriteTokenCore(SecurityToken token) { return _securityTokenHandlers.CanWriteToken(token); } /// /// Deserializes the SecurityToken from the given XmlReader. /// /// Reader to a Security token. /// Instance of SecurityTokenResolver. /// 'True' if the serializer can read the given Security Token. protected override SecurityToken ReadTokenCore(XmlReader reader, SecurityTokenResolver tokenResolver) { return _securityTokenHandlers.ReadToken(reader); } /// /// Serializes the SecurityToken to the XmlWriter. /// /// XmlWriter to write to. /// The SecurityToken to serializer. /// The input parameter 'writer' or 'token' is null. protected override void WriteTokenCore(XmlWriter writer, SecurityToken token) { _securityTokenHandlers.WriteToken(writer, token); } /// /// Checks if one of the wrapped SecurityTokenHandlers or the base WSSecurityTokenSerializer /// can read the security key identifier. /// /// Reader pointing at a Security Key Identifier {ds:Keyinfo}. /// 'True' if the serializer can read the given Security Key Identifier. /// The is null. protected override bool CanReadKeyIdentifierCore(XmlReader reader) { return (reader.IsStartElement(XmlSignatureConstants.Elements.KeyInfo, XmlSignatureConstants.Namespace)); } /// /// Reads an SecurityKeyIdentifier from a XML stream. /// /// An XML reader positioned at an SecurityKeyIdentifier (ds: KeyInfo) as defined in 'http://www.w3.org/TR/xmldsig-core'. /// SecurityKeyIdentifier. /// The is null. /// If the is not positioned at KeyInfo element. protected override SecurityKeyIdentifier ReadKeyIdentifierCore(XmlReader reader) { if (reader == null) { throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgumentNull("reader"); } if (reader.IsStartElement(XmlSignatureConstants.Elements.KeyInfo, XmlSignatureConstants.Namespace)) { KeyInfo keyInfo = new KeyInfo(this); keyInfo.ReadXml(XmlDictionaryReader.CreateDictionaryReader(reader)); return keyInfo.KeyIdentifier; } else { throw DiagnosticUtility.ExceptionUtility.ThrowHelperXml(reader, SR.GetString(SR.ID4192)); } } protected override bool CanWriteKeyIdentifierCore(SecurityKeyIdentifier keyIdentifier) { return _securityTokenHandlers.KeyInfoSerializer == null ? false : _securityTokenHandlers.KeyInfoSerializer.CanWriteKeyIdentifier(keyIdentifier); } protected override void WriteKeyIdentifierCore(XmlWriter writer, SecurityKeyIdentifier keyIdentifier) { _securityTokenHandlers.KeyInfoSerializer.WriteKeyIdentifier(writer, keyIdentifier); } /// /// Checks if the wrapped SecurityTokenHandler can read the /// SecurityKeyIdentifierClause. /// /// Reader to a SecurityKeyIdentifierClause. /// 'True' if the SecurityKeyIdentifierCause can be read. /// The input parameter 'reader' is null. protected override bool CanReadKeyIdentifierClauseCore(XmlReader reader) { foreach (SecurityTokenHandler securityTokenHandler in _securityTokenHandlers) { if (securityTokenHandler.CanReadKeyIdentifierClause(reader)) { return true; } } return (_securityTokenHandlers.KeyInfoSerializer == null) ? false : _securityTokenHandlers.KeyInfoSerializer.CanReadKeyIdentifierClause(reader); } /// /// Checks if the wrapped SecurityTokenHandler or the base WSSecurityTokenSerializer can write the /// given SecurityKeyIdentifierClause. /// /// SecurityKeyIdentifierClause to be checked. /// 'True' if the SecurityTokenKeyIdentifierClause can be written. /// The input parameter 'keyIdentifierClause' is null. protected override bool CanWriteKeyIdentifierClauseCore(SecurityKeyIdentifierClause keyIdentifierClause) { foreach (SecurityTokenHandler securityTokenHandler in _securityTokenHandlers) { if (securityTokenHandler.CanWriteKeyIdentifierClause(keyIdentifierClause)) { return true; } } return (_securityTokenHandlers.KeyInfoSerializer == null) ? false : _securityTokenHandlers.KeyInfoSerializer.CanWriteKeyIdentifierClause(keyIdentifierClause); } /// /// Deserializes a SecurityKeyIdentifierClause from the given reader. /// /// XmlReader to a SecurityKeyIdentifierClause. /// The deserialized SecurityKeyIdentifierClause. protected override SecurityKeyIdentifierClause ReadKeyIdentifierClauseCore(XmlReader reader) { return _securityTokenHandlers.ReadKeyIdentifierClause(reader); } /// /// Serializes the given SecurityKeyIdentifierClause in a XmlWriter. /// /// XmlWriter to write into. /// SecurityKeyIdentifierClause to be written. protected override void WriteKeyIdentifierClauseCore(XmlWriter writer, SecurityKeyIdentifierClause keyIdentifierClause) { _securityTokenHandlers.WriteKeyIdentifierClause(writer, keyIdentifierClause); } } }