mirror of
https://github.com/nsnail/Ocelot.git
synced 2025-06-19 04:38:14 +08:00
first passing proxy acceptnace test yeyyy!
This commit is contained in:
@ -0,0 +1,16 @@
|
||||
using System.Collections.Generic;
|
||||
using Ocelot.Library.Infrastructure.UrlMatcher;
|
||||
|
||||
namespace Ocelot.Library.Infrastructure.DownstreamRouteFinder
|
||||
{
|
||||
public class DownstreamRoute
|
||||
{
|
||||
public DownstreamRoute(List<TemplateVariableNameAndValue> templateVariableNameAndValues, string downstreamUrlTemplate)
|
||||
{
|
||||
TemplateVariableNameAndValues = templateVariableNameAndValues;
|
||||
DownstreamUrlTemplate = downstreamUrlTemplate;
|
||||
}
|
||||
public List<TemplateVariableNameAndValue> TemplateVariableNameAndValues { get; private set; }
|
||||
public string DownstreamUrlTemplate { get; private set; }
|
||||
}
|
||||
}
|
@ -0,0 +1,38 @@
|
||||
using System.Collections.Generic;
|
||||
using Microsoft.Extensions.Options;
|
||||
using Ocelot.Library.Infrastructure.Responses;
|
||||
using Ocelot.Library.Infrastructure.UrlMatcher;
|
||||
|
||||
namespace Ocelot.Library.Infrastructure.DownstreamRouteFinder
|
||||
{
|
||||
public class DownstreamRouteFinder : IDownstreamRouteFinder
|
||||
{
|
||||
private readonly IOptions<Configuration.Configuration> _configuration;
|
||||
private readonly IUrlPathToUrlTemplateMatcher _urlMatcher;
|
||||
|
||||
public DownstreamRouteFinder(IOptions<Configuration.Configuration> configuration, IUrlPathToUrlTemplateMatcher urlMatcher)
|
||||
{
|
||||
_configuration = configuration;
|
||||
_urlMatcher = urlMatcher;
|
||||
}
|
||||
|
||||
public Response<DownstreamRoute> FindDownstreamRoute(string upstreamUrlPath)
|
||||
{
|
||||
|
||||
foreach (var template in _configuration.Value.ReRoutes)
|
||||
{
|
||||
var urlMatch = _urlMatcher.Match(upstreamUrlPath, template.UpstreamTemplate);
|
||||
|
||||
if (urlMatch.Match)
|
||||
{
|
||||
return new OkResponse<DownstreamRoute>(new DownstreamRoute(urlMatch.TemplateVariableNameAndValues, template.DownstreamTemplate));
|
||||
}
|
||||
}
|
||||
|
||||
return new ErrorResponse<DownstreamRoute>(new List<Error>
|
||||
{
|
||||
new UnableToFindDownstreamRouteError()
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
@ -0,0 +1,9 @@
|
||||
using Ocelot.Library.Infrastructure.Responses;
|
||||
|
||||
namespace Ocelot.Library.Infrastructure.DownstreamRouteFinder
|
||||
{
|
||||
public interface IDownstreamRouteFinder
|
||||
{
|
||||
Response<DownstreamRoute> FindDownstreamRoute(string upstreamUrlPath);
|
||||
}
|
||||
}
|
@ -0,0 +1,15 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Threading.Tasks;
|
||||
using Ocelot.Library.Infrastructure.Responses;
|
||||
|
||||
namespace Ocelot.Library.Infrastructure.DownstreamRouteFinder
|
||||
{
|
||||
public class UnableToFindDownstreamRouteError : Error
|
||||
{
|
||||
public UnableToFindDownstreamRouteError() : base("UnableToFindDownstreamRouteError")
|
||||
{
|
||||
}
|
||||
}
|
||||
}
|
@ -1,17 +1,17 @@
|
||||
using System.Text;
|
||||
using Ocelot.Library.Infrastructure.UrlMatcher;
|
||||
using Ocelot.Library.Infrastructure.DownstreamRouteFinder;
|
||||
|
||||
namespace Ocelot.Library.Infrastructure.UrlTemplateReplacer
|
||||
{
|
||||
public class DownstreamUrlTemplateVariableReplacer : IDownstreamUrlTemplateVariableReplacer
|
||||
{
|
||||
public string ReplaceTemplateVariable(UrlMatch urlMatch)
|
||||
public string ReplaceTemplateVariable(DownstreamRoute downstreamRoute)
|
||||
{
|
||||
var upstreamUrl = new StringBuilder();
|
||||
|
||||
upstreamUrl.Append(urlMatch.DownstreamUrlTemplate);
|
||||
upstreamUrl.Append(downstreamRoute.DownstreamUrlTemplate);
|
||||
|
||||
foreach (var templateVarAndValue in urlMatch.TemplateVariableNameAndValues)
|
||||
foreach (var templateVarAndValue in downstreamRoute.TemplateVariableNameAndValues)
|
||||
{
|
||||
upstreamUrl.Replace(templateVarAndValue.TemplateVariableName, templateVarAndValue.TemplateVariableValue);
|
||||
}
|
||||
|
@ -1,9 +1,10 @@
|
||||
using Ocelot.Library.Infrastructure.DownstreamRouteFinder;
|
||||
using Ocelot.Library.Infrastructure.UrlMatcher;
|
||||
|
||||
namespace Ocelot.Library.Infrastructure.UrlTemplateReplacer
|
||||
{
|
||||
public interface IDownstreamUrlTemplateVariableReplacer
|
||||
{
|
||||
string ReplaceTemplateVariable(UrlMatch urlMatch);
|
||||
string ReplaceTemplateVariable(DownstreamRoute downstreamRoute);
|
||||
}
|
||||
}
|
@ -1,56 +1,62 @@
|
||||
using System.Net;
|
||||
using System.Net.Http;
|
||||
using System.Threading.Tasks;
|
||||
using Microsoft.AspNetCore.Http;
|
||||
using Ocelot.Library.Infrastructure.UrlMatcher;
|
||||
using Microsoft.Extensions.Options;
|
||||
using Ocelot.Library.Infrastructure.Configuration;
|
||||
using Ocelot.Library.Infrastructure.DownstreamRouteFinder;
|
||||
using Ocelot.Library.Infrastructure.UrlTemplateReplacer;
|
||||
|
||||
namespace Ocelot.Library.Middleware
|
||||
{
|
||||
using System.Net;
|
||||
using Infrastructure.Configuration;
|
||||
using Microsoft.Extensions.Options;
|
||||
|
||||
public class ProxyMiddleware
|
||||
{
|
||||
private readonly RequestDelegate _next;
|
||||
private readonly IUrlPathToUrlTemplateMatcher _urlMatcher;
|
||||
private readonly IDownstreamUrlTemplateVariableReplacer _urlReplacer;
|
||||
private readonly IOptions<Configuration> _configuration;
|
||||
private readonly IDownstreamRouteFinder _downstreamRouteFinder;
|
||||
|
||||
public ProxyMiddleware(RequestDelegate next,
|
||||
IUrlPathToUrlTemplateMatcher urlMatcher,
|
||||
IDownstreamUrlTemplateVariableReplacer urlReplacer, IOptions<Configuration> configuration)
|
||||
IDownstreamUrlTemplateVariableReplacer urlReplacer,
|
||||
IOptions<Configuration> configuration,
|
||||
IDownstreamRouteFinder downstreamRouteFinder)
|
||||
{
|
||||
_next = next;
|
||||
_urlMatcher = urlMatcher;
|
||||
_urlReplacer = urlReplacer;
|
||||
_configuration = configuration;
|
||||
_downstreamRouteFinder = downstreamRouteFinder;
|
||||
}
|
||||
|
||||
public async Task Invoke(HttpContext context)
|
||||
{
|
||||
var upstreamUrlPath = context.Request.Path.ToString();
|
||||
|
||||
UrlMatch urlMatch = null;
|
||||
var downstreamRoute = _downstreamRouteFinder.FindDownstreamRoute(upstreamUrlPath);
|
||||
|
||||
foreach (var template in _configuration.Value.ReRoutes)
|
||||
{
|
||||
urlMatch = _urlMatcher.Match(upstreamUrlPath, template.UpstreamTemplate);
|
||||
|
||||
if (urlMatch.Match)
|
||||
{
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (urlMatch == null || !urlMatch.Match)
|
||||
if (downstreamRoute.IsError)
|
||||
{
|
||||
context.Response.StatusCode = (int)HttpStatusCode.NotFound;
|
||||
return;
|
||||
}
|
||||
|
||||
var downstreamUrl = _urlReplacer.ReplaceTemplateVariable(urlMatch);
|
||||
|
||||
var downstreamUrl = _urlReplacer.ReplaceTemplateVariable(downstreamRoute.Data);
|
||||
|
||||
//make a http request to this endpoint...maybe bring in a library
|
||||
using (var httpClient = new HttpClient())
|
||||
{
|
||||
var httpMethod = new HttpMethod(context.Request.Method);
|
||||
|
||||
var httpRequestMessage = new HttpRequestMessage(httpMethod, downstreamUrl);
|
||||
|
||||
var response = await httpClient.SendAsync(httpRequestMessage);
|
||||
|
||||
if (!response.IsSuccessStatusCode)
|
||||
{
|
||||
context.Response.StatusCode = (int)response.StatusCode;
|
||||
return;
|
||||
}
|
||||
await context.Response.WriteAsync(await response.Content.ReadAsStringAsync());
|
||||
}
|
||||
|
||||
await _next.Invoke(context);
|
||||
}
|
||||
|
@ -3,6 +3,7 @@ using Microsoft.AspNetCore.Hosting;
|
||||
using Microsoft.Extensions.Configuration;
|
||||
using Microsoft.Extensions.DependencyInjection;
|
||||
using Microsoft.Extensions.Logging;
|
||||
using Ocelot.Library.Infrastructure.DownstreamRouteFinder;
|
||||
using Ocelot.Library.Middleware;
|
||||
|
||||
namespace Ocelot
|
||||
@ -36,6 +37,7 @@ namespace Ocelot
|
||||
// Add framework services.
|
||||
services.AddSingleton<IUrlPathToUrlTemplateMatcher, UrlPathToUrlTemplateMatcher>();
|
||||
services.AddSingleton<IDownstreamUrlTemplateVariableReplacer, DownstreamUrlTemplateVariableReplacer>();
|
||||
services.AddSingleton<IDownstreamRouteFinder, DownstreamRouteFinder>();
|
||||
}
|
||||
|
||||
// This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
|
||||
|
Reference in New Issue
Block a user