sup*_*jos 12 integration-testing asp.net-core asp.net-core-webapi
我有一个C#Asp.Net Core(1.x)项目,实现了一个Web REST API及其相关的集成测试项目,在任何测试之前有一个类似于以下的设置:
// ...
IWebHostBuilder webHostBuilder = GetWebHostBuilderSimilarToRealOne()
.UseStartup<MyTestStartup>();
TestServer server = new TestServer(webHostBuilder);
server.BaseAddress = new Uri("http://localhost:5000");
HttpClient client = server.CreateClient();
// ...
Run Code Online (Sandbox Code Playgroud)
在测试期间,client它用于向Web API(被测系统)发送HTTP请求并检索响应.
在实际测试的系统中,有一些组件从每个请求中提取发送方IP地址,如下所示:
HttpContext httpContext = ReceiveHttpContextDuringAuthentication();
// edge cases omitted for brevity
string remoteIpAddress = httpContext?.Connection?.RemoteIpAddress?.ToString()
Run Code Online (Sandbox Code Playgroud)
现在在集成测试期间,这段代码无法找到IP地址,因为RemoteIpAddress它总是为空.
有没有办法将其设置为测试代码中的某个已知值?我在这里搜索了SO,但找不到类似的东西.TA
Pav*_*kov 13
您可以编写中间件来设置自定义IP地址,因为此属性是可写的:
public class FakeRemoteIpAddressMiddleware
{
private readonly RequestDelegate next;
private readonly IPAddress fakeIpAddress = IPAddress.Parse("127.168.1.32");
public FakeRemoteIpAddressMiddleware(RequestDelegate next)
{
this.next = next;
}
public async Task Invoke(HttpContext httpContext)
{
httpContext.Connection.RemoteIpAddress = fakeIpAddress;
await this.next(httpContext);
}
}
Run Code Online (Sandbox Code Playgroud)
然后你可以创建这样的StartupStub类:
public class StartupStub : Startup
{
public StartupStub(IConfiguration configuration) : base(configuration)
{
}
public override void Configure(IApplicationBuilder app, IHostingEnvironment env)
{
app.UseMiddleware<FakeRemoteIpAddressMiddleware>();
base.Configure(app, env);
}
}
Run Code Online (Sandbox Code Playgroud)
并用它来创建一个TestServer:
new TestServer(new WebHostBuilder().UseStartup<StartupStub>());
Run Code Online (Sandbox Code Playgroud)
按照ASP.NET Core中的此答案,是否可以通过Program.cs设置中间件?
还可以从ConfigureServices配置中间件,该中间件使您无需StartupStub类即可创建自定义WebApplicationFactory:
public class CustomWebApplicationFactory : WebApplicationFactory<Startup>
{
protected override IWebHostBuilder CreateWebHostBuilder()
{
return WebHost
.CreateDefaultBuilder<Startup>(new string[0])
.ConfigureServices(services =>
{
services.AddSingleton<IStartupFilter, CustomStartupFilter>();
});
}
}
public class CustomStartupFilter : IStartupFilter
{
public Action<IApplicationBuilder> Configure(Action<IApplicationBuilder> next)
{
return app =>
{
app.UseMiddleware<FakeRemoteIpAddressMiddleware>();
next(app);
};
}
}
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
1577 次 |
| 最近记录: |