1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168
|
//-----------------------------------------------------------------------
// <copyright file="SecurityTokenElement.cs" company="Microsoft">
// Copyright (c) Microsoft Corporation. All rights reserved.
// </copyright>
//-----------------------------------------------------------------------
using System;
using System.IdentityModel.Selectors;
using System.IdentityModel.Tokens;
using System.IO;
using System.Xml;
using System.Security.Claims;
using System.Collections.ObjectModel;
namespace System.IdentityModel.Tokens
{
/// <summary>
/// This class represents a number elements found in a <see cref="System.IdentityModel.Protocols.WSTrust.RequestSecurityToken"/> which represent security tokens.
/// </summary>
/// <remarks>
/// This class is not thread-safe.
/// </remarks>
public class SecurityTokenElement
{
SecurityToken _securityToken;
XmlElement _securityTokenXml;
SecurityTokenHandlerCollection _securityTokenHandlers;
ReadOnlyCollection<ClaimsIdentity> _subject;
/// <summary>
/// Creates an instance of this object using a <see cref="SecurityToken"/> object.
/// </summary>
/// <param name="securityToken">The security token this object represents.</param>
/// <remarks>
/// <see cref="GetIdentities"/> is not supported by this object if this constructor is used unless
/// <see cref="ValidateToken"/> is overriden.
/// If the securityToken passed in is a <see cref="GenericXmlSecurityToken"/> then SecurityTokenXml will
/// be set to the value found in <see cref="GenericXmlSecurityToken"/>
/// </remarks>
public SecurityTokenElement(SecurityToken securityToken)
{
if (securityToken == null)
{
throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgumentNull("securityToken");
}
GenericXmlSecurityToken xmlToken = securityToken as GenericXmlSecurityToken;
if (xmlToken != null)
{
_securityTokenXml = xmlToken.TokenXml;
}
_securityToken = securityToken;
}
/// <summary>
/// Creates an instance of this object using XML representation of the security token.
/// </summary>
/// <param name="securityTokenXml">The <see cref="XmlElement"/> representation of the security token.</param>
/// <param name="securityTokenHandlers">The collection of <see cref="SecurityTokenHandler"/> objects that may
/// be used to read and validate the security token this object represents.</param>
public SecurityTokenElement(XmlElement securityTokenXml, SecurityTokenHandlerCollection securityTokenHandlers)
{
if (securityTokenXml == null)
{
throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgumentNull("securityTokenXml");
}
if (securityTokenHandlers == null)
{
throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgumentNull("securityTokenHandlers");
}
_securityTokenXml = securityTokenXml;
_securityTokenHandlers = securityTokenHandlers;
}
/// <summary>
/// Gets the XML representation of the token.
/// </summary>
/// <remarks>This property will be null unless this object was constructed using
/// <see cref="SecurityTokenElement(XmlElement, SecurityTokenHandlerCollection)"/>.
/// </remarks>
public XmlElement SecurityTokenXml
{
get
{
return _securityTokenXml;
}
}
/// <summary>
/// Gets the security token this object represents.
/// </summary>
/// <remarks>
/// If this object was not constructed directly with a <see cref="SecurityToken"/> using
/// <see cref="SecurityTokenElement(SecurityToken)"/>, <see cref="ReadSecurityToken"/>
/// will be called for this value.
/// </remarks>
/// <returns>The <see cref="SecurityToken"/> this object represents</returns>
public SecurityToken GetSecurityToken()
{
if (_securityToken == null)
{
_securityToken = ReadSecurityToken(_securityTokenXml, _securityTokenHandlers);
}
return _securityToken;
}
/// <summary>
/// Gets the collection of <see cref="ClaimsIdentity"/> contained in the token.
/// <seealso cref="ValidateToken"/>
/// </summary>
/// <returns>A <see cref="ReadOnlyCollection{T}"/> of <see cref="ClaimsIdentity"/> representing the identities contained in the token.</returns>
public ReadOnlyCollection<ClaimsIdentity> GetIdentities()
{
if (_subject == null)
{
_subject = ValidateToken(_securityTokenXml, _securityTokenHandlers);
}
return _subject;
}
/// <summary>
/// Creates the identities for the represented by the <see cref="SecurityToken"/>.
/// </summary>
/// <param name="securityTokenXml">The <see cref="XmlElement"/> representation of the security token.</param>
/// <param name="securityTokenHandlers">The collection of <see cref="SecurityTokenHandler"/> objects that may
/// be used to read and validate the security token this object represents.</param>
/// <returns>A <see cref="ReadOnlyCollection{T}"/> of <see cref="ClaimsIdentity"/> representing the identities contained in the token.</returns>
/// <exception cref="InvalidOperationException">If either parameter 'securityTokenXml' or 'securityTokenHandlers' are null.</exception>
protected virtual ReadOnlyCollection<ClaimsIdentity> ValidateToken(XmlElement securityTokenXml, SecurityTokenHandlerCollection securityTokenHandlers)
{
if (securityTokenXml == null || securityTokenHandlers == null)
{
throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new InvalidOperationException(SR.GetString(SR.ID4052)));
}
SecurityToken securityToken = GetSecurityToken();
return securityTokenHandlers.ValidateToken(securityToken);
}
/// <summary>
/// Reads a <see cref="SecurityToken"/> from the provided XML representation.
/// </summary>
/// <param name="securityTokenXml">The XML representation of the security token.</param>
/// <param name="securityTokenHandlers">The <see cref="SecurityTokenHandlerCollection"/> used to
/// read the token.</param>
/// <returns>A <see cref="SecurityToken"/>.</returns>
protected virtual SecurityToken ReadSecurityToken(XmlElement securityTokenXml,
SecurityTokenHandlerCollection securityTokenHandlers)
{
SecurityToken securityToken = null;
XmlReader reader = new XmlNodeReader(securityTokenXml);
reader.MoveToContent();
securityToken = securityTokenHandlers.ReadToken(reader);
if (securityToken == null)
{
throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new InvalidOperationException(SR.GetString(SR.ID4051, securityTokenXml, reader.LocalName, reader.NamespaceURI)));
}
return securityToken;
}
}
}
|