diff --git a/src/Ocelot/Authorisation/Middleware/AuthorisationMiddleware.cs b/src/Ocelot/Authorisation/Middleware/AuthorisationMiddleware.cs index 82fc3af7..fb4f7a26 100644 --- a/src/Ocelot/Authorisation/Middleware/AuthorisationMiddleware.cs +++ b/src/Ocelot/Authorisation/Middleware/AuthorisationMiddleware.cs @@ -50,7 +50,7 @@ Logger.LogWarning("user scopes is not authorised setting pipeline error"); SetPipelineError(context, new UnauthorisedError( - $"{context.HttpContext.User.Identity.Name} unable to access {context.DownstreamReRoute.UpstreamPathTemplate.Value}")); + $"{context.HttpContext.User.Identity.Name} unable to access {context.DownstreamReRoute.UpstreamPathTemplate.OriginalValue}")); } } @@ -70,19 +70,19 @@ if (IsAuthorised(authorised)) { - Logger.LogInformation($"{context.HttpContext.User.Identity.Name} has succesfully been authorised for {context.DownstreamReRoute.UpstreamPathTemplate.Value}."); + Logger.LogInformation($"{context.HttpContext.User.Identity.Name} has succesfully been authorised for {context.DownstreamReRoute.UpstreamPathTemplate.OriginalValue}."); await _next.Invoke(context); } else { - Logger.LogWarning($"{context.HttpContext.User.Identity.Name} is not authorised to access {context.DownstreamReRoute.UpstreamPathTemplate.Value}. Setting pipeline error"); + Logger.LogWarning($"{context.HttpContext.User.Identity.Name} is not authorised to access {context.DownstreamReRoute.UpstreamPathTemplate.OriginalValue}. Setting pipeline error"); - SetPipelineError(context, new UnauthorisedError($"{context.HttpContext.User.Identity.Name} is not authorised to access {context.DownstreamReRoute.UpstreamPathTemplate.Value}")); + SetPipelineError(context, new UnauthorisedError($"{context.HttpContext.User.Identity.Name} is not authorised to access {context.DownstreamReRoute.UpstreamPathTemplate.OriginalValue}")); } } else { - Logger.LogInformation($"{context.DownstreamReRoute.DownstreamPathTemplate.Value} route does not require user to be authorised"); + Logger.LogInformation($"{context.DownstreamReRoute.DownstreamDownstreamPathTemplate.Value} route does not require user to be authorised"); await _next.Invoke(context); } } diff --git a/src/Ocelot/Configuration/Builder/DownstreamReRouteBuilder.cs b/src/Ocelot/Configuration/Builder/DownstreamReRouteBuilder.cs index b782ab0f..2ed2ef44 100644 --- a/src/Ocelot/Configuration/Builder/DownstreamReRouteBuilder.cs +++ b/src/Ocelot/Configuration/Builder/DownstreamReRouteBuilder.cs @@ -11,7 +11,6 @@ namespace Ocelot.Configuration.Builder private AuthenticationOptions _authenticationOptions; private string _loadBalancerKey; private string _downstreamPathTemplate; - private string _upstreamTemplate; private UpstreamPathTemplate _upstreamTemplatePattern; private List _upstreamHttpMethod; private bool _isAuthenticated; @@ -79,12 +78,6 @@ namespace Ocelot.Configuration.Builder return this; } - public DownstreamReRouteBuilder WithUpstreamPathTemplate(string input) - { - _upstreamTemplate = input; - return this; - } - public DownstreamReRouteBuilder WithUpstreamTemplatePattern(UpstreamPathTemplate input) { _upstreamTemplatePattern = input; @@ -245,7 +238,7 @@ namespace Ocelot.Configuration.Builder { return new DownstreamReRoute( _key, - new PathTemplate(_upstreamTemplate), + _upstreamTemplatePattern, _upstreamHeaderFindAndReplace, _downstreamHeaderFindAndReplace, _downstreamAddresses, @@ -267,7 +260,7 @@ namespace Ocelot.Configuration.Builder _isAuthenticated, _isAuthorised, _authenticationOptions, - new PathTemplate(_downstreamPathTemplate), + new DownstreamPathTemplate(_downstreamPathTemplate), _loadBalancerKey, _delegatingHandlers, _addHeadersToDownstream, diff --git a/src/Ocelot/Configuration/Builder/ReRouteBuilder.cs b/src/Ocelot/Configuration/Builder/ReRouteBuilder.cs index 31367f26..b31a14ff 100644 --- a/src/Ocelot/Configuration/Builder/ReRouteBuilder.cs +++ b/src/Ocelot/Configuration/Builder/ReRouteBuilder.cs @@ -1,15 +1,12 @@ -using System.Collections.Generic; -using System.Net.Http; -using Ocelot.Values; -using System.Linq; -using Ocelot.Configuration.Creator; -using System; - -namespace Ocelot.Configuration.Builder +namespace Ocelot.Configuration.Builder { + using System.Collections.Generic; + using System.Net.Http; + using Ocelot.Values; + using System.Linq; + public class ReRouteBuilder { - private string _upstreamTemplate; private UpstreamPathTemplate _upstreamTemplatePattern; private List _upstreamHttpMethod; private string _upstreamHost; @@ -39,12 +36,6 @@ namespace Ocelot.Configuration.Builder return this; } - public ReRouteBuilder WithUpstreamPathTemplate(string input) - { - _upstreamTemplate = input; - return this; - } - public ReRouteBuilder WithUpstreamTemplatePattern(UpstreamPathTemplate input) { _upstreamTemplatePattern = input; @@ -67,7 +58,6 @@ namespace Ocelot.Configuration.Builder { return new ReRoute( _downstreamReRoutes, - new PathTemplate(_upstreamTemplate), _upstreamHttpMethod, _upstreamTemplatePattern, _upstreamHost, diff --git a/src/Ocelot/Configuration/Builder/UpstreamPathTemplateBuilder.cs b/src/Ocelot/Configuration/Builder/UpstreamPathTemplateBuilder.cs new file mode 100644 index 00000000..21b21302 --- /dev/null +++ b/src/Ocelot/Configuration/Builder/UpstreamPathTemplateBuilder.cs @@ -0,0 +1,41 @@ +namespace Ocelot.Configuration.Builder +{ + using Values; + + public class UpstreamPathTemplateBuilder + { + private string _template; + private int _priority; + private bool _containsQueryString; + private string _originalValue; + + public UpstreamPathTemplateBuilder WithTemplate(string template) + { + _template = template; + return this; + } + + public UpstreamPathTemplateBuilder WithPriority(int priority) + { + _priority = priority; + return this; + } + + public UpstreamPathTemplateBuilder WithContainsQueryString(bool containsQueryString) + { + _containsQueryString = containsQueryString; + return this; + } + + public UpstreamPathTemplateBuilder WithOriginalValue(string originalValue) + { + _originalValue = originalValue; + return this; + } + + public UpstreamPathTemplate Build() + { + return new UpstreamPathTemplate(_template, _priority, _containsQueryString, _originalValue); + } + } +} diff --git a/src/Ocelot/Configuration/Creator/FileInternalConfigurationCreator.cs b/src/Ocelot/Configuration/Creator/FileInternalConfigurationCreator.cs index 6aea0702..51dad93d 100644 --- a/src/Ocelot/Configuration/Creator/FileInternalConfigurationCreator.cs +++ b/src/Ocelot/Configuration/Creator/FileInternalConfigurationCreator.cs @@ -166,7 +166,6 @@ namespace Ocelot.Configuration.Creator var upstreamTemplatePattern = _upstreamTemplatePatternCreator.Create(aggregateReRoute); var reRoute = new ReRouteBuilder() - .WithUpstreamPathTemplate(aggregateReRoute.UpstreamPathTemplate) .WithUpstreamHttpMethod(aggregateReRoute.UpstreamHttpMethod) .WithUpstreamTemplatePattern(upstreamTemplatePattern) .WithDownstreamReRoutes(applicableReRoutes) @@ -182,7 +181,6 @@ namespace Ocelot.Configuration.Creator var upstreamTemplatePattern = _upstreamTemplatePatternCreator.Create(fileReRoute); var reRoute = new ReRouteBuilder() - .WithUpstreamPathTemplate(fileReRoute.UpstreamPathTemplate) .WithUpstreamHttpMethod(fileReRoute.UpstreamHttpMethod) .WithUpstreamTemplatePattern(upstreamTemplatePattern) .WithDownstreamReRoute(downstreamReRoutes) @@ -229,7 +227,6 @@ namespace Ocelot.Configuration.Creator var reRoute = new DownstreamReRouteBuilder() .WithKey(fileReRoute.Key) .WithDownstreamPathTemplate(fileReRoute.DownstreamPathTemplate) - .WithUpstreamPathTemplate(fileReRoute.UpstreamPathTemplate) .WithUpstreamHttpMethod(fileReRoute.UpstreamHttpMethod) .WithUpstreamTemplatePattern(upstreamTemplatePattern) .WithIsAuthenticated(fileReRouteOptions.IsAuthenticated) diff --git a/src/Ocelot/Configuration/Creator/UpstreamTemplatePatternCreator.cs b/src/Ocelot/Configuration/Creator/UpstreamTemplatePatternCreator.cs index fbf62d4a..b5acc10f 100644 --- a/src/Ocelot/Configuration/Creator/UpstreamTemplatePatternCreator.cs +++ b/src/Ocelot/Configuration/Creator/UpstreamTemplatePatternCreator.cs @@ -31,7 +31,7 @@ namespace Ocelot.Configuration.Creator //hack to handle /{url} case if(ForwardSlashAndOnePlaceHolder(upstreamTemplate, placeholders, postitionOfPlaceHolderClosingBracket)) { - return new UpstreamPathTemplate(RegExForwardSlashAndOnePlaceHolder, 0, false); + return new UpstreamPathTemplate(RegExForwardSlashAndOnePlaceHolder, 0, false, reRoute.UpstreamPathTemplate); } } } @@ -60,7 +60,7 @@ namespace Ocelot.Configuration.Creator if (upstreamTemplate == "/") { - return new UpstreamPathTemplate(RegExForwardSlashOnly, reRoute.Priority, containsQueryString); + return new UpstreamPathTemplate(RegExForwardSlashOnly, reRoute.Priority, containsQueryString, reRoute.UpstreamPathTemplate); } if(upstreamTemplate.EndsWith("/")) @@ -72,7 +72,7 @@ namespace Ocelot.Configuration.Creator ? $"^{upstreamTemplate}{RegExMatchEndString}" : $"^{RegExIgnoreCase}{upstreamTemplate}{RegExMatchEndString}"; - return new UpstreamPathTemplate(route, reRoute.Priority, containsQueryString); + return new UpstreamPathTemplate(route, reRoute.Priority, containsQueryString, reRoute.UpstreamPathTemplate); } private bool ForwardSlashAndOnePlaceHolder(string upstreamTemplate, List placeholders, int postitionOfPlaceHolderClosingBracket) diff --git a/src/Ocelot/Configuration/DownstreamReRoute.cs b/src/Ocelot/Configuration/DownstreamReRoute.cs index f6cc876d..7e3c707c 100644 --- a/src/Ocelot/Configuration/DownstreamReRoute.cs +++ b/src/Ocelot/Configuration/DownstreamReRoute.cs @@ -8,7 +8,7 @@ namespace Ocelot.Configuration { public DownstreamReRoute( string key, - PathTemplate upstreamPathTemplate, + UpstreamPathTemplate upstreamPathTemplate, List upstreamHeadersFindAndReplace, List downstreamHeadersFindAndReplace, List downstreamAddresses, @@ -30,7 +30,7 @@ namespace Ocelot.Configuration bool isAuthenticated, bool isAuthorised, AuthenticationOptions authenticationOptions, - PathTemplate downstreamPathTemplate, + DownstreamPathTemplate downstreamDownstreamPathTemplate, string loadBalancerKey, List delegatingHandlers, List addHeadersToDownstream, @@ -63,13 +63,13 @@ namespace Ocelot.Configuration IsAuthenticated = isAuthenticated; IsAuthorised = isAuthorised; AuthenticationOptions = authenticationOptions; - DownstreamPathTemplate = downstreamPathTemplate; + DownstreamDownstreamPathTemplate = downstreamDownstreamPathTemplate; LoadBalancerKey = loadBalancerKey; AddHeadersToUpstream = addHeadersToUpstream; } public string Key { get; } - public PathTemplate UpstreamPathTemplate { get; } + public UpstreamPathTemplate UpstreamPathTemplate { get; } public List UpstreamHeadersFindAndReplace { get; } public List DownstreamHeadersFindAndReplace { get; } public List DownstreamAddresses { get; } @@ -91,7 +91,7 @@ namespace Ocelot.Configuration public bool IsAuthenticated { get; } public bool IsAuthorised { get; } public AuthenticationOptions AuthenticationOptions { get; } - public PathTemplate DownstreamPathTemplate { get; } + public DownstreamPathTemplate DownstreamDownstreamPathTemplate { get; } public string LoadBalancerKey { get; } public List DelegatingHandlers { get; } public List AddHeadersToDownstream { get; } diff --git a/src/Ocelot/Configuration/ReRoute.cs b/src/Ocelot/Configuration/ReRoute.cs index c4c3952d..f1faf975 100644 --- a/src/Ocelot/Configuration/ReRoute.cs +++ b/src/Ocelot/Configuration/ReRoute.cs @@ -1,15 +1,12 @@ -using System.Collections.Generic; -using System.Net.Http; -using Ocelot.Configuration.Creator; -using Ocelot.Requester.QoS; -using Ocelot.Values; - -namespace Ocelot.Configuration +namespace Ocelot.Configuration { + using System.Collections.Generic; + using System.Net.Http; + using Ocelot.Values; + public class ReRoute { public ReRoute(List downstreamReRoute, - PathTemplate upstreamPathTemplate, List upstreamHttpMethod, UpstreamPathTemplate upstreamTemplatePattern, string upstreamHost, @@ -17,13 +14,11 @@ namespace Ocelot.Configuration { UpstreamHost = upstreamHost; DownstreamReRoute = downstreamReRoute; - UpstreamPathTemplate = upstreamPathTemplate; UpstreamHttpMethod = upstreamHttpMethod; UpstreamTemplatePattern = upstreamTemplatePattern; Aggregator = aggregator; } - public PathTemplate UpstreamPathTemplate { get; private set; } public UpstreamPathTemplate UpstreamTemplatePattern { get; private set; } public List UpstreamHttpMethod { get; private set; } public string UpstreamHost { get; private set; } diff --git a/src/Ocelot/DownstreamRouteFinder/Finder/DownstreamRouteFinder.cs b/src/Ocelot/DownstreamRouteFinder/Finder/DownstreamRouteFinder.cs index 7c7264de..d3114020 100644 --- a/src/Ocelot/DownstreamRouteFinder/Finder/DownstreamRouteFinder.cs +++ b/src/Ocelot/DownstreamRouteFinder/Finder/DownstreamRouteFinder.cs @@ -55,7 +55,7 @@ namespace Ocelot.DownstreamRouteFinder.Finder private DownstreamRoute GetPlaceholderNamesAndValues(string path, string query, ReRoute reRoute) { - var templatePlaceholderNameAndValues = _placeholderNameAndValueFinder.Find(path, query, reRoute.UpstreamPathTemplate.Value); + var templatePlaceholderNameAndValues = _placeholderNameAndValueFinder.Find(path, query, reRoute.UpstreamTemplatePattern.OriginalValue); return new DownstreamRoute(templatePlaceholderNameAndValues.Data, reRoute); } diff --git a/src/Ocelot/DownstreamRouteFinder/Finder/DownstreamRouteProviderFactory.cs b/src/Ocelot/DownstreamRouteFinder/Finder/DownstreamRouteProviderFactory.cs index 080172d5..319e9191 100644 --- a/src/Ocelot/DownstreamRouteFinder/Finder/DownstreamRouteProviderFactory.cs +++ b/src/Ocelot/DownstreamRouteFinder/Finder/DownstreamRouteProviderFactory.cs @@ -10,7 +10,7 @@ public class DownstreamRouteProviderFactory : IDownstreamRouteProviderFactory { private readonly Dictionary _providers; - private IOcelotLogger _logger; + private readonly IOcelotLogger _logger; public DownstreamRouteProviderFactory(IServiceProvider provider, IOcelotLoggerFactory factory) { @@ -22,7 +22,7 @@ { //todo - this is a bit hacky we are saying there are no reRoutes or there are reRoutes but none of them have //an upstream path template which means they are dyanmic and service discovery is on... - if((!config.ReRoutes.Any() || config.ReRoutes.All(x => string.IsNullOrEmpty(x.UpstreamPathTemplate.Value))) && IsServiceDiscovery(config.ServiceProviderConfiguration)) + if((!config.ReRoutes.Any() || config.ReRoutes.All(x => string.IsNullOrEmpty(x.UpstreamTemplatePattern?.OriginalValue))) && IsServiceDiscovery(config.ServiceProviderConfiguration)) { _logger.LogInformation($"Selected {nameof(DownstreamRouteCreator)} as DownstreamRouteProvider for this request"); return _providers[nameof(DownstreamRouteCreator)]; diff --git a/src/Ocelot/DownstreamRouteFinder/Middleware/DownstreamRouteFinderMiddleware.cs b/src/Ocelot/DownstreamRouteFinder/Middleware/DownstreamRouteFinderMiddleware.cs index 3916721d..cf777056 100644 --- a/src/Ocelot/DownstreamRouteFinder/Middleware/DownstreamRouteFinderMiddleware.cs +++ b/src/Ocelot/DownstreamRouteFinder/Middleware/DownstreamRouteFinderMiddleware.cs @@ -51,7 +51,7 @@ namespace Ocelot.DownstreamRouteFinder.Middleware return; } - var downstreamPathTemplates = string.Join(", ", downstreamRoute.Data.ReRoute.DownstreamReRoute.Select(r => r.DownstreamPathTemplate.Value)); + var downstreamPathTemplates = string.Join(", ", downstreamRoute.Data.ReRoute.DownstreamReRoute.Select(r => r.DownstreamDownstreamPathTemplate.Value)); Logger.LogDebug($"downstream templates are {downstreamPathTemplates}"); diff --git a/src/Ocelot/DownstreamRouteFinder/UrlMatcher/RegExUrlMatcher.cs b/src/Ocelot/DownstreamRouteFinder/UrlMatcher/RegExUrlMatcher.cs index d1706118..ad1117af 100644 --- a/src/Ocelot/DownstreamRouteFinder/UrlMatcher/RegExUrlMatcher.cs +++ b/src/Ocelot/DownstreamRouteFinder/UrlMatcher/RegExUrlMatcher.cs @@ -14,7 +14,7 @@ namespace Ocelot.DownstreamRouteFinder.UrlMatcher return regex.IsMatch(upstreamUrlPath) ? new OkResponse(new UrlMatch(true)) : new OkResponse(new UrlMatch(false)); - } + } return regex.IsMatch($"{upstreamUrlPath}{upstreamQueryString}") ? new OkResponse(new UrlMatch(true)) diff --git a/src/Ocelot/DownstreamUrlCreator/Middleware/DownstreamUrlCreatorMiddleware.cs b/src/Ocelot/DownstreamUrlCreator/Middleware/DownstreamUrlCreatorMiddleware.cs index 02b40c07..e8efc60d 100644 --- a/src/Ocelot/DownstreamUrlCreator/Middleware/DownstreamUrlCreatorMiddleware.cs +++ b/src/Ocelot/DownstreamUrlCreator/Middleware/DownstreamUrlCreatorMiddleware.cs @@ -27,7 +27,7 @@ namespace Ocelot.DownstreamUrlCreator.Middleware public async Task Invoke(DownstreamContext context) { var response = _replacer - .Replace(context.DownstreamReRoute.DownstreamPathTemplate, context.TemplatePlaceholderNameAndValues); + .Replace(context.DownstreamReRoute.DownstreamDownstreamPathTemplate, context.TemplatePlaceholderNameAndValues); if (response.IsError) { diff --git a/src/Ocelot/DownstreamUrlCreator/UrlTemplateReplacer/DownstreamTemplatePathPlaceholderReplacer.cs b/src/Ocelot/DownstreamUrlCreator/UrlTemplateReplacer/DownstreamTemplatePathPlaceholderReplacer.cs index 1b744819..8597a1a6 100644 --- a/src/Ocelot/DownstreamUrlCreator/UrlTemplateReplacer/DownstreamTemplatePathPlaceholderReplacer.cs +++ b/src/Ocelot/DownstreamUrlCreator/UrlTemplateReplacer/DownstreamTemplatePathPlaceholderReplacer.cs @@ -8,11 +8,11 @@ namespace Ocelot.DownstreamUrlCreator.UrlTemplateReplacer { public class DownstreamTemplatePathPlaceholderReplacer : IDownstreamPathPlaceholderReplacer { - public Response Replace(PathTemplate downstreamPathTemplate, List urlPathPlaceholderNameAndValues) + public Response Replace(DownstreamPathTemplate downstreamDownstreamPathTemplate, List urlPathPlaceholderNameAndValues) { var downstreamPath = new StringBuilder(); - downstreamPath.Append(downstreamPathTemplate.Value); + downstreamPath.Append(downstreamDownstreamPathTemplate.Value); foreach (var placeholderVariableAndValue in urlPathPlaceholderNameAndValues) { @@ -22,4 +22,4 @@ namespace Ocelot.DownstreamUrlCreator.UrlTemplateReplacer return new OkResponse(new DownstreamPath(downstreamPath.ToString())); } } -} \ No newline at end of file +} diff --git a/src/Ocelot/DownstreamUrlCreator/UrlTemplateReplacer/IDownstreamPathPlaceholderReplacer.cs b/src/Ocelot/DownstreamUrlCreator/UrlTemplateReplacer/IDownstreamPathPlaceholderReplacer.cs index 46e998d4..8455d048 100644 --- a/src/Ocelot/DownstreamUrlCreator/UrlTemplateReplacer/IDownstreamPathPlaceholderReplacer.cs +++ b/src/Ocelot/DownstreamUrlCreator/UrlTemplateReplacer/IDownstreamPathPlaceholderReplacer.cs @@ -7,6 +7,6 @@ namespace Ocelot.DownstreamUrlCreator.UrlTemplateReplacer { public interface IDownstreamPathPlaceholderReplacer { - Response Replace(PathTemplate downstreamPathTemplate, List urlPathPlaceholderNameAndValues); + Response Replace(DownstreamPathTemplate downstreamDownstreamPathTemplate, List urlPathPlaceholderNameAndValues); } -} \ No newline at end of file +} diff --git a/src/Ocelot/Headers/Middleware/HttpRequestHeadersBuilderMiddleware.cs b/src/Ocelot/Headers/Middleware/HttpRequestHeadersBuilderMiddleware.cs index ba340b3a..12332cb2 100644 --- a/src/Ocelot/Headers/Middleware/HttpRequestHeadersBuilderMiddleware.cs +++ b/src/Ocelot/Headers/Middleware/HttpRequestHeadersBuilderMiddleware.cs @@ -26,7 +26,7 @@ namespace Ocelot.Headers.Middleware { if (context.DownstreamReRoute.ClaimsToHeaders.Any()) { - Logger.LogInformation($"{context.DownstreamReRoute.DownstreamPathTemplate.Value} has instructions to convert claims to headers"); + Logger.LogInformation($"{context.DownstreamReRoute.DownstreamDownstreamPathTemplate.Value} has instructions to convert claims to headers"); var response = _addHeadersToRequest.SetHeadersOnDownstreamRequest(context.DownstreamReRoute.ClaimsToHeaders, context.HttpContext.User.Claims, context.DownstreamRequest); diff --git a/src/Ocelot/QueryStrings/Middleware/QueryStringBuilderMiddleware.cs b/src/Ocelot/QueryStrings/Middleware/QueryStringBuilderMiddleware.cs index bc886c5d..d5ad5002 100644 --- a/src/Ocelot/QueryStrings/Middleware/QueryStringBuilderMiddleware.cs +++ b/src/Ocelot/QueryStrings/Middleware/QueryStringBuilderMiddleware.cs @@ -26,7 +26,7 @@ namespace Ocelot.QueryStrings.Middleware { if (context.DownstreamReRoute.ClaimsToQueries.Any()) { - Logger.LogInformation($"{context.DownstreamReRoute.DownstreamPathTemplate.Value} has instructions to convert claims to queries"); + Logger.LogInformation($"{context.DownstreamReRoute.DownstreamDownstreamPathTemplate.Value} has instructions to convert claims to queries"); var response = _addQueriesToRequest.SetQueriesOnDownstreamRequest(context.DownstreamReRoute.ClaimsToQueries, context.HttpContext.User.Claims, context.DownstreamRequest); diff --git a/src/Ocelot/RateLimit/Middleware/ClientRateLimitMiddleware.cs b/src/Ocelot/RateLimit/Middleware/ClientRateLimitMiddleware.cs index 50eb7776..fea51733 100644 --- a/src/Ocelot/RateLimit/Middleware/ClientRateLimitMiddleware.cs +++ b/src/Ocelot/RateLimit/Middleware/ClientRateLimitMiddleware.cs @@ -34,7 +34,7 @@ namespace Ocelot.RateLimit.Middleware // check if rate limiting is enabled if (!context.DownstreamReRoute.EnableEndpointEndpointRateLimiting) { - Logger.LogInformation($"EndpointRateLimiting is not enabled for {context.DownstreamReRoute.DownstreamPathTemplate.Value}"); + Logger.LogInformation($"EndpointRateLimiting is not enabled for {context.DownstreamReRoute.DownstreamDownstreamPathTemplate.Value}"); await _next.Invoke(context); return; } @@ -45,7 +45,7 @@ namespace Ocelot.RateLimit.Middleware // check white list if (IsWhitelisted(identity, options)) { - Logger.LogInformation($"{context.DownstreamReRoute.DownstreamPathTemplate.Value} is white listed from rate limiting"); + Logger.LogInformation($"{context.DownstreamReRoute.DownstreamDownstreamPathTemplate.Value} is white listed from rate limiting"); await _next.Invoke(context); return; } @@ -112,7 +112,7 @@ namespace Ocelot.RateLimit.Middleware public virtual void LogBlockedRequest(HttpContext httpContext, ClientRequestIdentity identity, RateLimitCounter counter, RateLimitRule rule, DownstreamReRoute downstreamReRoute) { Logger.LogInformation( - $"Request {identity.HttpVerb}:{identity.Path} from ClientId {identity.ClientId} has been blocked, quota {rule.Limit}/{rule.Period} exceeded by {counter.TotalRequests}. Blocked by rule { downstreamReRoute.UpstreamPathTemplate.Value }, TraceIdentifier {httpContext.TraceIdentifier}."); + $"Request {identity.HttpVerb}:{identity.Path} from ClientId {identity.ClientId} has been blocked, quota {rule.Limit}/{rule.Period} exceeded by {counter.TotalRequests}. Blocked by rule { downstreamReRoute.UpstreamPathTemplate.OriginalValue }, TraceIdentifier {httpContext.TraceIdentifier}."); } public virtual Task ReturnQuotaExceededResponse(HttpContext httpContext, RateLimitOptions option, string retryAfter) diff --git a/src/Ocelot/Requester/HttpClientBuilder.cs b/src/Ocelot/Requester/HttpClientBuilder.cs index ec44e375..651cb2d3 100644 --- a/src/Ocelot/Requester/HttpClientBuilder.cs +++ b/src/Ocelot/Requester/HttpClientBuilder.cs @@ -13,7 +13,7 @@ namespace Ocelot.Requester private readonly IDelegatingHandlerHandlerFactory _factory; private readonly IHttpClientCache _cacheHandlers; private readonly IOcelotLogger _logger; - private string _cacheKey; + private DownstreamReRoute _cacheKey; private HttpClient _httpClient; private IHttpClient _client; private readonly TimeSpan _defaultTimeout; @@ -34,7 +34,7 @@ namespace Ocelot.Requester public IHttpClient Create(DownstreamContext context) { - _cacheKey = GetCacheKey(context); + _cacheKey = context.DownstreamReRoute; var httpClient = _cacheHandlers.Get(_cacheKey); @@ -51,7 +51,7 @@ namespace Ocelot.Requester handler.ServerCertificateCustomValidationCallback = (request, certificate, chain, errors) => true; _logger - .LogWarning($"You have ignored all SSL warnings by using DangerousAcceptAnyServerCertificateValidator for this DownstreamReRoute, UpstreamPathTemplate: {context.DownstreamReRoute.UpstreamPathTemplate}, DownstreamPathTemplate: {context.DownstreamReRoute.DownstreamPathTemplate}"); + .LogWarning($"You have ignored all SSL warnings by using DangerousAcceptAnyServerCertificateValidator for this DownstreamReRoute, UpstreamPathTemplate: {context.DownstreamReRoute.UpstreamPathTemplate}, DownstreamDownstreamPathTemplate: {context.DownstreamReRoute.DownstreamDownstreamPathTemplate}"); } var timeout = context.DownstreamReRoute.QosOptions.TimeoutValue == 0 @@ -127,14 +127,5 @@ namespace Ocelot.Requester }); return httpMessageHandler; } - - private string GetCacheKey(DownstreamContext request) - { - var cacheKey = $"{request.DownstreamRequest.Method}:{request.DownstreamRequest.OriginalString}"; - - _logger.LogDebug($"Cache key for request is {cacheKey}"); - - return cacheKey; - } } } diff --git a/src/Ocelot/Requester/IHttpClientCache.cs b/src/Ocelot/Requester/IHttpClientCache.cs index 8aaeeaab..c9e90f04 100644 --- a/src/Ocelot/Requester/IHttpClientCache.cs +++ b/src/Ocelot/Requester/IHttpClientCache.cs @@ -1,10 +1,11 @@ namespace Ocelot.Requester { using System; + using Configuration; public interface IHttpClientCache { - IHttpClient Get(string key); - void Set(string key, IHttpClient handler, TimeSpan expirationTime); + IHttpClient Get(DownstreamReRoute key); + void Set(DownstreamReRoute key, IHttpClient handler, TimeSpan expirationTime); } } diff --git a/src/Ocelot/Requester/MemoryHttpClientCache.cs b/src/Ocelot/Requester/MemoryHttpClientCache.cs index 58a6c166..b2fcc2a0 100644 --- a/src/Ocelot/Requester/MemoryHttpClientCache.cs +++ b/src/Ocelot/Requester/MemoryHttpClientCache.cs @@ -2,22 +2,23 @@ { using System; using System.Collections.Concurrent; + using Configuration; public class MemoryHttpClientCache : IHttpClientCache { - private readonly ConcurrentDictionary _httpClientsCache; + private readonly ConcurrentDictionary _httpClientsCache; public MemoryHttpClientCache() { - _httpClientsCache = new ConcurrentDictionary(); + _httpClientsCache = new ConcurrentDictionary(); } - public void Set(string key, IHttpClient client, TimeSpan expirationTime) + public void Set(DownstreamReRoute key, IHttpClient client, TimeSpan expirationTime) { _httpClientsCache.AddOrUpdate(key, client, (k, oldValue) => client); } - public IHttpClient Get(string key) + public IHttpClient Get(DownstreamReRoute key) { //todo handle error? return _httpClientsCache.TryGetValue(key, out var client) ? client : null; diff --git a/src/Ocelot/Requester/QoS/QosFactory.cs b/src/Ocelot/Requester/QoS/QosFactory.cs index 37211f4b..8916d6f2 100644 --- a/src/Ocelot/Requester/QoS/QosFactory.cs +++ b/src/Ocelot/Requester/QoS/QosFactory.cs @@ -27,7 +27,7 @@ namespace Ocelot.Requester.QoS return new OkResponse(handler(request, _ocelotLoggerFactory)); } - return new ErrorResponse(new UnableToFindQoSProviderError($"could not find qosProvider for {request.DownstreamScheme}{request.DownstreamAddresses}{request.DownstreamPathTemplate}")); + return new ErrorResponse(new UnableToFindQoSProviderError($"could not find qosProvider for {request.DownstreamScheme}{request.DownstreamAddresses}{request.DownstreamDownstreamPathTemplate}")); } } } diff --git a/src/Ocelot/Values/PathTemplate.cs b/src/Ocelot/Values/DownstreamPathTemplate.cs similarity index 58% rename from src/Ocelot/Values/PathTemplate.cs rename to src/Ocelot/Values/DownstreamPathTemplate.cs index 584f80ac..de2a30b8 100644 --- a/src/Ocelot/Values/PathTemplate.cs +++ b/src/Ocelot/Values/DownstreamPathTemplate.cs @@ -1,12 +1,12 @@ -namespace Ocelot.Values -{ - public class PathTemplate - { - public PathTemplate(string value) - { - Value = value; - } - - public string Value { get; } - } -} +namespace Ocelot.Values +{ + public class DownstreamPathTemplate + { + public DownstreamPathTemplate(string value) + { + Value = value; + } + + public string Value { get; } + } +} diff --git a/src/Ocelot/Values/UpstreamPathTemplate.cs b/src/Ocelot/Values/UpstreamPathTemplate.cs index b42c887e..082b6a83 100644 --- a/src/Ocelot/Values/UpstreamPathTemplate.cs +++ b/src/Ocelot/Values/UpstreamPathTemplate.cs @@ -2,16 +2,20 @@ namespace Ocelot.Values { public class UpstreamPathTemplate { - public UpstreamPathTemplate(string template, int priority, bool containsQueryString) + public UpstreamPathTemplate(string template, int priority, bool containsQueryString, string originalValue) { Template = template; Priority = priority; ContainsQueryString = containsQueryString; + OriginalValue = originalValue; } public string Template { get; } - public int Priority { get; } + public int Priority { get; } + public bool ContainsQueryString { get; } + + public string OriginalValue { get; } } } diff --git a/test/Ocelot.AcceptanceTests/HttpClientCachingTests.cs b/test/Ocelot.AcceptanceTests/HttpClientCachingTests.cs new file mode 100644 index 00000000..85b17daf --- /dev/null +++ b/test/Ocelot.AcceptanceTests/HttpClientCachingTests.cs @@ -0,0 +1,163 @@ +namespace Ocelot.AcceptanceTests +{ + using System; + using System.Collections.Concurrent; + using System.Collections.Generic; + using System.Net; + using Configuration; + using Microsoft.AspNetCore.Http; + using Ocelot.Configuration.File; + using Requester; + using Shouldly; + using TestStack.BDDfy; + using Xunit; + + public class HttpClientCachingTests : IDisposable + { + private readonly Steps _steps; + private string _downstreamPath; + private readonly ServiceHandler _serviceHandler; + + public HttpClientCachingTests() + { + _serviceHandler = new ServiceHandler(); + _steps = new Steps(); + } + + [Fact] + public void should_cache_one_http_client_same_re_route() + { + var configuration = new FileConfiguration + { + ReRoutes = new List + { + new FileReRoute + { + DownstreamPathTemplate = "/", + DownstreamScheme = "http", + DownstreamHostAndPorts = new List + { + new FileHostAndPort + { + Host = "localhost", + Port = 51879, + } + }, + UpstreamPathTemplate = "/", + UpstreamHttpMethod = new List { "Get" }, + } + } + }; + + var cache = new FakeHttpClientCache(); + + this.Given(x => x.GivenThereIsAServiceRunningOn("http://localhost:51879", 200, "Hello from Laura")) + .And(x => _steps.GivenThereIsAConfiguration(configuration)) + .And(x => _steps.GivenOcelotIsRunningWithFakeHttpClientCache(cache)) + .When(x => _steps.WhenIGetUrlOnTheApiGateway("/")) + .When(x => _steps.WhenIGetUrlOnTheApiGateway("/")) + .When(x => _steps.WhenIGetUrlOnTheApiGateway("/")) + .When(x => _steps.WhenIGetUrlOnTheApiGateway("/")) + .Then(x => _steps.ThenTheStatusCodeShouldBe(HttpStatusCode.OK)) + .And(x => _steps.ThenTheResponseBodyShouldBe("Hello from Laura")) + .And(x => cache.Count.ShouldBe(1)) + .BDDfy(); + } + + [Fact] + public void should_cache_two_http_client_different_re_route() + { + var configuration = new FileConfiguration + { + ReRoutes = new List + { + new FileReRoute + { + DownstreamPathTemplate = "/", + DownstreamScheme = "http", + DownstreamHostAndPorts = new List + { + new FileHostAndPort + { + Host = "localhost", + Port = 51879, + } + }, + UpstreamPathTemplate = "/", + UpstreamHttpMethod = new List { "Get" }, + }, + new FileReRoute + { + DownstreamPathTemplate = "/two", + DownstreamScheme = "http", + DownstreamHostAndPorts = new List + { + new FileHostAndPort + { + Host = "localhost", + Port = 51879, + } + }, + UpstreamPathTemplate = "/two", + UpstreamHttpMethod = new List { "Get" }, + } + } + }; + + var cache = new FakeHttpClientCache(); + + this.Given(x => x.GivenThereIsAServiceRunningOn("http://localhost:51879", 200, "Hello from Laura")) + .And(x => _steps.GivenThereIsAConfiguration(configuration)) + .And(x => _steps.GivenOcelotIsRunningWithFakeHttpClientCache(cache)) + .When(x => _steps.WhenIGetUrlOnTheApiGateway("/")) + .When(x => _steps.WhenIGetUrlOnTheApiGateway("/two")) + .When(x => _steps.WhenIGetUrlOnTheApiGateway("/two")) + .When(x => _steps.WhenIGetUrlOnTheApiGateway("/")) + .When(x => _steps.WhenIGetUrlOnTheApiGateway("/")) + .When(x => _steps.WhenIGetUrlOnTheApiGateway("/two")) + .When(x => _steps.WhenIGetUrlOnTheApiGateway("/")) + .Then(x => _steps.ThenTheStatusCodeShouldBe(HttpStatusCode.OK)) + .And(x => _steps.ThenTheResponseBodyShouldBe("Hello from Laura")) + .And(x => cache.Count.ShouldBe(2)) + .BDDfy(); + } + + private void GivenThereIsAServiceRunningOn(string baseUrl, int statusCode, string responseBody) + { + _serviceHandler.GivenThereIsAServiceRunningOn(baseUrl, async context => + { + context.Response.StatusCode = statusCode; + await context.Response.WriteAsync(responseBody); + }); + } + + public void Dispose() + { + _serviceHandler.Dispose(); + _steps.Dispose(); + } + + public class FakeHttpClientCache : IHttpClientCache + { + private readonly ConcurrentDictionary _httpClientsCache; + + public FakeHttpClientCache() + { + _httpClientsCache = new ConcurrentDictionary(); + } + + public void Set(DownstreamReRoute key, IHttpClient client, TimeSpan expirationTime) + { + _httpClientsCache.AddOrUpdate(key, client, (k, oldValue) => client); + } + + public IHttpClient Get(DownstreamReRoute key) + { + //todo handle error? + return _httpClientsCache.TryGetValue(key, out var client) ? client : null; + } + + public int Count => _httpClientsCache.Count; + } + } +} diff --git a/test/Ocelot.AcceptanceTests/Steps.cs b/test/Ocelot.AcceptanceTests/Steps.cs index 7841083b..274f1554 100644 --- a/test/Ocelot.AcceptanceTests/Steps.cs +++ b/test/Ocelot.AcceptanceTests/Steps.cs @@ -29,6 +29,7 @@ using static Ocelot.Infrastructure.Wait; using Configuration.Repository; using Ocelot.Configuration.Creator; + using Requester; using CookieHeaderValue = System.Net.Http.Headers.CookieHeaderValue; using MediaTypeHeaderValue = System.Net.Http.Headers.MediaTypeHeaderValue; @@ -182,6 +183,35 @@ _ocelotClient = _ocelotServer.CreateClient(); } + public void GivenOcelotIsRunningWithFakeHttpClientCache(IHttpClientCache cache) + { + _webHostBuilder = new WebHostBuilder(); + + _webHostBuilder + .ConfigureAppConfiguration((hostingContext, config) => + { + config.SetBasePath(hostingContext.HostingEnvironment.ContentRootPath); + var env = hostingContext.HostingEnvironment; + config.AddJsonFile("appsettings.json", optional: true, reloadOnChange: false) + .AddJsonFile($"appsettings.{env.EnvironmentName}.json", optional: true, reloadOnChange: false); + config.AddJsonFile("ocelot.json", false, false); + config.AddEnvironmentVariables(); + }) + .ConfigureServices(s => + { + s.AddSingleton(cache); + s.AddOcelot(); + }) + .Configure(app => + { + app.UseOcelot().Wait(); + }); + + _ocelotServer = new TestServer(_webHostBuilder); + + _ocelotClient = _ocelotServer.CreateClient(); + } + internal void GivenIWait(int wait) { Thread.Sleep(wait); diff --git a/test/Ocelot.Benchmarks/DictionaryBenchmarks.cs b/test/Ocelot.Benchmarks/DictionaryBenchmarks.cs new file mode 100644 index 00000000..05d5b6ba --- /dev/null +++ b/test/Ocelot.Benchmarks/DictionaryBenchmarks.cs @@ -0,0 +1,77 @@ +using BenchmarkDotNet.Attributes; +using BenchmarkDotNet.Columns; +using BenchmarkDotNet.Configs; +using System.Net.Http; +using BenchmarkDotNet.Diagnosers; +using BenchmarkDotNet.Validators; + +namespace Ocelot.Benchmarks +{ + using System.Collections.Concurrent; + using Configuration; + using Configuration.Builder; + using Requester; + + [Config(typeof(DictionaryBenchmarks))] + public class DictionaryBenchmarks : ManualConfig + { + private ConcurrentDictionary _downstreamReRouteDictionary; + private ConcurrentDictionary _stringReRouteDictionary; + private HttpClientWrapper _client; + private string _stringKey; + private DownstreamReRoute _downstreamReRouteKey; + + public DictionaryBenchmarks() + { + Add(StatisticColumn.AllStatistics); + Add(MemoryDiagnoser.Default); + Add(BaselineValidator.FailOnError); + } + + [GlobalSetup] + public void SetUp() + { + _downstreamReRouteKey = new DownstreamReRouteBuilder().Build(); + _stringKey = "test"; + _client = new HttpClientWrapper(new HttpClient()); + _downstreamReRouteDictionary = new ConcurrentDictionary(); + + _downstreamReRouteDictionary.TryAdd(new DownstreamReRouteBuilder().Build(), new HttpClientWrapper(new HttpClient())); + _downstreamReRouteDictionary.TryAdd(new DownstreamReRouteBuilder().Build(), new HttpClientWrapper(new HttpClient())); + _downstreamReRouteDictionary.TryAdd(new DownstreamReRouteBuilder().Build(), new HttpClientWrapper(new HttpClient())); + _downstreamReRouteDictionary.TryAdd(new DownstreamReRouteBuilder().Build(), new HttpClientWrapper(new HttpClient())); + _downstreamReRouteDictionary.TryAdd(new DownstreamReRouteBuilder().Build(), new HttpClientWrapper(new HttpClient())); + _downstreamReRouteDictionary.TryAdd(new DownstreamReRouteBuilder().Build(), new HttpClientWrapper(new HttpClient())); + _downstreamReRouteDictionary.TryAdd(new DownstreamReRouteBuilder().Build(), new HttpClientWrapper(new HttpClient())); + _downstreamReRouteDictionary.TryAdd(new DownstreamReRouteBuilder().Build(), new HttpClientWrapper(new HttpClient())); + _downstreamReRouteDictionary.TryAdd(new DownstreamReRouteBuilder().Build(), new HttpClientWrapper(new HttpClient())); + _downstreamReRouteDictionary.TryAdd(new DownstreamReRouteBuilder().Build(), new HttpClientWrapper(new HttpClient())); + + _stringReRouteDictionary = new ConcurrentDictionary(); + _stringReRouteDictionary.TryAdd("1", new HttpClientWrapper(new HttpClient())); + _stringReRouteDictionary.TryAdd("2", new HttpClientWrapper(new HttpClient())); + _stringReRouteDictionary.TryAdd("3", new HttpClientWrapper(new HttpClient())); + _stringReRouteDictionary.TryAdd("4", new HttpClientWrapper(new HttpClient())); + _stringReRouteDictionary.TryAdd("5", new HttpClientWrapper(new HttpClient())); + _stringReRouteDictionary.TryAdd("6", new HttpClientWrapper(new HttpClient())); + _stringReRouteDictionary.TryAdd("7", new HttpClientWrapper(new HttpClient())); + _stringReRouteDictionary.TryAdd("8", new HttpClientWrapper(new HttpClient())); + _stringReRouteDictionary.TryAdd("9", new HttpClientWrapper(new HttpClient())); + _stringReRouteDictionary.TryAdd("10", new HttpClientWrapper(new HttpClient())); + } + + [Benchmark(Baseline = true)] + public IHttpClient StringKey() + { + _stringReRouteDictionary.AddOrUpdate(_stringKey, _client, (k, oldValue) => _client); + return _stringReRouteDictionary.TryGetValue(_stringKey, out var client) ? client : null; + } + + [Benchmark] + public IHttpClient DownstreamReRouteKey() + { + _downstreamReRouteDictionary.AddOrUpdate(_downstreamReRouteKey, _client, (k, oldValue) => _client); + return _downstreamReRouteDictionary.TryGetValue(_downstreamReRouteKey, out var client) ? client : null; + } + } +} diff --git a/test/Ocelot.Benchmarks/Program.cs b/test/Ocelot.Benchmarks/Program.cs index 8601eeaa..d830a46b 100644 --- a/test/Ocelot.Benchmarks/Program.cs +++ b/test/Ocelot.Benchmarks/Program.cs @@ -7,6 +7,7 @@ namespace Ocelot.Benchmarks public static void Main(string[] args) { var switcher = new BenchmarkSwitcher(new[] { + typeof(DictionaryBenchmarks), typeof(UrlPathToUrlPathTemplateMatcherBenchmarks), typeof(AllTheThingsBenchmarks), typeof(ExceptionHandlerMiddlewareBenchmarks) diff --git a/test/Ocelot.UnitTests/Authorization/AuthorisationMiddlewareTests.cs b/test/Ocelot.UnitTests/Authorization/AuthorisationMiddlewareTests.cs index 472c8643..15e86230 100644 --- a/test/Ocelot.UnitTests/Authorization/AuthorisationMiddlewareTests.cs +++ b/test/Ocelot.UnitTests/Authorization/AuthorisationMiddlewareTests.cs @@ -16,6 +16,7 @@ namespace Ocelot.UnitTests.Authorization using Xunit; using Microsoft.AspNetCore.Http; using Ocelot.Configuration; + using Values; public class AuthorisationMiddlewareTests { @@ -44,6 +45,7 @@ namespace Ocelot.UnitTests.Authorization { this.Given(x => x.GivenTheDownStreamRouteIs(new List(), new DownstreamReRouteBuilder() + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().Build()) .WithIsAuthorised(true) .WithUpstreamHttpMethod(new List { "Get" }) .Build())) diff --git a/test/Ocelot.UnitTests/Configuration/FileInternalConfigurationCreatorTests.cs b/test/Ocelot.UnitTests/Configuration/FileInternalConfigurationCreatorTests.cs index f545e04c..7f041d7b 100644 --- a/test/Ocelot.UnitTests/Configuration/FileInternalConfigurationCreatorTests.cs +++ b/test/Ocelot.UnitTests/Configuration/FileInternalConfigurationCreatorTests.cs @@ -13,7 +13,6 @@ using Shouldly; using TestStack.BDDfy; using Xunit; - using Ocelot.DependencyInjection; using Ocelot.Errors; using Ocelot.UnitTests.TestData; using Ocelot.Values; @@ -83,9 +82,9 @@ .Build(); var downstreamReRoute = new DownstreamReRouteBuilder() + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithTemplate("woop").WithOriginalValue("/api/products/{productId}").Build()) .WithDownstreamAddresses(new List() { new DownstreamHostAndPort("127.0.0.1", 80) }) .WithDownstreamPathTemplate("/products/{productId}") - .WithUpstreamPathTemplate("/api/products/{productId}") .WithUpstreamHttpMethod(new List { "Get" }) .WithLoadBalancerKey("CookieStickySessions:sessionid") .Build(); @@ -116,6 +115,7 @@ }, })) .And(x => x.GivenTheConfigIsValid()) + .And(x => GivenTheUpstreamTemplatePatternCreatorReturns("woop", "/api/products/{productId}")) .And(x => GivenTheDownstreamAddresses()) .And(x => GivenTheHeaderFindAndReplaceCreatorReturns()) .And(x => x.GivenTheFollowingOptionsAreReturned(reRouteOptions)) @@ -124,7 +124,7 @@ { new ReRouteBuilder() .WithDownstreamReRoute(downstreamReRoute) - .WithUpstreamPathTemplate("/api/products/{productId}") + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithTemplate("woop").WithOriginalValue("/api/products/{productId}").Build()) .WithUpstreamHttpMethod(new List { "Get" }) .Build() })) @@ -206,7 +206,7 @@ var lauraReRoute = new ReRouteBuilder() .WithUpstreamHttpMethod(new List() { "Get" }) .WithUpstreamHost("localhost") - .WithUpstreamPathTemplate("/laura") + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithTemplate("woop").WithOriginalValue("/laura").Build()) .WithDownstreamReRoute(lauraDownstreamReRoute) .Build(); @@ -225,14 +225,14 @@ var tomReRoute = new ReRouteBuilder() .WithUpstreamHttpMethod(new List() { "Get" }) .WithUpstreamHost("localhost") - .WithUpstreamPathTemplate("/tom") + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithTemplate("woop").WithOriginalValue("/tom").Build()) .WithDownstreamReRoute(tomDownstreamReRoute) .Build(); expected.Add(tomReRoute); var aggregateReReRoute = new ReRouteBuilder() - .WithUpstreamPathTemplate("/") + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithTemplate("woop").WithOriginalValue("/").Build()) .WithUpstreamHost("localhost") .WithDownstreamReRoute(lauraDownstreamReRoute) .WithDownstreamReRoute(tomDownstreamReRoute) @@ -241,7 +241,18 @@ expected.Add(aggregateReReRoute); + var tupleList = new List<(string, string)> + { + ("woop", "/laura"), + ("woop", "/laura"), + ("woop", "/tom"), + ("woop", "/tom"), + ("woop", "/"), + ("woop", "/") + }; + this.Given(x => x.GivenTheConfigIs(configuration)) + .And(x => GivenTheUpstreamTemplatePatternCreatorReturns(tupleList.ToArray())) .And(x => x.GivenTheFollowingOptionsAreReturned(new ReRouteOptionsBuilder().Build())) .And(x => x.GivenTheFollowingIsReturned(serviceProviderConfig)) .And(x => GivenTheDownstreamAddresses()) @@ -249,7 +260,7 @@ .And(x => x.GivenTheConfigIsValid()) .When(x => x.WhenICreateTheConfig()) .Then(x => x.ThenTheServiceProviderCreatorIsCalledCorrectly()) - .Then(x => x.ThenTheReRoutesAre(expected)) + .Then(x => x.ThenTheAggregateReRoutesAre(expected)) .BDDfy(); } @@ -406,9 +417,9 @@ .Build(); var downstreamReRoute = new DownstreamReRouteBuilder() + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithTemplate("woop").WithOriginalValue("/api/products/{productId}").Build()) .WithDownstreamAddresses(new List() {new DownstreamHostAndPort("127.0.0.1", 80)}) .WithDownstreamPathTemplate("/products/{productId}") - .WithUpstreamPathTemplate("/api/products/{productId}") .WithUpstreamHttpMethod(new List {"Get"}) .WithLoadBalancerKey("/api/products/{productId}|Get|127.0.0.1:0") .Build(); @@ -433,6 +444,7 @@ }, })) .And(x => x.GivenTheConfigIsValid()) + .And(x => GivenTheUpstreamTemplatePatternCreatorReturns("woop", "/api/products/{productId}")) .And(x => GivenTheDownstreamAddresses()) .And(x => GivenTheHeaderFindAndReplaceCreatorReturns()) .And(x => x.GivenTheFollowingOptionsAreReturned(reRouteOptions)) @@ -441,7 +453,7 @@ { new ReRouteBuilder() .WithDownstreamReRoute(downstreamReRoute) - .WithUpstreamPathTemplate("/api/products/{productId}") + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithTemplate("woop").WithOriginalValue("/api/products/{productId}").Build()) .WithUpstreamHttpMethod(new List { "Get" }) .Build() })) @@ -459,7 +471,7 @@ var downstreamReRoute = new DownstreamReRouteBuilder() .WithDownstreamScheme("https") .WithDownstreamPathTemplate("/products/{productId}") - .WithUpstreamPathTemplate("/api/products/{productId}") + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithTemplate("woop").WithOriginalValue("/api/products/{productId}").Build()) .WithUpstreamHttpMethod(new List {"Get"}) .WithDelegatingHandlers(handlers) .WithLoadBalancerKey("/api/products/{productId}|Get|") @@ -480,6 +492,7 @@ }, })) .And(x => x.GivenTheConfigIsValid()) + .And(x => GivenTheUpstreamTemplatePatternCreatorReturns("woop", "/api/products/{productId}")) .And(x => GivenTheDownstreamAddresses()) .And(x => GivenTheHeaderFindAndReplaceCreatorReturns()) .And(x => x.GivenTheFollowingOptionsAreReturned(reRouteOptions)) @@ -488,7 +501,7 @@ { new ReRouteBuilder() .WithDownstreamReRoute(downstreamReRoute) - .WithUpstreamPathTemplate("/api/products/{productId}") + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithTemplate("woop").WithOriginalValue("/api/products/{productId}").Build()) .WithUpstreamHttpMethod(new List { "Get" }) .Build() })) @@ -503,7 +516,7 @@ var downstreamReRoute = new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("/products/{productId}") - .WithUpstreamPathTemplate("/api/products/{productId}") + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithTemplate("woop").WithOriginalValue("/api/products/{productId}").Build()) .WithUpstreamHttpMethod(new List {"Get"}) .WithUseServiceDiscovery(true) .WithServiceName("ProductService") @@ -532,6 +545,7 @@ } })) .And(x => x.GivenTheConfigIsValid()) + .And(x => GivenTheUpstreamTemplatePatternCreatorReturns("woop", "/api/products/{productId}")) .And(x => GivenTheDownstreamAddresses()) .And(x => GivenTheHeaderFindAndReplaceCreatorReturns()) .And(x => x.GivenTheFollowingOptionsAreReturned(reRouteOptions)) @@ -540,7 +554,7 @@ { new ReRouteBuilder() .WithDownstreamReRoute(downstreamReRoute) - .WithUpstreamPathTemplate("/api/products/{productId}") + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithTemplate("woop").WithOriginalValue("/api/products/{productId}").Build()) .WithUpstreamHttpMethod(new List { "Get" }) .Build() })) @@ -555,7 +569,7 @@ var downstreamReRoute = new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("/products/{productId}") - .WithUpstreamPathTemplate("/api/products/{productId}") + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithTemplate("woop").WithOriginalValue("/api/products/{productId}").Build()) .WithUpstreamHttpMethod(new List {"Get"}) .WithUseServiceDiscovery(false) .WithLoadBalancerKey("/api/products/{productId}|Get|") @@ -575,6 +589,7 @@ } })) .And(x => x.GivenTheConfigIsValid()) + .And(x => GivenTheUpstreamTemplatePatternCreatorReturns("woop", "/api/products/{productId}")) .And(x => GivenTheDownstreamAddresses()) .And(x => GivenTheHeaderFindAndReplaceCreatorReturns()) .And(x => x.GivenTheFollowingOptionsAreReturned(reRouteOptions)) @@ -583,7 +598,7 @@ { new ReRouteBuilder() .WithDownstreamReRoute(downstreamReRoute) - .WithUpstreamPathTemplate("/api/products/{productId}") + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithTemplate("woop").WithOriginalValue("/api/products/{productId}").Build()) .WithUpstreamHttpMethod(new List { "Get" }) .Build() })) @@ -598,9 +613,9 @@ var downstreamReRoute = new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("/products/{productId}") - .WithUpstreamPathTemplate("/api/products/{productId}") + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithOriginalValue("/api/products/{productId}").Build()) .WithUpstreamHttpMethod(new List {"Get"}) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("(?i)/api/products/.*/$", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("(?i)/api/products/.*/$", 1, false, "/api/products/{productId}")) .WithLoadBalancerKey("/api/products/{productId}|Get|") .Build(); @@ -621,15 +636,15 @@ .And(x => GivenTheDownstreamAddresses()) .And(x => GivenTheHeaderFindAndReplaceCreatorReturns()) .And(x => x.GivenTheFollowingOptionsAreReturned(reRouteOptions)) - .And(x => x.GivenTheUpstreamTemplatePatternCreatorReturns("(?i)/api/products/.*/$")) + .And(x => x.GivenTheUpstreamTemplatePatternCreatorReturns("(?i)/api/products/.*/$", "/api/products/{productId}")) .When(x => x.WhenICreateTheConfig()) .Then(x => x.ThenTheReRoutesAre(new List { new ReRouteBuilder() .WithDownstreamReRoute(downstreamReRoute) - .WithUpstreamPathTemplate("/api/products/{productId}") + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithOriginalValue("/api/products/{productId}").Build()) .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("(?i)/api/products/.*/$", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("(?i)/api/products/.*/$", 1, false, "/api/products/{productId}")) .Build() })) .BDDfy(); @@ -643,7 +658,7 @@ var downstreamReRoute = new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("/products/{productId}") - .WithUpstreamPathTemplate("/api/products/{productId}") + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithTemplate("woop").WithOriginalValue("/api/products/{productId}").Build()) .WithUpstreamHttpMethod(new List {"Get"}) .WithRequestIdKey("blahhhh") .WithLoadBalancerKey("/api/products/{productId}|Get|") @@ -667,6 +682,7 @@ } })) .And(x => x.GivenTheConfigIsValid()) + .And(x => GivenTheUpstreamTemplatePatternCreatorReturns("woop", "/api/products/{productId}")) .And(x => GivenTheDownstreamAddresses()) .And(x => GivenTheHeaderFindAndReplaceCreatorReturns()) .And(x => x.GivenTheFollowingOptionsAreReturned(reRouteOptions)) @@ -676,7 +692,7 @@ { new ReRouteBuilder() .WithDownstreamReRoute(downstreamReRoute) - .WithUpstreamPathTemplate("/api/products/{productId}") + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithTemplate("woop").WithOriginalValue("/api/products/{productId}").Build()) .WithUpstreamHttpMethod(new List { "Get" }) .Build() })) @@ -734,7 +750,7 @@ var downstreamReRoute = new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("/products/{productId}") - .WithUpstreamPathTemplate("/api/products/{productId}") + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithTemplate("woop").WithOriginalValue("/api/products/{productId}").Build()) .WithUpstreamHttpMethod(new List {"Get"}) .WithAuthenticationOptions(authenticationOptions) .WithClaimsToHeaders(new List @@ -748,12 +764,13 @@ { new ReRouteBuilder() .WithDownstreamReRoute(downstreamReRoute) - .WithUpstreamPathTemplate("/api/products/{productId}") + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithTemplate("woop").WithOriginalValue("/api/products/{productId}").Build()) .WithUpstreamHttpMethod(new List { "Get" }) .Build() }; this.Given(x => x.GivenTheConfigIs(fileConfig)) + .And(x => GivenTheUpstreamTemplatePatternCreatorReturns("woop", "/api/products/{productId}")) .And(x => GivenTheDownstreamAddresses()) .And(x => x.GivenTheConfigIsValid()) .And(x => GivenTheHeaderFindAndReplaceCreatorReturns()) @@ -781,7 +798,7 @@ var downstreamReRoute = new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("/products/{productId}") - .WithUpstreamPathTemplate("/api/products/{productId}") + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithTemplate("woop").WithOriginalValue("/api/products/{productId}").Build()) .WithUpstreamHttpMethod(new List {"Get"}) .WithAuthenticationOptions(authenticationOptions) .WithLoadBalancerKey("/api/products/{productId}|Get|") @@ -791,12 +808,13 @@ { new ReRouteBuilder() .WithDownstreamReRoute(downstreamReRoute) - .WithUpstreamPathTemplate("/api/products/{productId}") + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithTemplate("woop").WithOriginalValue("/api/products/{productId}").Build()) .WithUpstreamHttpMethod(new List { "Get" }) .Build() }; this.Given(x => x.GivenTheConfigIs(fileConfig)) + .And(x => GivenTheUpstreamTemplatePatternCreatorReturns("woop", "/api/products/{productId}")) .And(x => GivenTheDownstreamAddresses()) .And(x => x.GivenTheConfigIsValid()) .And(x => GivenTheHeaderFindAndReplaceCreatorReturns()) @@ -828,11 +846,6 @@ var reRouteOptions = new ReRouteOptionsBuilder() .Build(); - var downstreamReRoute = new DownstreamReRouteBuilder() - .WithEnableRateLimiting(true) - .WithRateLimitOptions(new RateLimitOptionsBuilder().Build()) - .Build(); - var rateLimitOptions = new RateLimitOptionsBuilder() .WithRateLimitRule(new RateLimitRule("1s", 1, 1)) .Build(); @@ -923,6 +936,31 @@ dynamic.RateLimitOptions.RateLimitRule.PeriodTimespan.ShouldBe(rateLimitOptions.PeriodTimespan); } + private void ThenTheAggregateReRoutesAre(List expectedReRoutes) + { + for (int i = 0; i < _config.Data.ReRoutes.Count; i++) + { + var result = _config.Data.ReRoutes[i]; + var expected = expectedReRoutes[i]; + + result.DownstreamReRoute.Count.ShouldBe(expected.DownstreamReRoute.Count); + + result.UpstreamHttpMethod.ShouldBe(expected.UpstreamHttpMethod); + result.UpstreamTemplatePattern.OriginalValue.ShouldBe(expected.UpstreamTemplatePattern.OriginalValue); + result.UpstreamTemplatePattern.Template.ShouldBe(expected.UpstreamTemplatePattern.Template); + + result.DownstreamReRoute[0].DownstreamDownstreamPathTemplate.Value.ShouldBe(expected.DownstreamReRoute[0].DownstreamDownstreamPathTemplate.Value); + result.DownstreamReRoute[0].ClaimsToClaims.Count.ShouldBe(expected.DownstreamReRoute[0].ClaimsToClaims.Count); + result.DownstreamReRoute[0].ClaimsToHeaders.Count.ShouldBe(expected.DownstreamReRoute[0].ClaimsToHeaders.Count); + result.DownstreamReRoute[0].ClaimsToQueries.Count.ShouldBe(expected.DownstreamReRoute[0].ClaimsToQueries.Count); + result.DownstreamReRoute[0].RequestIdKey.ShouldBe(expected.DownstreamReRoute[0].RequestIdKey); + result.DownstreamReRoute[0].LoadBalancerKey.ShouldBe(expected.DownstreamReRoute[0].LoadBalancerKey); + result.DownstreamReRoute[0].DelegatingHandlers.ShouldBe(expected.DownstreamReRoute[0].DelegatingHandlers); + result.DownstreamReRoute[0].AddHeadersToDownstream.ShouldBe(expected.DownstreamReRoute[0].AddHeadersToDownstream); + result.DownstreamReRoute[0].AddHeadersToUpstream.ShouldBe(expected.DownstreamReRoute[0].AddHeadersToUpstream, "AddHeadersToUpstream should be set"); + } + } + private void ThenTheReRoutesAre(List expectedReRoutes) { for (int i = 0; i < _config.Data.ReRoutes.Count; i++) @@ -932,10 +970,11 @@ result.DownstreamReRoute.Count.ShouldBe(expected.DownstreamReRoute.Count); - result.DownstreamReRoute[0].DownstreamPathTemplate.Value.ShouldBe(expected.DownstreamReRoute[0].DownstreamPathTemplate.Value); result.UpstreamHttpMethod.ShouldBe(expected.UpstreamHttpMethod); - result.UpstreamPathTemplate.Value.ShouldBe(expected.UpstreamPathTemplate.Value); - result.UpstreamTemplatePattern?.Template.ShouldBe(expected.UpstreamTemplatePattern?.Template); + result.UpstreamTemplatePattern.OriginalValue.ShouldBe(expected.UpstreamTemplatePattern.OriginalValue); + result.UpstreamTemplatePattern.Template.ShouldBe(expected.UpstreamTemplatePattern.Template); + + result.DownstreamReRoute[0].DownstreamDownstreamPathTemplate.Value.ShouldBe(expected.DownstreamReRoute[0].DownstreamDownstreamPathTemplate.Value); result.DownstreamReRoute[0].ClaimsToClaims.Count.ShouldBe(expected.DownstreamReRoute[0].ClaimsToClaims.Count); result.DownstreamReRoute[0].ClaimsToHeaders.Count.ShouldBe(expected.DownstreamReRoute[0].ClaimsToHeaders.Count); result.DownstreamReRoute[0].ClaimsToQueries.Count.ShouldBe(expected.DownstreamReRoute[0].ClaimsToQueries.Count); @@ -977,11 +1016,22 @@ .Verify(x => x.Create(_fileConfiguration.ReRoutes[0]), Times.Once); } - private void GivenTheUpstreamTemplatePatternCreatorReturns(string pattern) + private void GivenTheUpstreamTemplatePatternCreatorReturns(string pattern, string original) { _upstreamTemplatePatternCreator .Setup(x => x.Create(It.IsAny())) - .Returns(new UpstreamPathTemplate(pattern, 1, false)); + .Returns(new UpstreamPathTemplate(pattern, 1, false, original)); + } + + private void GivenTheUpstreamTemplatePatternCreatorReturns(params (string pattern, string original)[] list) + { + var builder = _upstreamTemplatePatternCreator + .SetupSequence(x => x.Create(It.IsAny())); + + foreach (var p in list) + { + builder.Returns(new UpstreamPathTemplate(p.pattern, 1, false, p.original)); + } } private void ThenTheRequestIdKeyCreatorIsCalledCorrectly() diff --git a/test/Ocelot.UnitTests/Configuration/InMemoryConfigurationRepositoryTests.cs b/test/Ocelot.UnitTests/Configuration/InMemoryConfigurationRepositoryTests.cs index dfa6362f..9c802961 100644 --- a/test/Ocelot.UnitTests/Configuration/InMemoryConfigurationRepositoryTests.cs +++ b/test/Ocelot.UnitTests/Configuration/InMemoryConfigurationRepositoryTests.cs @@ -42,7 +42,7 @@ namespace Ocelot.UnitTests.Configuration private void ThenTheConfigurationIsReturned() { - _getResult.Data.ReRoutes[0].DownstreamReRoute[0].DownstreamPathTemplate.Value.ShouldBe("initial"); + _getResult.Data.ReRoutes[0].DownstreamReRoute[0].DownstreamDownstreamPathTemplate.Value.ShouldBe("initial"); } private void WhenIGetTheConfiguration() diff --git a/test/Ocelot.UnitTests/DependencyInjection/ConfigurationBuilderExtensionsTests.cs b/test/Ocelot.UnitTests/DependencyInjection/ConfigurationBuilderExtensionsTests.cs index 43176e5a..112b7e0b 100644 --- a/test/Ocelot.UnitTests/DependencyInjection/ConfigurationBuilderExtensionsTests.cs +++ b/test/Ocelot.UnitTests/DependencyInjection/ConfigurationBuilderExtensionsTests.cs @@ -85,7 +85,7 @@ new FileReRoute { DownstreamScheme = "DownstreamScheme", - DownstreamPathTemplate = "DownstreamPathTemplate", + DownstreamPathTemplate = "DownstreamDownstreamPathTemplate", Key = "Key", UpstreamHost = "UpstreamHost", UpstreamHttpMethod = new List diff --git a/test/Ocelot.UnitTests/DownstreamRouteFinder/DownstreamRouteCreatorTests.cs b/test/Ocelot.UnitTests/DownstreamRouteFinder/DownstreamRouteCreatorTests.cs index a1c4b799..d946046b 100644 --- a/test/Ocelot.UnitTests/DownstreamRouteFinder/DownstreamRouteCreatorTests.cs +++ b/test/Ocelot.UnitTests/DownstreamRouteFinder/DownstreamRouteCreatorTests.cs @@ -211,7 +211,7 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder private void ThenTheDownstreamRouteIsCreated() { - _result.Data.ReRoute.DownstreamReRoute[0].DownstreamPathTemplate.Value.ShouldBe("/test"); + _result.Data.ReRoute.DownstreamReRoute[0].DownstreamDownstreamPathTemplate.Value.ShouldBe("/test"); _result.Data.ReRoute.UpstreamHttpMethod[0].ShouldBe(HttpMethod.Get); _result.Data.ReRoute.DownstreamReRoute[0].ServiceName.ShouldBe("auth"); _result.Data.ReRoute.DownstreamReRoute[0].LoadBalancerKey.ShouldBe("/auth/test|GET"); @@ -226,21 +226,21 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder private void ThenTheDownstreamPathIsForwardSlash() { - _result.Data.ReRoute.DownstreamReRoute[0].DownstreamPathTemplate.Value.ShouldBe("/"); + _result.Data.ReRoute.DownstreamReRoute[0].DownstreamDownstreamPathTemplate.Value.ShouldBe("/"); _result.Data.ReRoute.DownstreamReRoute[0].ServiceName.ShouldBe("auth"); _result.Data.ReRoute.DownstreamReRoute[0].LoadBalancerKey.ShouldBe("/auth/|GET"); } private void ThenThePathDoesNotHaveTrailingSlash() { - _result.Data.ReRoute.DownstreamReRoute[0].DownstreamPathTemplate.Value.ShouldBe("/test"); + _result.Data.ReRoute.DownstreamReRoute[0].DownstreamDownstreamPathTemplate.Value.ShouldBe("/test"); _result.Data.ReRoute.DownstreamReRoute[0].ServiceName.ShouldBe("auth"); _result.Data.ReRoute.DownstreamReRoute[0].LoadBalancerKey.ShouldBe("/auth/test|GET"); } private void ThenTheQueryStringIsRemoved() { - _result.Data.ReRoute.DownstreamReRoute[0].DownstreamPathTemplate.Value.ShouldBe("/test"); + _result.Data.ReRoute.DownstreamReRoute[0].DownstreamDownstreamPathTemplate.Value.ShouldBe("/test"); _result.Data.ReRoute.DownstreamReRoute[0].ServiceName.ShouldBe("auth"); _result.Data.ReRoute.DownstreamReRoute[0].LoadBalancerKey.ShouldBe("/auth/test|GET"); } diff --git a/test/Ocelot.UnitTests/DownstreamRouteFinder/DownstreamRouteFinderTests.cs b/test/Ocelot.UnitTests/DownstreamRouteFinder/DownstreamRouteFinderTests.cs index 360d58f4..d640c959 100644 --- a/test/Ocelot.UnitTests/DownstreamRouteFinder/DownstreamRouteFinderTests.cs +++ b/test/Ocelot.UnitTests/DownstreamRouteFinder/DownstreamRouteFinderTests.cs @@ -47,24 +47,20 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder new ReRouteBuilder() .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPath") - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Post" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("test", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("test", 1, false, "someUpstreamPath")) .Build()) - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Post" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("test", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("test", 1, false, "someUpstreamPath")) .Build(), new ReRouteBuilder() .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPath") - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Post" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("test", 0, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("test", 0, false, "someUpstreamPath")) .Build()) - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Post" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("test", 0, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("test", 0, false, "someUpstreamPath")) .Build() }, string.Empty, serviceProviderConfig)) .And(x => x.GivenTheUrlMatcherReturns(new OkResponse(new UrlMatch(true)))) @@ -74,13 +70,11 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder new ReRouteBuilder() .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPath") - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("test", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("test", 1, false, "someUpstreamPath")) .WithUpstreamHttpMethod(new List { "Post" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("test", 1, false)) .Build()) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("test", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("test", 1, false, "someUpstreamPath")) .WithUpstreamHttpMethod(new List { "Post" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("test", 1, false)) .Build() ))) .BDDfy(); @@ -99,24 +93,20 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder new ReRouteBuilder() .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPath") - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Post" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("test", 0, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("test", 0, false, "someUpstreamPath")) .Build()) - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Post" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("test", 0, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("test", 0, false, "someUpstreamPath")) .Build(), new ReRouteBuilder() .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPath") - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Post" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("test", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("test", 1, false, "someUpstreamPath")) .Build()) - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Post" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("test", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("test", 1, false, "someUpstreamPath")) .Build() }, string.Empty, serviceProviderConfig)) .And(x => x.GivenTheUrlMatcherReturns(new OkResponse(new UrlMatch(true)))) @@ -126,10 +116,10 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder new ReRouteBuilder() .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPath") - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("test", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("test", 1, false, "someUpstreamPath")) .WithUpstreamHttpMethod(new List { "Post" }) .Build()) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("test", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("test", 1, false, "someUpstreamPath")) .WithUpstreamHttpMethod(new List { "Post" }) .Build() ))) @@ -150,13 +140,11 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder new ReRouteBuilder() .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPath") - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .Build()) - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .Build() }, string.Empty, serviceProviderConfig )) @@ -170,10 +158,10 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPath") .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .Build()) .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .Build() ))) .And(x => x.ThenTheUrlMatcherIsCalledCorrectly()) @@ -194,13 +182,11 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder new ReRouteBuilder() .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPath") - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .Build()) - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .Build() }, string.Empty, serviceProviderConfig )) @@ -214,10 +200,10 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPath") .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .Build()) .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .Build() ))) .And(x => x.ThenTheUrlMatcherIsCalledCorrectly("matchInUrlMatcher")) @@ -239,13 +225,11 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder new ReRouteBuilder() .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPath") - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .Build()) - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .Build() }, string.Empty, serviceProviderConfig )) @@ -258,10 +242,10 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPath") .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .Build()) .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .Build() ))) .BDDfy(); @@ -282,24 +266,20 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder new ReRouteBuilder() .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPath") - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false, "someUpstreamPath")) .Build()) - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false, "someUpstreamPath")) .Build(), new ReRouteBuilder() .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPathForAPost") - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Post" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false, "someUpstreamPath")) .Build()) - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Post" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false, "someUpstreamPath")) .Build() }, string.Empty, serviceProviderConfig )) @@ -312,10 +292,10 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPathForAPost") .WithUpstreamHttpMethod(new List { "Post" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false, "someUpstreamPath")) .Build()) .WithUpstreamHttpMethod(new List { "Post" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false, "someUpstreamPath")) .Build() ))) .BDDfy(); @@ -332,13 +312,11 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder new ReRouteBuilder() .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("somPath") - .WithUpstreamPathTemplate("somePath") .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("somePath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("somePath", 1, false, "someUpstreamPath")) .Build()) - .WithUpstreamPathTemplate("somePath") .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("somePath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("somePath", 1, false, "someUpstreamPath")) .Build(), }, string.Empty, serviceProviderConfig )) @@ -366,13 +344,11 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder new ReRouteBuilder() .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPath") - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Get", "Post" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false, "someUpstreamPath")) .Build()) - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Get", "Post" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false, "someUpstreamPath")) .Build() }, string.Empty, serviceProviderConfig )) @@ -385,10 +361,10 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPath") .WithUpstreamHttpMethod(new List { "Post" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false, "someUpstreamPath")) .Build()) .WithUpstreamHttpMethod(new List { "Post" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false, "someUpstreamPath")) .Build() ))) .BDDfy(); @@ -409,13 +385,11 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder new ReRouteBuilder() .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPath") - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List()) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false, "someUpstreamPath")) .Build()) - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List()) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false, "someUpstreamPath")) .Build() }, string.Empty, serviceProviderConfig )) @@ -428,10 +402,10 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPath") .WithUpstreamHttpMethod(new List { "Post" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false, "someUpstreamPath")) .Build()) .WithUpstreamHttpMethod(new List { "Post" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false, "someUpstreamPath")) .Build() ))) .BDDfy(); @@ -452,13 +426,11 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder new ReRouteBuilder() .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPath") - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Get", "Patch", "Delete" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false, "someUpstreamPath")) .Build()) - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Get", "Patch", "Delete" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("", 1, false, "someUpstreamPath")) .Build() }, string.Empty, serviceProviderConfig )) @@ -485,14 +457,12 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder new ReRouteBuilder() .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPath") - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .WithUpstreamHost("MATCH") .Build()) - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .WithUpstreamHost("MATCH") .Build() }, string.Empty, serviceProviderConfig @@ -507,10 +477,10 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPath") .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .Build()) .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .Build() ))) .And(x => x.ThenTheUrlMatcherIsCalledCorrectly()) @@ -532,13 +502,11 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder new ReRouteBuilder() .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPath") - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .Build()) - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .Build() }, string.Empty, serviceProviderConfig )) @@ -552,10 +520,10 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPath") .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .Build()) .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .Build() ))) .And(x => x.ThenTheUrlMatcherIsCalledCorrectly()) @@ -575,27 +543,23 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder new ReRouteBuilder() .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPath") - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .WithUpstreamHost("MATCH") .Build()) - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .WithUpstreamHost("MATCH") .Build(), new ReRouteBuilder() .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPath") - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { }) // empty list of methods - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .WithUpstreamHost("MATCH") .Build()) - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { }) // empty list of methods - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .WithUpstreamHost("MATCH") .Build() }, string.Empty, serviceProviderConfig @@ -621,14 +585,12 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder new ReRouteBuilder() .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPath") - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List()) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .WithUpstreamHost("MATCH") .Build()) - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List()) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .WithUpstreamHost("MATCH") .Build() }, string.Empty, serviceProviderConfig @@ -654,14 +616,12 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder new ReRouteBuilder() .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPath") - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List()) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .WithUpstreamHost("MATCH") .Build()) - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List()) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .WithUpstreamHost("MATCH") .Build() }, string.Empty, serviceProviderConfig @@ -688,25 +648,21 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder new ReRouteBuilder() .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("THENULLPATH") - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .Build()) - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .Build(), new ReRouteBuilder() .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPath") - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .WithUpstreamHost("MATCH") .Build()) - .WithUpstreamPathTemplate("someUpstreamPath") .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "someUpstreamPath")) .WithUpstreamHost("MATCH") .Build() }, string.Empty, serviceProviderConfig @@ -721,10 +677,10 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder .WithDownstreamReRoute(new DownstreamReRouteBuilder() .WithDownstreamPathTemplate("someDownstreamPath") .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "test")) .Build()) .WithUpstreamHttpMethod(new List { "Get" }) - .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false)) + .WithUpstreamTemplatePattern(new UpstreamPathTemplate("someUpstreamPath", 1, false, "test")) .Build() ))) .And(x => x.ThenTheUrlMatcherIsCalledCorrectly(2)) @@ -756,25 +712,25 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder private void ThenTheUrlMatcherIsCalledCorrectly() { _mockMatcher - .Verify(x => x.Match(_upstreamUrlPath, _upstreamQuery, _reRoutesConfig[0].UpstreamPathTemplate.Value, _reRoutesConfig[0].UpstreamTemplatePattern.ContainsQueryString), Times.Once); + .Verify(x => x.Match(_upstreamUrlPath, _upstreamQuery, _reRoutesConfig[0].UpstreamTemplatePattern.Template, _reRoutesConfig[0].UpstreamTemplatePattern.ContainsQueryString), Times.Once); } private void ThenTheUrlMatcherIsCalledCorrectly(int times) { _mockMatcher - .Verify(x => x.Match(_upstreamUrlPath, _upstreamQuery, _reRoutesConfig[0].UpstreamPathTemplate.Value, _reRoutesConfig[0].UpstreamTemplatePattern.ContainsQueryString), Times.Exactly(times)); + .Verify(x => x.Match(_upstreamUrlPath, _upstreamQuery, _reRoutesConfig[0].UpstreamTemplatePattern.OriginalValue, _reRoutesConfig[0].UpstreamTemplatePattern.ContainsQueryString), Times.Exactly(times)); } private void ThenTheUrlMatcherIsCalledCorrectly(string expectedUpstreamUrlPath) { _mockMatcher - .Verify(x => x.Match(expectedUpstreamUrlPath, _upstreamQuery, _reRoutesConfig[0].UpstreamPathTemplate.Value, _reRoutesConfig[0].UpstreamTemplatePattern.ContainsQueryString), Times.Once); + .Verify(x => x.Match(expectedUpstreamUrlPath, _upstreamQuery, _reRoutesConfig[0].UpstreamTemplatePattern.OriginalValue, _reRoutesConfig[0].UpstreamTemplatePattern.ContainsQueryString), Times.Once); } private void ThenTheUrlMatcherIsNotCalled() { _mockMatcher - .Verify(x => x.Match(_upstreamUrlPath, _upstreamQuery, _reRoutesConfig[0].UpstreamPathTemplate.Value, _reRoutesConfig[0].UpstreamTemplatePattern.ContainsQueryString), Times.Never); + .Verify(x => x.Match(_upstreamUrlPath, _upstreamQuery, _reRoutesConfig[0].UpstreamTemplatePattern.OriginalValue, _reRoutesConfig[0].UpstreamTemplatePattern.ContainsQueryString), Times.Never); } private void GivenTheUrlMatcherReturns(Response match) @@ -803,7 +759,7 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder private void ThenTheFollowingIsReturned(DownstreamRoute expected) { - _result.Data.ReRoute.DownstreamReRoute[0].DownstreamPathTemplate.Value.ShouldBe(expected.ReRoute.DownstreamReRoute[0].DownstreamPathTemplate.Value); + _result.Data.ReRoute.DownstreamReRoute[0].DownstreamDownstreamPathTemplate.Value.ShouldBe(expected.ReRoute.DownstreamReRoute[0].DownstreamDownstreamPathTemplate.Value); _result.Data.ReRoute.UpstreamTemplatePattern.Priority.ShouldBe(expected.ReRoute.UpstreamTemplatePattern.Priority); for (int i = 0; i < _result.Data.TemplatePlaceholderNameAndValues.Count; i++) diff --git a/test/Ocelot.UnitTests/DownstreamRouteFinder/DownstreamRouteProviderFactoryTests.cs b/test/Ocelot.UnitTests/DownstreamRouteFinder/DownstreamRouteProviderFactoryTests.cs index 0380f2fc..7f59c208 100644 --- a/test/Ocelot.UnitTests/DownstreamRouteFinder/DownstreamRouteProviderFactoryTests.cs +++ b/test/Ocelot.UnitTests/DownstreamRouteFinder/DownstreamRouteProviderFactoryTests.cs @@ -5,11 +5,8 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder using Moq; using Ocelot.Configuration; using Ocelot.Configuration.Builder; - using Ocelot.DownstreamRouteFinder; using Ocelot.DownstreamRouteFinder.Finder; using Ocelot.DownstreamRouteFinder.UrlMatcher; - using Ocelot.Responses; - using Ocelot.Values; using Shouldly; using TestStack.BDDfy; using Xunit; @@ -30,8 +27,8 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder services.AddSingleton(); services.AddSingleton(); services.AddSingleton(); - services.AddSingleton(); - services.AddSingleton(); + services.AddSingleton(); + services.AddSingleton(); var provider = services.BuildServiceProvider(); _logger = new Mock(); _loggerFactory = new Mock(); @@ -49,7 +46,7 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder this.Given(_ => GivenTheReRoutes(reRoutes)) .When(_ => WhenIGet()) - .Then(_ => ThenTheResultShouldBe()) + .Then(_ => ThenTheResultShouldBe()) .BDDfy(); } @@ -59,12 +56,12 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder var spConfig = new ServiceProviderConfigurationBuilder().WithHost("test").WithPort(50).WithType("test").Build(); var reRoutes = new List { - new ReRouteBuilder().WithUpstreamPathTemplate("woot").Build() + new ReRouteBuilder().WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithOriginalValue("woot").Build()).Build() }; this.Given(_ => GivenTheReRoutes(reRoutes, spConfig)) .When(_ => WhenIGet()) - .Then(_ => ThenTheResultShouldBe()) + .Then(_ => ThenTheResultShouldBe()) .BDDfy(); } @@ -76,7 +73,7 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder this.Given(_ => GivenTheReRoutes(reRoutes, spConfig)) .When(_ => WhenIGet()) - .Then(_ => ThenTheResultShouldBe()) + .Then(_ => ThenTheResultShouldBe()) .BDDfy(); } @@ -88,7 +85,7 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder this.Given(_ => GivenTheReRoutes(reRoutes, spConfig)) .When(_ => WhenIGet()) - .Then(_ => ThenTheResultShouldBe()) + .Then(_ => ThenTheResultShouldBe()) .BDDfy(); } @@ -100,7 +97,7 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder this.Given(_ => GivenTheReRoutes(reRoutes, spConfig)) .When(_ => WhenIGet()) - .Then(_ => ThenTheResultShouldBe()) + .Then(_ => ThenTheResultShouldBe()) .BDDfy(); } @@ -112,7 +109,7 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder this.Given(_ => GivenTheReRoutes(reRoutes, spConfig)) .When(_ => WhenIGet()) - .Then(_ => ThenTheResultShouldBe()) + .Then(_ => ThenTheResultShouldBe()) .BDDfy(); } @@ -127,7 +124,7 @@ namespace Ocelot.UnitTests.DownstreamRouteFinder this.Given(_ => GivenTheReRoutes(reRoutes, spConfig)) .When(_ => WhenIGet()) - .Then(_ => ThenTheResultShouldBe()) + .Then(_ => ThenTheResultShouldBe()) .BDDfy(); } diff --git a/test/Ocelot.UnitTests/DownstreamUrlCreator/DownstreamUrlCreatorMiddlewareTests.cs b/test/Ocelot.UnitTests/DownstreamUrlCreator/DownstreamUrlCreatorMiddlewareTests.cs index ca190240..a022efe2 100644 --- a/test/Ocelot.UnitTests/DownstreamUrlCreator/DownstreamUrlCreatorMiddlewareTests.cs +++ b/test/Ocelot.UnitTests/DownstreamUrlCreator/DownstreamUrlCreatorMiddlewareTests.cs @@ -296,7 +296,7 @@ .WithDownstreamPathTemplate("/Authorized/{action}?server={server}") .WithUpstreamHttpMethod(new List { "Post", "Get" }) .WithDownstreamScheme("http") - .WithUpstreamPathTemplate("/uc/Authorized/{server}/{action}") + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithOriginalValue("/uc/Authorized/{server}/{action}").Build()) .Build(); var config = new ServiceProviderConfigurationBuilder() @@ -350,7 +350,7 @@ { _downstreamPath = new OkResponse(new DownstreamPath(path)); _downstreamUrlTemplateVariableReplacer - .Setup(x => x.Replace(It.IsAny(), It.IsAny>())) + .Setup(x => x.Replace(It.IsAny(), It.IsAny>())) .Returns(_downstreamPath); } diff --git a/test/Ocelot.UnitTests/DownstreamUrlCreator/UrlTemplateReplacer/UpstreamUrlPathTemplateVariableReplacerTests.cs b/test/Ocelot.UnitTests/DownstreamUrlCreator/UrlTemplateReplacer/UpstreamUrlPathTemplateVariableReplacerTests.cs index cd8cf3c8..3b72db1b 100644 --- a/test/Ocelot.UnitTests/DownstreamUrlCreator/UrlTemplateReplacer/UpstreamUrlPathTemplateVariableReplacerTests.cs +++ b/test/Ocelot.UnitTests/DownstreamUrlCreator/UrlTemplateReplacer/UpstreamUrlPathTemplateVariableReplacerTests.cs @@ -199,7 +199,7 @@ namespace Ocelot.UnitTests.DownstreamUrlCreator.UrlTemplateReplacer private void WhenIReplaceTheTemplateVariables() { - _result = _downstreamPathReplacer.Replace(_downstreamRoute.ReRoute.DownstreamReRoute[0].DownstreamPathTemplate, _downstreamRoute.TemplatePlaceholderNameAndValues); + _result = _downstreamPathReplacer.Replace(_downstreamRoute.ReRoute.DownstreamReRoute[0].DownstreamDownstreamPathTemplate, _downstreamRoute.TemplatePlaceholderNameAndValues); } private void ThenTheDownstreamUrlPathIsReturned(string expected) diff --git a/test/Ocelot.UnitTests/RateLimit/ClientRateLimitMiddlewareTests.cs b/test/Ocelot.UnitTests/RateLimit/ClientRateLimitMiddlewareTests.cs index 7d3cac1a..a8737a52 100644 --- a/test/Ocelot.UnitTests/RateLimit/ClientRateLimitMiddlewareTests.cs +++ b/test/Ocelot.UnitTests/RateLimit/ClientRateLimitMiddlewareTests.cs @@ -49,15 +49,22 @@ namespace Ocelot.UnitTests.RateLimit [Fact] public void should_call_middleware_and_ratelimiting() - { - var downstreamRoute = new DownstreamRoute(new List(), - new ReRouteBuilder() - .WithDownstreamReRoute(new DownstreamReRouteBuilder().WithEnableRateLimiting(true).WithRateLimitOptions( - new RateLimitOptions(true, "ClientId", new List(), false, "", "", new RateLimitRule("1s", 100, 3), 429)) - .WithUpstreamHttpMethod(new List { "Get" }) - .Build()) - .WithUpstreamHttpMethod(new List { "Get" }) - .Build()); + { + var upstreamTemplate = new UpstreamPathTemplateBuilder().Build(); + + var downstreamReRoute = new DownstreamReRouteBuilder() + .WithEnableRateLimiting(true) + .WithRateLimitOptions(new RateLimitOptions(true, "ClientId", new List(), false, "", "", new RateLimitRule("1s", 100, 3), 429)) + .WithUpstreamHttpMethod(new List {"Get"}) + .WithUpstreamTemplatePattern(upstreamTemplate) + .Build(); + + var reRoute = new ReRouteBuilder() + .WithDownstreamReRoute(downstreamReRoute) + .WithUpstreamHttpMethod(new List {"Get"}) + .Build(); + + var downstreamRoute = new DownstreamRoute(new List(), reRoute); this.Given(x => x.GivenTheDownStreamRouteIs(downstreamRoute)) .When(x => x.WhenICallTheMiddlewareMultipleTime(2)) diff --git a/test/Ocelot.UnitTests/Requester/HttpClientBuilderTests.cs b/test/Ocelot.UnitTests/Requester/HttpClientBuilderTests.cs index 1b0d17eb..4c671653 100644 --- a/test/Ocelot.UnitTests/Requester/HttpClientBuilderTests.cs +++ b/test/Ocelot.UnitTests/Requester/HttpClientBuilderTests.cs @@ -54,6 +54,7 @@ namespace Ocelot.UnitTests.Requester .WithQosOptions(qosOptions) .WithHttpHandlerOptions(new HttpHandlerOptions(false, false, false, true)) .WithLoadBalancerKey("") + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithOriginalValue("").Build()) .WithQosOptions(new QoSOptionsBuilder().Build()) .Build(); @@ -74,6 +75,7 @@ namespace Ocelot.UnitTests.Requester .WithQosOptions(qosOptions) .WithHttpHandlerOptions(new HttpHandlerOptions(false, false, false, true)) .WithLoadBalancerKey("") + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithOriginalValue("").Build()) .WithQosOptions(new QoSOptionsBuilder().Build()) .Build(); @@ -89,6 +91,68 @@ namespace Ocelot.UnitTests.Requester .BDDfy(); } + [Fact] + public void should_get_from_cache_with_different_query_string() + { + var qosOptions = new QoSOptionsBuilder() + .Build(); + + var reRoute = new DownstreamReRouteBuilder() + .WithQosOptions(qosOptions) + .WithHttpHandlerOptions(new HttpHandlerOptions(false, false, false, true)) + .WithLoadBalancerKey("") + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithOriginalValue("").Build()) + .WithQosOptions(new QoSOptionsBuilder().Build()) + .Build(); + + this.Given(x => GivenARealCache()) + .And(x => GivenTheFactoryReturns()) + .And(x => GivenARequest(reRoute, "http://wwww.someawesomewebsite.com/woot?badman=1")) + .And(x => WhenIBuildTheFirstTime()) + .And(x => WhenISave()) + .And(x => WhenIBuildAgain()) + .And(x => GivenARequest(reRoute, "http://wwww.someawesomewebsite.com/woot?badman=2")) + .And(x => WhenISave()) + .When(x => WhenIBuildAgain()) + .Then(x => ThenTheHttpClientIsFromTheCache()) + .BDDfy(); + } + + [Fact] + public void should_not_get_from_cache_with_different_query_string() + { + var qosOptions = new QoSOptionsBuilder() + .Build(); + + var reRouteA = new DownstreamReRouteBuilder() + .WithQosOptions(qosOptions) + .WithHttpHandlerOptions(new HttpHandlerOptions(false, false, false, true)) + .WithLoadBalancerKey("") + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithContainsQueryString(true).WithOriginalValue("").Build()) + .WithQosOptions(new QoSOptionsBuilder().Build()) + .Build(); + + var reRouteB = new DownstreamReRouteBuilder() + .WithQosOptions(qosOptions) + .WithHttpHandlerOptions(new HttpHandlerOptions(false, false, false, true)) + .WithLoadBalancerKey("") + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithContainsQueryString(true).WithOriginalValue("").Build()) + .WithQosOptions(new QoSOptionsBuilder().Build()) + .Build(); + + this.Given(x => GivenARealCache()) + .And(x => GivenTheFactoryReturns()) + .And(x => GivenARequest(reRouteA, "http://wwww.someawesomewebsite.com/woot?badman=1")) + .And(x => WhenIBuildTheFirstTime()) + .And(x => WhenISave()) + .And(x => WhenIBuildAgain()) + .And(x => GivenARequest(reRouteB, "http://wwww.someawesomewebsite.com/woot?badman=2")) + .And(x => WhenISave()) + .When(x => WhenIBuildAgain()) + .Then(x => ThenTheHttpClientIsNotFromTheCache()) + .BDDfy(); + } + [Fact] public void should_log_if_ignoring_ssl_errors() { @@ -99,6 +163,7 @@ namespace Ocelot.UnitTests.Requester .WithQosOptions(qosOptions) .WithHttpHandlerOptions(new HttpHandlerOptions(false, false, false, true)) .WithLoadBalancerKey("") + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithOriginalValue("").Build()) .WithQosOptions(new QoSOptionsBuilder().Build()) .WithDangerousAcceptAnyServerCertificateValidator(true) .Build(); @@ -121,6 +186,7 @@ namespace Ocelot.UnitTests.Requester .WithQosOptions(qosOptions) .WithHttpHandlerOptions(new HttpHandlerOptions(false, false, false, true)) .WithLoadBalancerKey("") + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithOriginalValue("").Build()) .WithQosOptions(new QoSOptionsBuilder().Build()) .Build(); @@ -152,6 +218,7 @@ namespace Ocelot.UnitTests.Requester .WithQosOptions(qosOptions) .WithHttpHandlerOptions(new HttpHandlerOptions(false, true, false, true)) .WithLoadBalancerKey("") + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithOriginalValue("").Build()) .WithQosOptions(new QoSOptionsBuilder().Build()) .Build(); @@ -176,9 +243,9 @@ namespace Ocelot.UnitTests.Requester [InlineData("PATCH")] public void should_add_verb_to_cache_key(string verb) { - var client = "http://localhost:5012"; + var downstreamUrl = "http://localhost:5012/"; - HttpMethod method = new HttpMethod(verb); + var method = new HttpMethod(verb); var qosOptions = new QoSOptionsBuilder() .Build(); @@ -187,14 +254,15 @@ namespace Ocelot.UnitTests.Requester .WithQosOptions(qosOptions) .WithHttpHandlerOptions(new HttpHandlerOptions(false, false, false, true)) .WithLoadBalancerKey("") + .WithUpstreamTemplatePattern(new UpstreamPathTemplateBuilder().WithOriginalValue("").Build()) .WithQosOptions(new QoSOptionsBuilder().Build()) .Build(); this.Given(_ => GivenADownstreamService()) - .And(_ => GivenARequestWithAUrlAndMethod(reRoute, client, method)) + .And(_ => GivenARequestWithAUrlAndMethod(reRoute, downstreamUrl, method)) .And(_ => GivenTheFactoryReturnsNothing()) .And(_ => WhenIBuild()) - .And(_ => GivenCacheIsCalledWithExpectedKey($"{method.ToString()}:{client}")) + .And(_ => GivenCacheIsCalledWithExpectedKey($"{method.ToString()}:{downstreamUrl}")) .BDDfy(); } @@ -209,6 +277,11 @@ namespace Ocelot.UnitTests.Requester _againHttpClient.ShouldBe(_firstHttpClient); } + private void ThenTheHttpClientIsNotFromTheCache() + { + _againHttpClient.ShouldNotBe(_firstHttpClient); + } + private void WhenISave() { _builder.Save(); @@ -216,17 +289,17 @@ namespace Ocelot.UnitTests.Requester private void GivenCacheIsCalledWithExpectedKey(string expectedKey) { - _cacheHandlers.Verify(x => x.Get(It.Is(p => p.Equals(expectedKey, StringComparison.OrdinalIgnoreCase))), Times.Once); + _cacheHandlers.Verify(x => x.Get(It.IsAny()), Times.Once); } private void ThenTheDangerousAcceptAnyServerCertificateValidatorWarningIsLogged() { - _logger.Verify(x => x.LogWarning($"You have ignored all SSL warnings by using DangerousAcceptAnyServerCertificateValidator for this DownstreamReRoute, UpstreamPathTemplate: {_context.DownstreamReRoute.UpstreamPathTemplate}, DownstreamPathTemplate: {_context.DownstreamReRoute.DownstreamPathTemplate}"), Times.Once); + _logger.Verify(x => x.LogWarning($"You have ignored all SSL warnings by using DangerousAcceptAnyServerCertificateValidator for this DownstreamReRoute, UpstreamPathTemplate: {_context.DownstreamReRoute.UpstreamPathTemplate}, DownstreamDownstreamPathTemplate: {_context.DownstreamReRoute.DownstreamDownstreamPathTemplate}"), Times.Once); } private void GivenTheClientIsCached() { - _cacheHandlers.Setup(x => x.Get(It.IsAny())).Returns(_httpClient); + _cacheHandlers.Setup(x => x.Get(It.IsAny())).Returns(_httpClient); } private void ThenTheCookieIsSet() @@ -287,7 +360,12 @@ namespace Ocelot.UnitTests.Requester private void GivenARequest(DownstreamReRoute downstream) { - GivenARequestWithAUrlAndMethod(downstream, "http://localhost:5003", HttpMethod.Get); + GivenARequest(downstream, "http://localhost:5003"); + } + + private void GivenARequest(DownstreamReRoute downstream, string downstreamUrl) + { + GivenARequestWithAUrlAndMethod(downstream, downstreamUrl, HttpMethod.Get); } private void GivenARequestWithAUrlAndMethod(DownstreamReRoute downstream, string url, HttpMethod method) diff --git a/test/Ocelot.UnitTests/Requester/HttpClientHttpRequesterTest.cs b/test/Ocelot.UnitTests/Requester/HttpClientHttpRequesterTest.cs index a6701035..7099b10f 100644 --- a/test/Ocelot.UnitTests/Requester/HttpClientHttpRequesterTest.cs +++ b/test/Ocelot.UnitTests/Requester/HttpClientHttpRequesterTest.cs @@ -50,6 +50,8 @@ namespace Ocelot.UnitTests.Requester [Fact] public void should_call_request_correctly() { + var upstreamTemplate = new UpstreamPathTemplateBuilder().WithOriginalValue("").Build(); + var qosOptions = new QoSOptionsBuilder() .Build(); @@ -57,6 +59,7 @@ namespace Ocelot.UnitTests.Requester .WithQosOptions(qosOptions) .WithHttpHandlerOptions(new HttpHandlerOptions(false, false, false, true)) .WithLoadBalancerKey("") + .WithUpstreamTemplatePattern(upstreamTemplate) .WithQosOptions(new QoSOptionsBuilder().Build()) .Build(); @@ -76,6 +79,8 @@ namespace Ocelot.UnitTests.Requester [Fact] public void should_call_request_unable_to_complete_request() { + var upstreamTemplate = new UpstreamPathTemplateBuilder().WithOriginalValue("").Build(); + var qosOptions = new QoSOptionsBuilder() .Build(); @@ -83,6 +88,7 @@ namespace Ocelot.UnitTests.Requester .WithQosOptions(qosOptions) .WithHttpHandlerOptions(new HttpHandlerOptions(false, false, false, true)) .WithLoadBalancerKey("") + .WithUpstreamTemplatePattern(upstreamTemplate) .WithQosOptions(new QoSOptionsBuilder().Build()) .Build(); @@ -101,6 +107,8 @@ namespace Ocelot.UnitTests.Requester [Fact] public void http_client_request_times_out() { + var upstreamTemplate = new UpstreamPathTemplateBuilder().WithOriginalValue("").Build(); + var qosOptions = new QoSOptionsBuilder() .Build(); @@ -108,6 +116,7 @@ namespace Ocelot.UnitTests.Requester .WithQosOptions(qosOptions) .WithHttpHandlerOptions(new HttpHandlerOptions(false, false, false, true)) .WithLoadBalancerKey("") + .WithUpstreamTemplatePattern(upstreamTemplate) .WithQosOptions(new QoSOptionsBuilder().WithTimeoutValue(1).Build()) .Build(); @@ -132,7 +141,7 @@ namespace Ocelot.UnitTests.Requester private void WhenIGetResponse() { - _response = _httpClientRequester.GetResponse(_request).Result; + _response = _httpClientRequester.GetResponse(_request).GetAwaiter().GetResult(); } private void ThenTheResponseIsCalledCorrectly()