繁体   English   中英

UseStatusCodePagesWithReExecute 显示空白页

[英]UseStatusCodePagesWithReExecute shows blank page

我一直在尝试使用UseStatusCodePagesWithReExecute方法来显示一个页面,该页面根据我尝试使用 ASP.NET Core 3.0 创建的应用程序上的状态代码显示自定义消息

我已按照此网站上的说明进行操作,但是现在,如果我尝试通过访问一个不存在的网页来对此进行测试,则会显示一个空白页面,并且代码不会通过 Razor 页面上的OnGet方法我想要显示(我使用了断点)。

但是,我可以通过使用/Status/404 URI 手动访问浏览器上的页面来显示状态页面。

在启动文件中,我添加了所需的行,如教程中所示。

// Startup.cs
public static void Configure(IApplicationBuilder app,
                             IWebHostEnvironment env,
                             IHostApplicationLifetime appLifetime)
    {
        app.UseDeveloperExceptionPage();
        app.UseStatusCodePagesWithReExecute("/Status/{0}");
        app.UseExceptionHandler("/Status");

        // Irrelevant code below        
    }

状态模型包含一个OnGet方法,该方法将代码编号作为参数

// Status.cshtml.cs

[ResponseCache(Duration = 0, Location = ResponseCacheLocation.None, NoStore = true)]
public class StatusModel : PageModel
{
    public void OnGet(string? code = null)
    {
        if (null == code)
            code = HttpContext.Response.StatusCode.ToString();

        PageTitle = $"HTTP status {code}";
        StatusNumber = code;

        if (code.CompareTo("404") == 0)
        {
            StatusName = "Not found";
            StatusDescription = "The requested page was not found.";
        }
        else
        {
            StatusName = "Unknown error";
            StatusDescription = "An unknown error occurred.";
        }
    }
}

状态视图非常简单:

@page "{code?}"
@model StatusModel
@{
}

<!DOCTYPE html>
<html>
<head>
    <meta name="viewport" content="width=device-width" />
    <title>@Model.PageTitle</title>
</head>
<body>
    <div>
        <h1>@Model.StatusNumber</h1>
        <h2>@Model.StatusName</h2>
        <h2>@Model.StatusDescription</h2>
    </div>
    <p>RID: @Model.RequestId</p>
</body>
</html>

在输出控制台上,我可以看到应用程序确实注意到它捕获了 404,但它似乎没有做任何事情:

info: Microsoft.AspNetCore.Mvc.StatusCodeResult[1]
      Executing HttpStatusCodeResult, setting HTTP status code 404
info: Microsoft.AspNetCore.Mvc.RazorPages.Infrastructure.PageActionInvoker[4]
      Executed page /Index in 225.4469ms
info: Microsoft.AspNetCore.Routing.EndpointMiddleware[1]
      Executed endpoint '/Index'

从 ASP.NET Core 2.2 传递到 3.0 时,我忘记编辑/添加以使其工作时是否发生了变化,或者这是否已经可以工作?

从 ASP.NET Core 2.2 传递到 3.0 时,我忘记编辑/添加以使其工作时是否发生了变化,或者这是否已经可以工作?

这应该已经可以工作了。

状态.cshtml:

@page "{code?}"
@model StatusModel
@{
}

<!DOCTYPE html>
<html>
<head>
    <meta name="viewport" content="width=device-width" />
    <title>@Model.PageTitle</title>
</head>
<body>
    <div>
        <h1>@Model.StatusNumber</h1>
        <h2>@Model.StatusName</h2>
        <h2>@Model.StatusDescription</h2>
    </div>
</body>
</html>

状态.cshtml.cs:

[ResponseCache(Duration = 0, Location = ResponseCacheLocation.None, NoStore = true)]
public class StatusModel : PageModel
{
    public string PageTitle { get;  set; }
    public string StatusNumber { get;  set; }
    public string StatusName { get;  set; }
    public string StatusDescription { get;  set; }

    public void OnGet(string? code = null)
    {
        if (null == code)
            code = HttpContext.Response.StatusCode.ToString();

        PageTitle = $"HTTP status {code}";
        StatusNumber = code;

        if (code.CompareTo("404") == 0)
        {
            StatusName = "Not found";
            StatusDescription = "The requested page was not found.";
        }
        else
        {
            StatusName = "Unknown error";
            StatusDescription = "An unknown error occurred.";
        }
    }
}

结果: 在此处输入图片说明

更新:

public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
{
    if (env.IsDevelopment())
    {
        app.UseDeveloperExceptionPage();
        app.UseStatusCodePagesWithReExecute("/Status/{0}");
        app.UseExceptionHandler("/Status");
    }
    else
    {
        app.UseDeveloperExceptionPage();
        app.UseStatusCodePagesWithReExecute("/Status/{0}");
        app.UseExceptionHandler("/Status");
        // The default HSTS value is 30 days. You may want to change this for production scenarios, see https://aka.ms/aspnetcore-hsts.
        app.UseHsts();
    }
    app.Use(async (context, next) =>
    {
        await next();

        if (context.Response.StatusCode == 401)
        {

            var newPath = new PathString("/Status/401");
            var originalPath = context.Request.Path;
            var originalQueryString = context.Request.QueryString;
            context.Features.Set<IStatusCodeReExecuteFeature>(new StatusCodeReExecuteFeature()
            {
                OriginalPathBase = context.Request.PathBase.Value,
                OriginalPath = originalPath.Value,
                OriginalQueryString = originalQueryString.HasValue ? originalQueryString.Value : null,
            });

            // An endpoint may have already been set. Since we're going to re-invoke the middleware pipeline we need to reset
            // the endpoint and route values to ensure things are re-calculated.
            context.SetEndpoint(endpoint: null);
            var routeValuesFeature = context.Features.Get<IRouteValuesFeature>();
            routeValuesFeature?.RouteValues?.Clear();

            context.Request.Path = newPath;
            try
            {
                await next();
            }
            finally
            {
                context.Request.QueryString = originalQueryString;
                context.Request.Path = originalPath;
                context.Features.Set<IStatusCodeReExecuteFeature>(null);
            }

            // which policy failed? need to inform consumer which requirement was not met
            //await next();
        }

    });
    app.UseHttpsRedirection();
    app.UseStaticFiles();

    app.UseRouting();

    app.UseAuthorization();

    app.UseEndpoints(endpoints =>
    {
        endpoints.MapRazorPages();
    });
}

结果: 在此处输入图片说明

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM