Skip to content

Commit

Permalink
Support placeholder in service fabric services names (ThreeMammals#722)
Browse files Browse the repository at this point in the history
  • Loading branch information
FelixBoers authored and philproctor committed Jan 11, 2019
1 parent 7ba6d30 commit 6495891
Show file tree
Hide file tree
Showing 6 changed files with 90 additions and 12 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ public DownstreamUrlCreatorMiddleware(OcelotRequestDelegate next,
public async Task Invoke(DownstreamContext context)
{
var response = _replacer
.Replace(context.DownstreamReRoute.DownstreamPathTemplate, context.TemplatePlaceholderNameAndValues);
.Replace(context.DownstreamReRoute.DownstreamPathTemplate.Value, context.TemplatePlaceholderNameAndValues);

if (response.IsError)
{
Expand Down Expand Up @@ -103,7 +103,7 @@ private string GetPath(DownstreamPath dsPath)
return dsPath.Value.Substring(0, dsPath.Value.IndexOf("?", StringComparison.Ordinal));
}

private string GetQueryString(DownstreamPath dsPath)
private string GetQueryString(DownstreamPath dsPath)
{
return dsPath.Value.Substring(dsPath.Value.IndexOf("?", StringComparison.Ordinal));
}
Expand All @@ -116,8 +116,9 @@ private bool ContainsQueryString(DownstreamPath dsPath)
private (string path, string query) CreateServiceFabricUri(DownstreamContext context, Response<DownstreamPath> dsPath)
{
var query = context.DownstreamRequest.Query;
var serviceFabricPath = $"/{context.DownstreamReRoute.ServiceName + dsPath.Data.Value}";
return (serviceFabricPath, query);
var serviceName = _replacer.Replace(context.DownstreamReRoute.ServiceName, context.TemplatePlaceholderNameAndValues);
var pathTemplate = $"/{serviceName.Data.Value}{dsPath.Data.Value}";
return (pathTemplate, query);
}

private static bool ServiceFabricRequest(DownstreamContext context)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,11 +8,12 @@ namespace Ocelot.DownstreamUrlCreator.UrlTemplateReplacer
{
public class DownstreamTemplatePathPlaceholderReplacer : IDownstreamPathPlaceholderReplacer
{
public Response<DownstreamPath> Replace(DownstreamPathTemplate downstreamPathTemplate, List<PlaceholderNameAndValue> urlPathPlaceholderNameAndValues)
public Response<DownstreamPath> Replace(string downstreamPathTemplate,
List<PlaceholderNameAndValue> urlPathPlaceholderNameAndValues)
{
var downstreamPath = new StringBuilder();

downstreamPath.Append(downstreamPathTemplate.Value);
downstreamPath.Append(downstreamPathTemplate);

foreach (var placeholderVariableAndValue in urlPathPlaceholderNameAndValues)
{
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,6 @@ namespace Ocelot.DownstreamUrlCreator.UrlTemplateReplacer
{
public interface IDownstreamPathPlaceholderReplacer
{
Response<DownstreamPath> Replace(DownstreamPathTemplate downstreamPathTemplate, List<PlaceholderNameAndValue> urlPathPlaceholderNameAndValues);
Response<DownstreamPath> Replace(string downstreamPathTemplate, List<PlaceholderNameAndValue> urlPathPlaceholderNameAndValues);
}
}
36 changes: 36 additions & 0 deletions test/Ocelot.AcceptanceTests/ServiceFabricTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -128,6 +128,42 @@ public void should_support_service_fabric_naming_and_dns_service_statefull_and_a
.BDDfy();
}

[Fact]
public void should_support_placeholder_in_service_fabric_service_name()
{
var configuration = new FileConfiguration
{
ReRoutes = new List<FileReRoute>
{
new FileReRoute
{
DownstreamPathTemplate = "/values",
DownstreamScheme = "http",
UpstreamPathTemplate = "/api/{version}/values",
UpstreamHttpMethod = new List<string> { "Get" },
ServiceName = "Service_{version}/Api"
}
},
GlobalConfiguration = new FileGlobalConfiguration
{
ServiceDiscoveryProvider = new FileServiceDiscoveryProvider()
{
Host = "localhost",
Port = 19081,
Type = "ServiceFabric"
}
}
};

this.Given(x => x.GivenThereIsAServiceRunningOn("http://localhost:19081", "/Service_1.0/Api/values", 200, "Hello from Laura", "test=best"))
.And(x => _steps.GivenThereIsAConfiguration(configuration))
.And(x => _steps.GivenOcelotIsRunning())
.When(x => _steps.WhenIGetUrlOnTheApiGateway("/api/1.0/values?test=best"))
.Then(x => _steps.ThenTheStatusCodeShouldBe(HttpStatusCode.OK))
.And(x => _steps.ThenTheResponseBodyShouldBe("Hello from Laura"))
.BDDfy();
}

private void GivenThereIsAServiceRunningOn(string baseUrl, string basePath, int statusCode, string responseBody, string expectedQueryString)
{
_serviceHandler.GivenThereIsAServiceRunningOn(baseUrl, basePath, async context =>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -223,7 +223,7 @@ public void should_create_service_fabric_url()
this.Given(x => x.GivenTheDownStreamRouteIs(downstreamRoute))
.And(x => GivenTheServiceProviderConfigIs(config))
.And(x => x.GivenTheDownstreamRequestUriIs("http://localhost:19081"))
.And(x => x.GivenTheUrlReplacerWillReturn("/api/products/1"))
.And(x => x.GivenTheUrlReplacerWillReturnSequence("/api/products/1", "Ocelot/OcelotApp"))
.When(x => x.WhenICallTheMiddleware())
.Then(x => x.ThenTheDownstreamRequestUriIs("http://localhost:19081/Ocelot/OcelotApp/api/products/1"))
.BDDfy();
Expand Down Expand Up @@ -253,7 +253,7 @@ public void should_create_service_fabric_url_with_query_string_for_stateless_ser
this.Given(x => x.GivenTheDownStreamRouteIs(downstreamRoute))
.And(x => GivenTheServiceProviderConfigIs(config))
.And(x => x.GivenTheDownstreamRequestUriIs("http://localhost:19081?Tom=test&laura=1"))
.And(x => x.GivenTheUrlReplacerWillReturn("/api/products/1"))
.And(x => x.GivenTheUrlReplacerWillReturnSequence("/api/products/1", "Ocelot/OcelotApp"))
.When(x => x.WhenICallTheMiddleware())
.Then(x => x.ThenTheDownstreamRequestUriIs("http://localhost:19081/Ocelot/OcelotApp/api/products/1?Tom=test&laura=1"))
.BDDfy();
Expand Down Expand Up @@ -283,12 +283,40 @@ public void should_create_service_fabric_url_with_query_string_for_stateful_serv
this.Given(x => x.GivenTheDownStreamRouteIs(downstreamRoute))
.And(x => GivenTheServiceProviderConfigIs(config))
.And(x => x.GivenTheDownstreamRequestUriIs("http://localhost:19081?PartitionKind=test&PartitionKey=1"))
.And(x => x.GivenTheUrlReplacerWillReturn("/api/products/1"))
.And(x => x.GivenTheUrlReplacerWillReturnSequence("/api/products/1", "Ocelot/OcelotApp"))
.When(x => x.WhenICallTheMiddleware())
.Then(x => x.ThenTheDownstreamRequestUriIs("http://localhost:19081/Ocelot/OcelotApp/api/products/1?PartitionKind=test&PartitionKey=1"))
.BDDfy();
}

[Fact]
public void should_create_service_fabric_url_with_version_from_upstream_path_template()
{
var downstreamRoute = new DownstreamRoute(
new List<PlaceholderNameAndValue>(),
new ReRouteBuilder().WithDownstreamReRoute(
new DownstreamReRouteBuilder()
.WithDownstreamScheme("http")
.WithUpstreamPathTemplate(new UpstreamPathTemplateBuilder().WithOriginalValue("/products").Build())
.WithUseServiceDiscovery(true)
.Build()
).Build());

var config = new ServiceProviderConfigurationBuilder()
.WithType("ServiceFabric")
.WithHost("localhost")
.WithPort(19081)
.Build();

this.Given(x => x.GivenTheDownStreamRouteIs(downstreamRoute))
.And(x => GivenTheServiceProviderConfigIs(config))
.And(x => x.GivenTheDownstreamRequestUriIs("http://localhost:19081?PartitionKind=test&PartitionKey=1"))
.And(x => x.GivenTheUrlReplacerWillReturnSequence("/products", "Service_1.0/Api"))
.When(x => x.WhenICallTheMiddleware())
.Then(x => x.ThenTheDownstreamRequestUriIs("http://localhost:19081/Service_1.0/Api/products?PartitionKind=test&PartitionKey=1"))
.BDDfy();
}

[Fact]
public void issue_473_should_not_remove_additional_query_string()
{
Expand Down Expand Up @@ -322,6 +350,8 @@ public void issue_473_should_not_remove_additional_query_string()
.BDDfy();
}



private void GivenTheServiceProviderConfigIs(ServiceProviderConfiguration config)
{
var configuration = new InternalConfiguration(null, null, config, null, null, null, null, null);
Expand All @@ -346,11 +376,21 @@ private void GivenTheDownstreamRequestUriIs(string uri)
_downstreamContext.DownstreamRequest = new DownstreamRequest(_request);
}

private void GivenTheUrlReplacerWillReturnSequence(params string[] paths)
{
var setup = _downstreamUrlTemplateVariableReplacer
.SetupSequence(x => x.Replace(It.IsAny<string>(), It.IsAny<List<PlaceholderNameAndValue>>()));
foreach (var path in paths)
{
var response = new OkResponse<DownstreamPath>(new DownstreamPath(path));
setup.Returns(response);
}
}
private void GivenTheUrlReplacerWillReturn(string path)
{
_downstreamPath = new OkResponse<DownstreamPath>(new DownstreamPath(path));
_downstreamUrlTemplateVariableReplacer
.Setup(x => x.Replace(It.IsAny<DownstreamPathTemplate>(), It.IsAny<List<PlaceholderNameAndValue>>()))
.Setup(x => x.Replace(It.IsAny<string>(), It.IsAny<List<PlaceholderNameAndValue>>()))
.Returns(_downstreamPath);
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -199,7 +199,7 @@ private void GivenThereIsAUrlMatch(DownstreamRoute downstreamRoute)

private void WhenIReplaceTheTemplateVariables()
{
_result = _downstreamPathReplacer.Replace(_downstreamRoute.ReRoute.DownstreamReRoute[0].DownstreamPathTemplate, _downstreamRoute.TemplatePlaceholderNameAndValues);
_result = _downstreamPathReplacer.Replace(_downstreamRoute.ReRoute.DownstreamReRoute[0].DownstreamPathTemplate.Value, _downstreamRoute.TemplatePlaceholderNameAndValues);
}

private void ThenTheDownstreamUrlPathIsReturned(string expected)
Expand Down

0 comments on commit 6495891

Please sign in to comment.