public override SignatureVerificationFailure VerifySync(HttpRequestForSigning signedRequest, Signature signature, Client client)
        {
            if (!signature.Headers.Contains(HeaderName.PredefinedHeaderNames.RequestTarget))
            {
                return(SignatureVerificationFailure.HeaderMissing($"The {HeaderName.PredefinedHeaderNames.RequestTarget} header is required to be included in the signature."));
            }

            if (client.SignatureAlgorithm.ShouldIncludeDateHeader() && !signature.Headers.Contains(HeaderName.PredefinedHeaderNames.Date))
            {
                return(SignatureVerificationFailure.HeaderMissing($"The inclusion of the {HeaderName.PredefinedHeaderNames.Date} header is required when using security algorithm '{client.SignatureAlgorithm.Name}'."));
            }

            if (client.SignatureAlgorithm.ShouldIncludeCreatedHeader() && !signature.Headers.Contains(HeaderName.PredefinedHeaderNames.Created))
            {
                return(SignatureVerificationFailure.HeaderMissing($"The inclusion of the {HeaderName.PredefinedHeaderNames.Created} header is required when using security algorithm '{client.SignatureAlgorithm.Name}'."));
            }

            if (client.SignatureAlgorithm.ShouldIncludeExpiresHeader() && !signature.Headers.Contains(HeaderName.PredefinedHeaderNames.Expires))
            {
                return(SignatureVerificationFailure.HeaderMissing($"The inclusion of the {HeaderName.PredefinedHeaderNames.Expires} header is required when using security algorithm '{client.SignatureAlgorithm.Name}'."));
            }

            foreach (var headerName in signature.Headers)
            {
                if (headerName != HeaderName.PredefinedHeaderNames.RequestTarget)
                {
                    if (!signedRequest.Headers.Contains(headerName))
                    {
                        return(SignatureVerificationFailure.HeaderMissing($"The request header {headerName} is missing, but it is required to validate the signature."));
                    }
                }
            }

            return(null);
        }
            public async Task WhenSignatureVerificationFails_InvokesConfiguredCallback()
            {
                _request.Headers["Authorization"] = "TestScheme abc123";

                var failureResult = new RequestSignatureVerificationResultFailure(
                    new Client("c1", "test", SignatureAlgorithm.CreateForVerification("s3cr3t"), TimeSpan.FromMinutes(1), TimeSpan.FromMinutes(1)),
                    new Signature(),
                    SignatureVerificationFailure.HeaderMissing("A header is missing.", null));

                A.CallTo(() => _options.RequestSignatureVerifier.VerifySignature(
                             A <IOwinRequest> .That.Matches(ConvertedRequest),
                             A <SignedHttpRequestAuthenticationOptions> ._))
                .Returns(failureResult);

                RequestSignatureVerificationResult resultFromCallback = null;

                _options.OnIdentityVerificationFailed = (request, failure) => {
                    resultFromCallback = failure;
                    return(Task.CompletedTask);
                };

                await _method();

                resultFromCallback.Should().Be(failureResult);
            }
Exemple #3
0
        public override SignatureVerificationFailure VerifySync(HttpRequestForVerification signedRequest, Signature signature, Client client)
        {
            if (signature.Headers.Contains(HeaderName.PredefinedHeaderNames.Expires) && !signature.Expires.HasValue)
            {
                return(SignatureVerificationFailure.HeaderMissing($"The signature does not contain a value for the {nameof(signature.Expires)} property, but it is required."));
            }

            if (signature.Expires.HasValue && signature.Expires.Value < _systemClock.UtcNow.Add(-client.ClockSkew))
            {
                return(SignatureVerificationFailure.SignatureExpired("The signature is expired."));
            }

            return(null);
        }
        public override SignatureVerificationFailure VerifySync(HttpRequestForSigning signedRequest, Signature signature, Client client)
        {
            if (!signature.Expires.HasValue)
            {
                return(SignatureVerificationFailure.HeaderMissing($"The signature does not contain a value for the {nameof(signature.Expires)} property, but it is required."));
            }

            if (signature.Expires.Value < _systemClock.UtcNow)
            {
                return(SignatureVerificationFailure.SignatureExpired("The signature is expired."));
            }

            return(null);
        }
            public async Task WhenSignatureVerificationFails_ReturnsNull()
            {
                _request.Headers["Authorization"] = "TestScheme abc123";

                var failureResult = new RequestSignatureVerificationResultFailure(
                    new Client("c1", "test", SignatureAlgorithm.CreateForVerification("s3cr3t"), TimeSpan.FromMinutes(1), TimeSpan.FromMinutes(1)),
                    new Signature(),
                    SignatureVerificationFailure.HeaderMissing("A header is missing.", null));

                A.CallTo(() => _options.RequestSignatureVerifier.VerifySignature(
                             A <IOwinRequest> .That.Matches(ConvertedRequest),
                             A <SignedHttpRequestAuthenticationOptions> ._))
                .Returns(failureResult);

                var actual = await _method();

                actual.Should().BeNull();
            }
        public override SignatureVerificationFailure VerifySync(HttpRequestForVerification signedRequest, Signature signature, Client client)
        {
            if (signature.Headers.Contains(HeaderName.PredefinedHeaderNames.RequestTarget) && !signature.Headers.Contains(HeaderName.PredefinedHeaderNames.RequestTarget))
            {
                return(SignatureVerificationFailure.HeaderMissing($"The {HeaderName.PredefinedHeaderNames.RequestTarget} header is required to be included in the signature."));
            }

            foreach (var headerName in signature.Headers)
            {
                var isPresent = PseudoHeaders.Contains(headerName);

                if (!isPresent)
                {
                    isPresent = signedRequest.Headers.Contains(headerName);
                }

                if (!isPresent)
                {
                    return(SignatureVerificationFailure.HeaderMissing($"The request header {headerName} is missing, but it is required to validate the signature."));
                }
            }

            return(null);
        }
Exemple #7
0
        public override SignatureVerificationFailure VerifySync(HttpRequestForSigning signedRequest, Signature signature, Client client)
        {
            if (signature.Headers.Contains(HeaderName.PredefinedHeaderNames.Digest) &&
                !signedRequest.Headers.Contains(HeaderName.PredefinedHeaderNames.Digest))
            {
                return(SignatureVerificationFailure.HeaderMissing($"The {HeaderName.PredefinedHeaderNames.Digest} header is indicated as part of the signature, but it is not included in the request."));
            }

            if (!signedRequest.Headers.Contains(HeaderName.PredefinedHeaderNames.Digest))
            {
                _logger?.LogDebug("{0} header verification is not required, because it is not present in the request to verify.", HeaderName.PredefinedHeaderNames.Digest);
                return(null);
            }

            if (signedRequest.Body == null)
            {
                return(SignatureVerificationFailure.InvalidDigestHeader($"The {HeaderName.PredefinedHeaderNames.Digest} header verification failed. The request has no body."));
            }

            var digestHeaderValue = signedRequest.Headers.GetValues(HeaderName.PredefinedHeaderNames.Digest).FirstOrDefault();
            var digestParams      = new List <string>();

            if (!string.IsNullOrEmpty(digestHeaderValue))
            {
                var separatorIndex = digestHeaderValue.IndexOf('=');
                if (separatorIndex < 0 || separatorIndex >= digestHeaderValue.Length - 1)
                {
                    digestParams.Add(digestHeaderValue);
                }
                else
                {
                    digestParams.Add(digestHeaderValue.Substring(0, separatorIndex));
                    digestParams.Add(digestHeaderValue.Substring(separatorIndex + 1));
                }
            }

            if (digestParams.Count < 2)
            {
                return(SignatureVerificationFailure.InvalidDigestHeader($"The {HeaderName.PredefinedHeaderNames.Digest} request header is invalid."));
            }

            if (!Constants.DigestHashAlgorithms.TryGetValue(digestParams[0], out var digestAlgorithmName))
            {
                return(SignatureVerificationFailure.InvalidDigestHeader($"The {HeaderName.PredefinedHeaderNames.Digest} algorithm name ({digestParams[0] ?? "[null]"}) is invalid."));
            }

            using (var hashAlgorithm = HashAlgorithmFactory.Create(new HashAlgorithmName(digestAlgorithmName))) {
                if (hashAlgorithm == null)
                {
                    return(SignatureVerificationFailure.InvalidDigestHeader($"The {HeaderName.PredefinedHeaderNames.Digest} algorithm name ({digestParams[0] ?? "[null]"}) is currently not supported."));
                }

                var payloadBytes     = hashAlgorithm.ComputeHash(signedRequest.Body);
                var calculatedDigest = _base64Converter.ToBase64(payloadBytes);
                var receivedDigest   = digestParams[1];

                if (calculatedDigest != receivedDigest)
                {
                    return(SignatureVerificationFailure.InvalidDigestHeader("The digest header verification failed."));
                }
            }

            return(null);
        }