设置响应 ContentType 的中间件
Middleware to set response ContentType
在我们的 ASP.NET 基于核心的 Web 应用程序中,我们需要以下内容:某些请求的文件类型应该获得自定义 ContentType 作为响应。例如。 .map
应映射到 application/json
。在 "full" ASP.NET 4.x 中并结合 IIS 可以使用 web.config <staticContent>/<mimeMap>
为此,我想用自定义 ASP.NET核心中间件。
所以我尝试了以下方法(为简洁起见进行了简化):
public async Task Invoke(HttpContext context)
{
await nextMiddleware.Invoke(context);
if (context.Response.StatusCode == (int)HttpStatusCode.OK)
{
if (context.Request.Path.Value.EndsWith(".map"))
{
context.Response.ContentType = "application/json";
}
}
}
不幸的是,在调用中间件链的其余部分后尝试设置 context.Response.ContentType
会导致以下异常:
System.InvalidOperationException: "Headers are read-only, response has already started."
如何创建满足此要求的中间件?
尝试使用HttpContext.Response.OnStarting
回调。这是发送 headers 之前触发的最后一个事件。
public async Task Invoke(HttpContext context)
{
context.Response.OnStarting((state) =>
{
if (context.Response.StatusCode == (int)HttpStatusCode.OK)
{
if (context.Request.Path.Value.EndsWith(".map"))
{
context.Response.ContentType = "application/json";
}
}
return Task.FromResult(0);
}, null);
await nextMiddleware.Invoke(context);
}
使用 OnStarting 方法的重载:
public async Task Invoke(HttpContext context)
{
context.Response.OnStarting(() =>
{
if (context.Response.StatusCode == (int) HttpStatusCode.OK &&
context.Request.Path.Value.EndsWith(".map"))
{
context.Response.ContentType = "application/json";
}
return Task.CompletedTask;
});
await nextMiddleware.Invoke(context);
}
在我们的 ASP.NET 基于核心的 Web 应用程序中,我们需要以下内容:某些请求的文件类型应该获得自定义 ContentType 作为响应。例如。 .map
应映射到 application/json
。在 "full" ASP.NET 4.x 中并结合 IIS 可以使用 web.config <staticContent>/<mimeMap>
为此,我想用自定义 ASP.NET核心中间件。
所以我尝试了以下方法(为简洁起见进行了简化):
public async Task Invoke(HttpContext context)
{
await nextMiddleware.Invoke(context);
if (context.Response.StatusCode == (int)HttpStatusCode.OK)
{
if (context.Request.Path.Value.EndsWith(".map"))
{
context.Response.ContentType = "application/json";
}
}
}
不幸的是,在调用中间件链的其余部分后尝试设置 context.Response.ContentType
会导致以下异常:
System.InvalidOperationException: "Headers are read-only, response has already started."
如何创建满足此要求的中间件?
尝试使用HttpContext.Response.OnStarting
回调。这是发送 headers 之前触发的最后一个事件。
public async Task Invoke(HttpContext context)
{
context.Response.OnStarting((state) =>
{
if (context.Response.StatusCode == (int)HttpStatusCode.OK)
{
if (context.Request.Path.Value.EndsWith(".map"))
{
context.Response.ContentType = "application/json";
}
}
return Task.FromResult(0);
}, null);
await nextMiddleware.Invoke(context);
}
使用 OnStarting 方法的重载:
public async Task Invoke(HttpContext context)
{
context.Response.OnStarting(() =>
{
if (context.Response.StatusCode == (int) HttpStatusCode.OK &&
context.Request.Path.Value.EndsWith(".map"))
{
context.Response.ContentType = "application/json";
}
return Task.CompletedTask;
});
await nextMiddleware.Invoke(context);
}