Пример #1
0
        public static AuthScheme[] List()
        {
            AuthScheme[]       tmp       = new AuthScheme[registry.Count];
            IList <AuthScheme> tmpValues = registry.Values.ToList();

            for (int i = 0; i < registry.Count; i++)
            {
                tmp[i] = tmpValues[i];
            }
            return(tmp);
        }
Пример #2
0
        //////////////////////////////////////////////////////////////////////////
        // Open
        //////////////////////////////////////////////////////////////////////////

        public async Task OpenAsync()
        {
            try
            {
                // send initial hello message
                var helloResp = await SendHelloAsync();

                // first try standard authentication
                if (await OpenStdAsync(helloResp))
                {
                    authenticated = true;
                    return;
                }
                // check if we have a 200
                if (helloResp.StatusCode == HttpStatusCode.OK)
                {
                    authenticated = true;
                    return;
                }

                var content = ReadContent(helloResp);
                var schemes = AuthScheme.List();
                for (var i = 0; i < schemes.Length; ++i)
                {
                    if (await schemes[i].OnClientNonStdAsync(this, helloResp, content))
                    {
                        authenticated = true;
                        return;
                    }
                }

                // give up
                var resCode   = (int)helloResp.StatusCode;
                var resServer = helloResp.GetResponseHeader("Server");
                if (resCode / 100 >= 4)
                {
                    throw new IOException("HTTP error code: " + resCode); // 4xx or 5xx
                }
                throw new AuthException("No suitable auth scheme for: " + resCode + " " + resServer);
            }
            catch (AuthException)
            {
                throw;
            }
            catch (Exception e)
            {
                throw new AuthException("authenticate failed", e);
            }
            finally
            {
                pass = null;
                stash.Clear();
            }
        }
Пример #3
0
        /// <summary>
        /// Lookup an AuthScheme for the given case-insensitive name.
        /// </summary>
        public static AuthScheme Find(string name, bool @checked)
        {
            AuthScheme scheme = (AuthScheme)registry[name];

            if (scheme != null)
            {
                return(scheme);
            }
            if (@checked)
            {
                throw new System.ArgumentException("No auth scheme found for '" + name + "'");
            }
            return(null);
        }
        /// <summary>
        ///   Attempt standard authentication
        /// </summary>
        /// <param name="resp"> The response to the hello message </param>
        /// <returns>
        ///   true if haystack authentciation was used, false if the
        ///   server does not appear to implement RFC 7235.
        /// </returns>
        private bool OpenStd(HttpWebResponse resp)
        {
            // must be 401 challenge with WWW-Authenticate header
            if (resp.StatusCode != HttpStatusCode.Unauthorized)
            {
                return(false);
            }
            var wwwAuth = ResHeader(resp, "WWW-Authenticate");

            // don't Use this mechanism for Basic which we
            // handle as a non-standard scheme because the headers
            // don't fit nicely into our restricted AuthMsg format
            if (string.IsNullOrEmpty(wwwAuth) || wwwAuth.ToLower().StartsWith("basic", StringComparison.Ordinal))
            {
                return(false);
            }
            // process res/req messages until we have 200 or non-401 failure
            AuthScheme scheme = null;

            for (var loopCount = 0; ; ++loopCount)
            {
                // sanity check that we don't loop too many times
                if (loopCount > 5)
                {
                    throw new AuthException("Loop count exceeded");
                }

                // parse the WWW-Auth header and Use the first scheme
                var       header  = ResHeader(resp, "WWW-Authenticate");
                AuthMsg[] resMsgs = AuthMsg.ListFromStr(header);
                var       resMsg  = resMsgs[0];
                scheme = AuthScheme.Find(resMsg.scheme);

                // let scheme handle message
                var reqMsg = scheme.OnClient(this, resMsg);
                // send request back to the server
                resp = GetAuth(reqMsg);
                try
                {
                    DumpRes(resp, false);
                }
                catch (Exception e)
                {
                    e.ToString();
                }
                // 200 means we are done, 401 means keep looping,
                // consider anything else a failure
                if (resp.StatusCode == HttpStatusCode.OK)
                {
                    break;
                }
                if (resp.StatusCode == HttpStatusCode.Unauthorized)
                {
                    continue;
                }
                throw new AuthException((int)resp.StatusCode + " " + resp.GetResponseStream());
            }
            // init the bearer token
            var     authInfo    = ResHeader(resp, "Authentication-Info");
            AuthMsg authInfoMsg = AuthMsg.FromStr("bearer " + authInfo);

            // callback to scheme for client Success
            scheme.OnClientSuccess(this, authInfoMsg);

            // only keep authToken parameter for Authorization header
            authInfoMsg = new AuthMsg("bearer", new[]
            {
                "authToken",
                authInfoMsg.Param("authToken")
            });
            headers["Authorization"] = authInfoMsg.ToString();

            // we did it!
            return(true);
        }
Пример #5
0
        //////////////////////////////////////////////////////////////////////////
        // Registry
        //////////////////////////////////////////////////////////////////////////

        public static AuthScheme Find(string name)
        {
            return(AuthScheme.Find(name, true));
        }