我正在制作一个位于ASP.Net WebAPI之上的SPA。我等待使用HTML5历史记录而不是#/
进行历史记录路由,但这会导致深层链接出现问题,我需要确保/
和/foo/bar
都返回相同的HTML文件(我的JS将呈现SPA的正确部分)。
如何让OWIN / Katana为多个不同的网址返回相同的HTML文件?
答案 0 :(得分:23)
为了简单起见,同时仍保留StaticFiles中间件的所有缓存优势等,我只是使用内联中间件重写请求路径,如下所示
public class Startup
{
public void Configuration(IAppBuilder app)
{
app.Map("/app", spa =>
{
spa.Use((context, next) =>
{
context.Request.Path = new PathString("/index.html");
return next();
});
spa.UseStaticFiles();
});
app.UseWelcomePage();
}
}
这将提供除/app/*
以外的任何内容的欢迎页面,该页面将始终为index.html提供服务。
答案 1 :(得分:0)
我在使用Angular js时遇到了类似的问题,并使用了稍微不同的方法来解决问题。
我们使用Owin将路线映射到SPA的入口点(index.html)。这允许您访问SPA并导航到不同的页面。但是,如果您刷新了页面,那么您将获得404.基本上,AngularJS的路由和Owin / Katana的路由都是踩到彼此的脚趾。
我通过创建自定义DelegatingHandler解决了这个问题。只要Owin / Katana无法找到与请求匹配的路线,就会使用此委托处理程序(404)。
public class CustomDelegatingHandler : DelegatingHandler
{
protected override Task<HttpResponseMessage> SendAsync(HttpRequestMessage request, CancellationToken cancellationToken)
{
Task<HttpResponseMessage> response = base.SendAsync(request, cancellationToken);
if (response.Result.StatusCode == HttpStatusCode.NotFound)
{
response.Result.Content = new StringContent(File.ReadAllText(@"index.html"));
response.Result.Content.Headers.ContentType = new MediaTypeHeaderValue("text/html");
response.Result.StatusCode = HttpStatusCode.OK;
}
return response;
}
}
当我们无法找到与请求匹配的网页时,上面的代码段会返回SPA的入口点index.html。
要使用此委托处理程序,必须在启动Owin主机时将以下行添加到HttpConfiguration():
var httpConfig = new HttpConfiguration();
httpConfig.MessageHandlers.Add(new CustomDelegatingHandler());
简而言之,我有一个映射到SPA的默认路由,任何无法识别的路由都将通过DelegatingHandler并提供相同的SPA。我们不修改Request.Path,允许SPA将请求路由到正确的页面。