예제 #1
0
        /// <summary>
        /// Performs discovery on the specified identifier.
        /// </summary>
        /// <param name="identifier">The identifier to perform discovery on.</param>
        /// <param name="requestHandler">The means to place outgoing HTTP requests.</param>
        /// <param name="abortDiscoveryChain">if set to <c>true</c>, no further discovery services will be called for this identifier.</param>
        /// <returns>
        /// A sequence of service endpoints yielded by discovery.  Must not be null, but may be empty.
        /// </returns>
        public IEnumerable <IdentifierDiscoveryResult> Discover(Identifier identifier, IDirectWebRequestHandler requestHandler, out bool abortDiscoveryChain)
        {
            abortDiscoveryChain = false;
            var uriIdentifier = identifier as UriIdentifier;

            if (uriIdentifier == null)
            {
                return(Enumerable.Empty <IdentifierDiscoveryResult>());
            }

            var endpoints = new List <IdentifierDiscoveryResult>();

            // Attempt YADIS discovery
            DiscoveryResult yadisResult = Yadis.Discover(requestHandler, uriIdentifier, identifier.IsDiscoverySecureEndToEnd);

            if (yadisResult != null)
            {
                if (yadisResult.IsXrds)
                {
                    try {
                        XrdsDocument xrds          = new XrdsDocument(yadisResult.ResponseText);
                        var          xrdsEndpoints = xrds.XrdElements.CreateServiceEndpoints(yadisResult.NormalizedUri, uriIdentifier);

                        // Filter out insecure endpoints if high security is required.
                        if (uriIdentifier.IsDiscoverySecureEndToEnd)
                        {
                            xrdsEndpoints = xrdsEndpoints.Where(se => se.ProviderEndpoint.IsTransportSecure());
                        }
                        endpoints.AddRange(xrdsEndpoints);
                    } catch (XmlException ex) {
                        Logger.Yadis.Error("Error while parsing the XRDS document.  Falling back to HTML discovery.", ex);
                    }
                }

                // Failing YADIS discovery of an XRDS document, we try HTML discovery.
                if (endpoints.Count == 0)
                {
                    var htmlEndpoints = new List <IdentifierDiscoveryResult>(DiscoverFromHtml(yadisResult.NormalizedUri, uriIdentifier, yadisResult.ResponseText));
                    if (htmlEndpoints.Any())
                    {
                        Logger.Yadis.DebugFormat("Total services discovered in HTML: {0}", htmlEndpoints.Count);
                        Logger.Yadis.Debug(htmlEndpoints.ToStringDeferred(true));
                        endpoints.AddRange(htmlEndpoints.Where(ep => !uriIdentifier.IsDiscoverySecureEndToEnd || ep.ProviderEndpoint.IsTransportSecure()));
                        if (endpoints.Count == 0)
                        {
                            Logger.Yadis.Info("No HTML discovered endpoints met the security requirements.");
                        }
                    }
                    else
                    {
                        Logger.Yadis.Debug("HTML discovery failed to find any endpoints.");
                    }
                }
                else
                {
                    Logger.Yadis.Debug("Skipping HTML discovery because XRDS contained service endpoints.");
                }
            }
            return(endpoints);
        }
예제 #2
0
        /// <summary>
        /// Downloads the XRDS document for this XRI.
        /// </summary>
        /// <param name="requestHandler">The request handler.</param>
        /// <returns>The XRDS document.</returns>
        private XrdsDocument DownloadXrds(IDirectWebRequestHandler requestHandler)
        {
            XrdsDocument doc;

            using (var xrdsResponse = Yadis.Request(requestHandler, this.XrdsUrl, this.IsDiscoverySecureEndToEnd)) {
                doc = new XrdsDocument(XmlReader.Create(xrdsResponse.ResponseStream));
            }
            ErrorUtilities.VerifyProtocol(doc.IsXrdResolutionSuccessful, OpenIdStrings.XriResolutionFailed);
            return(doc);
        }
        /// <summary>
        /// Downloads the XRDS document for this XRI.
        /// </summary>
        /// <param name="identifier">The identifier.</param>
        /// <param name="requestHandler">The request handler.</param>
        /// <returns>The XRDS document.</returns>
        private static XrdsDocument DownloadXrds(XriIdentifier identifier, IDirectWebRequestHandler requestHandler)
        {
            Requires.NotNull(identifier, "identifier");
            Requires.NotNull(requestHandler, "requestHandler");
            XrdsDocument doc;

            using (var xrdsResponse = Yadis.Request(requestHandler, GetXrdsUrl(identifier), identifier.IsDiscoverySecureEndToEnd)) {
                var readerSettings = MessagingUtilities.CreateUntrustedXmlReaderSettings();
                doc = new XrdsDocument(XmlReader.Create(xrdsResponse.ResponseStream, readerSettings));
            }
            ErrorUtilities.VerifyProtocol(doc.IsXrdResolutionSuccessful, OpenIdStrings.XriResolutionFailed);
            return(doc);
        }
        /// <summary>
        /// Downloads the XRDS document for this XRI.
        /// </summary>
        /// <param name="identifier">The identifier.</param>
        /// <param name="requestHandler">The request handler.</param>
        /// <returns>The XRDS document.</returns>
        private static XrdsDocument DownloadXrds(XriIdentifier identifier, IDirectWebRequestHandler requestHandler)
        {
            Requires.NotNull(identifier, "identifier");
            Requires.NotNull(requestHandler, "requestHandler");
            Contract.Ensures(Contract.Result <XrdsDocument>() != null);
            XrdsDocument doc;

            using (var xrdsResponse = Yadis.Request(requestHandler, GetXrdsUrl(identifier), identifier.IsDiscoverySecureEndToEnd)) {
                doc = new XrdsDocument(XmlReader.Create(xrdsResponse.ResponseStream));
            }
            ErrorUtilities.VerifyProtocol(doc.IsXrdResolutionSuccessful, OpenIdStrings.XriResolutionFailed);
            return(doc);
        }
예제 #5
0
        /// <summary>
        /// Performs discovery on the Identifier.
        /// </summary>
        /// <param name="requestHandler">The web request handler to use for discovery.</param>
        /// <returns>
        /// An initialized structure containing the discovered provider endpoint information.
        /// </returns>
        internal override IEnumerable <ServiceEndpoint> Discover(IDirectWebRequestHandler requestHandler)
        {
            List <ServiceEndpoint> endpoints = new List <ServiceEndpoint>();

            // Attempt YADIS discovery
            DiscoveryResult yadisResult = Yadis.Discover(requestHandler, this, IsDiscoverySecureEndToEnd);

            if (yadisResult != null)
            {
                if (yadisResult.IsXrds)
                {
                    XrdsDocument xrds          = new XrdsDocument(yadisResult.ResponseText);
                    var          xrdsEndpoints = xrds.CreateServiceEndpoints(yadisResult.NormalizedUri, this);

                    // Filter out insecure endpoints if high security is required.
                    if (IsDiscoverySecureEndToEnd)
                    {
                        xrdsEndpoints = xrdsEndpoints.Where(se => se.IsSecure);
                    }
                    endpoints.AddRange(xrdsEndpoints);
                }

                // Failing YADIS discovery of an XRDS document, we try HTML discovery.
                if (endpoints.Count == 0)
                {
                    var htmlEndpoints = new List <ServiceEndpoint>(DiscoverFromHtml(yadisResult.NormalizedUri, this, yadisResult.ResponseText));
                    if (htmlEndpoints.Any())
                    {
                        Logger.DebugFormat("Total services discovered in HTML: {0}", htmlEndpoints.Count);
                        Logger.Debug(htmlEndpoints.ToStringDeferred(true));
                        endpoints.AddRange(htmlEndpoints.Where(ep => !IsDiscoverySecureEndToEnd || ep.IsSecure));
                        if (endpoints.Count == 0)
                        {
                            Logger.Info("No HTML discovered endpoints met the security requirements.");
                        }
                    }
                    else
                    {
                        Logger.Debug("HTML discovery failed to find any endpoints.");
                    }
                }
                else
                {
                    Logger.Debug("Skipping HTML discovery because XRDS contained service endpoints.");
                }
            }
            return(endpoints);
        }
예제 #6
0
		/// <summary>
		/// Searches for an XRDS document at the realm URL.
		/// </summary>
		/// <param name="requestHandler">The mechanism to use for sending HTTP requests.</param>
		/// <param name="allowRedirects">Whether redirects may be followed when discovering the Realm.
		/// This may be true when creating an unsolicited assertion, but must be
		/// false when performing return URL verification per 2.0 spec section 9.2.1.</param>
		/// <returns>
		/// The XRDS document if found; or <c>null</c> if no service document was discovered.
		/// </returns>
		internal virtual XrdsDocument Discover(IDirectWebRequestHandler requestHandler, bool allowRedirects) {
			// Attempt YADIS discovery
			DiscoveryResult yadisResult = Yadis.Discover(requestHandler, this.UriWithWildcardChangedToWww, false);
			if (yadisResult != null) {
				// Detect disallowed redirects, since realm discovery never allows them for security.
				ErrorUtilities.VerifyProtocol(allowRedirects || yadisResult.NormalizedUri == yadisResult.RequestUri, OpenIdStrings.RealmCausedRedirectUponDiscovery, yadisResult.RequestUri);
				if (yadisResult.IsXrds) {
					try {
						return new XrdsDocument(yadisResult.ResponseText);
					} catch (XmlException ex) {
						throw ErrorUtilities.Wrap(ex, XrdsStrings.InvalidXRDSDocument);
					}
				}
			}

			return null;
		}
예제 #7
0
        /// <summary>
        /// Searches for an XRDS document at the realm URL, and if found, searches
        /// for a description of a relying party endpoints (OpenId login pages).
        /// </summary>
        /// <param name="requestHandler">The mechanism to use for sending HTTP requests.</param>
        /// <param name="allowRedirects">Whether redirects may be followed when discovering the Realm.
        /// This may be true when creating an unsolicited assertion, but must be
        /// false when performing return URL verification per 2.0 spec section 9.2.1.</param>
        /// <returns>
        /// The details of the endpoints if found, otherwise null.
        /// </returns>
        internal IEnumerable <RelyingPartyEndpointDescription> Discover(IDirectWebRequestHandler requestHandler, bool allowRedirects)
        {
            // Attempt YADIS discovery
            DiscoveryResult yadisResult = Yadis.Discover(requestHandler, this.UriWithWildcardChangedToWww, false);

            if (yadisResult != null)
            {
                // Detect disallowed redirects, since realm discovery never allows them for security.
                ErrorUtilities.VerifyProtocol(allowRedirects || yadisResult.NormalizedUri == yadisResult.RequestUri, OpenIdStrings.RealmCausedRedirectUponDiscovery, yadisResult.RequestUri);
                if (yadisResult.IsXrds)
                {
                    try {
                        XrdsDocument xrds = new XrdsDocument(yadisResult.ResponseText);
                        return(xrds.FindRelyingPartyReceivingEndpoints());
                    } catch (XmlException ex) {
                        throw ErrorUtilities.Wrap(ex, XrdsStrings.InvalidXRDSDocument);
                    }
                }
            }
            return(Enumerable.Empty <RelyingPartyEndpointDescription>());
        }
예제 #8
0
        /// <summary>
        /// Downloads the XRDS document for this XRI.
        /// </summary>
        /// <param name="identifier">The identifier.</param>
        /// <param name="hostFactories">The host factories.</param>
        /// <param name="cancellationToken">The cancellation token.</param>
        /// <returns>
        /// The XRDS document.
        /// </returns>
        private static async Task <XrdsDocument> DownloadXrdsAsync(XriIdentifier identifier, IHostFactories hostFactories, CancellationToken cancellationToken)
        {
            Requires.NotNull(identifier, "identifier");
            Requires.NotNull(hostFactories, "hostFactories");

            XrdsDocument doc;

            using (var xrdsResponse = await Yadis.RequestAsync(GetXrdsUrl(identifier), identifier.IsDiscoverySecureEndToEnd, hostFactories, cancellationToken)) {
                xrdsResponse.EnsureSuccessStatusCode();
                var readerSettings = MessagingUtilities.CreateUntrustedXmlReaderSettings();
                ErrorUtilities.VerifyProtocol(xrdsResponse.Content != null, "XRDS request \"{0}\" returned no response.", GetXrdsUrl(identifier));
                await xrdsResponse.Content.LoadIntoBufferAsync();

                using (var xrdsStream = await xrdsResponse.Content.ReadAsStreamAsync()) {
                    doc = new XrdsDocument(XmlReader.Create(xrdsStream, readerSettings));
                }
            }

            ErrorUtilities.VerifyProtocol(doc.IsXrdResolutionSuccessful, OpenIdStrings.XriResolutionFailed);
            return(doc);
        }
예제 #9
0
파일: Realm.cs 프로젝트: terry2012/DSV
        /// <summary>
        /// Searches for an XRDS document at the realm URL.
        /// </summary>
        /// <param name="hostFactories">The host factories.</param>
        /// <param name="allowRedirects">Whether redirects may be followed when discovering the Realm.
        /// This may be true when creating an unsolicited assertion, but must be
        /// false when performing return URL verification per 2.0 spec section 9.2.1.</param>
        /// <param name="cancellationToken">The cancellation token.</param>
        /// <returns>
        /// The XRDS document if found; or <c>null</c> if no service document was discovered.
        /// </returns>
        internal virtual async Task <XrdsDocument> DiscoverAsync(IHostFactories hostFactories, bool allowRedirects, CancellationToken cancellationToken)
        {
            // Attempt YADIS discovery
            DiscoveryResult yadisResult = await Yadis.DiscoverAsync(hostFactories, this.UriWithWildcardChangedToWww, false, cancellationToken);

            if (yadisResult != null)
            {
                // Detect disallowed redirects, since realm discovery never allows them for security.
                ErrorUtilities.VerifyProtocol(allowRedirects || yadisResult.NormalizedUri == yadisResult.RequestUri, OpenIdStrings.RealmCausedRedirectUponDiscovery, yadisResult.RequestUri);
                if (yadisResult.IsXrds)
                {
                    try {
                        return(new XrdsDocument(yadisResult.ResponseText));
                    } catch (XmlException ex) {
                        throw ErrorUtilities.Wrap(ex, XrdsStrings.InvalidXRDSDocument);
                    }
                }
            }

            return(null);
        }
        /// <summary>
        /// Performs discovery on the specified identifier.
        /// </summary>
        /// <param name="identifier">The identifier to perform discovery on.</param>
        /// <param name="cancellationToken">The cancellation token.</param>
        /// <returns>
        /// A sequence of service endpoints yielded by discovery.  Must not be null, but may be empty.
        /// </returns>
        public async Task <IdentifierDiscoveryServiceResult> DiscoverAsync(Identifier identifier, CancellationToken cancellationToken)
        {
            Requires.NotNull(identifier, "identifier");
            Verify.Operation(this.HostFactories != null, Strings.HostFactoriesRequired);
            cancellationToken.ThrowIfCancellationRequested();

            var uriIdentifier = identifier as UriIdentifier;

            if (uriIdentifier == null)
            {
                return(new IdentifierDiscoveryServiceResult(Enumerable.Empty <IdentifierDiscoveryResult>()));
            }

            var endpoints = new List <IdentifierDiscoveryResult>();

            // Attempt YADIS discovery
            DiscoveryResult yadisResult = await Yadis.DiscoverAsync(this.HostFactories, uriIdentifier, identifier.IsDiscoverySecureEndToEnd, cancellationToken);

            cancellationToken.ThrowIfCancellationRequested();
            if (yadisResult != null)
            {
                if (yadisResult.IsXrds)
                {
                    try {
                        XrdsDocument xrds          = new XrdsDocument(yadisResult.ResponseText);
                        var          xrdsEndpoints = xrds.XrdElements.CreateServiceEndpoints(yadisResult.NormalizedUri, uriIdentifier);

                        // Filter out insecure endpoints if high security is required.
                        if (uriIdentifier.IsDiscoverySecureEndToEnd)
                        {
                            xrdsEndpoints = xrdsEndpoints.Where(se => se.ProviderEndpoint.IsTransportSecure());
                        }
                        endpoints.AddRange(xrdsEndpoints);
                    } catch (XmlException ex) {
                        Logger.Yadis.ErrorException("Error while parsing the XRDS document.  Falling back to HTML discovery.", ex);
                    }
                }

                // Failing YADIS discovery of an XRDS document, we try HTML discovery.
                if (endpoints.Count == 0)
                {
                    await yadisResult.TryRevertToHtmlResponseAsync();

                    var htmlEndpoints = new List <IdentifierDiscoveryResult>(DiscoverFromHtml(yadisResult.NormalizedUri, uriIdentifier, yadisResult.ResponseText));
                    if (htmlEndpoints.Any())
                    {
                        Logger.Yadis.DebugFormat("Total services discovered in HTML: {0}", htmlEndpoints.Count);
                        Logger.Yadis.Debug(htmlEndpoints.ToStringDeferred(true).ToString());
                        endpoints.AddRange(htmlEndpoints.Where(ep => !uriIdentifier.IsDiscoverySecureEndToEnd || ep.ProviderEndpoint.IsTransportSecure()));
                        if (endpoints.Count == 0)
                        {
                            Logger.Yadis.Info("No HTML discovered endpoints met the security requirements.");
                        }
                    }
                    else
                    {
                        Logger.Yadis.Debug("HTML discovery failed to find any endpoints.");
                    }
                }
                else
                {
                    Logger.Yadis.Debug("Skipping HTML discovery because XRDS contained service endpoints.");
                }
            }

            return(new IdentifierDiscoveryServiceResult(endpoints));
        }