Razor 页面路由到默认页面的问题

Posted

技术标签:

【中文标题】Razor 页面路由到默认页面的问题【英文标题】:Problem with Razor pages routing to default pages 【发布时间】:2021-10-02 14:29:07 【问题描述】:

当我尝试使用 url /Home/ 访问 /Pages/Home 目录下的 index.cshtml 页面时Home/index 内部重定向总是发生在 /Pages 目录下的 index.cshtml 页面上。

如果我使用 URL /Home/Home 的另一种情况,我可以成功访问 /Pages/Home 下的 index.cshtml 页面,并且不会发生重定向。

这是项目结构

启动类配置

  public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
    
        app.UseMiddleware<ErrorHandlerMiddleware>();

        if (env.IsDevelopment())
        
            app.UseDeveloperExceptionPage();
        
        else
        
            app.UseExceptionHandler("/Error");
            // 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.UseHttpsRedirection();
        

        app.UseFileServer();
        app.UseSession();
        app.UseRouting();
        app.UseAuthentication();
        app.UseAuthorization();
        app.UseRequestLocalization();

        app.UseEndpoints(endpoints =>
        
            endpoints.MapRazorPages().RequireAuthorization();
     

        );
    

配置服务

  public void ConfigureServices(IServiceCollection services)
    
        services.AddAntiforgery(o => o.HeaderName = xHeaderName);
        services.AddDataReposiotry();
        services.AddBackOfficeServices();
        services.AddDbContext<DigitalServiceContext>(options => options.UseSqlServer(Configuration.GetConnectionString(ConnectionString)));

        services.ConfigureApplicationCookie(options =>
        
            options.LoginPath = xLoginPath;
            options.Cookie.HttpOnly = true;
            options.Cookie.IsEssential = true;
            options.ExpireTimeSpan = TimeSpan.FromHours(1);
        );
        services.Configure<CookiePolicyOptions>(options =>
        
            // This lambda determines whether user consent for non-essential cookies is needed for a given request.
            options.CheckConsentNeeded = context => true;
            options.MinimumSameSitePolicy = SameSiteMode.None;
        );
        services.AddAuthentication(CookieAuthenticationDefaults.AuthenticationScheme).AddCookie(cookieOptions =>
        
            cookieOptions.LoginPath = xLoginPath;
            cookieOptions.Cookie.Name = "DSINTRANET";
            cookieOptions.Cookie.IsEssential = true;
        );
        services.AddHttpClient();
        //services.AddLocalization(options => options.ResourcesPath = "Resources");
        services
           .AddMvc()
           .AddViewLocalization()
           .AddDataAnnotationsLocalization(options =>
           
               options.DataAnnotationLocalizerProvider = (type, factory) =>
               
                   var assemblyName = new AssemblyName(typeof(CommonResources).GetTypeInfo().Assembly.FullName);
                   return factory.Create(nameof(CommonResources), assemblyName.Name);
               ;
           );

        var cultures = new CultureInfo[]
        
            new CultureInfo("en"),
            new CultureInfo("ar"),
        ;
        services.AddRazorPages(options =>
        
            options.RootDirectory = "/Pages";
            options.Conventions.AddFolderApplicationModelConvention(
                "/Workflow",
                model => model.Filters.Add(new VerfiySessionDataAttribute(Configuration)));
            options.Conventions.AddFolderApplicationModelConvention(
                "/Home",
                model => model.Filters.Add(new VerfiySessionDataAttribute(Configuration)));
            options.Conventions.AddFolderApplicationModelConvention(
                "/Dashboard",
                model => model.Filters.Add(new VerfiySessionDataAttribute(Configuration)));
        )
        .AddExpressLocalization<CommonResources>(ops =>
        
            ops.ResourcesPath = "Resources";
            ops.RequestLocalizationOptions = o =>
            
                o.SupportedCultures = cultures;
                o.SupportedUICultures = cultures;
                o.DefaultRequestCulture = new RequestCulture("en");
            ;
        );
        services.AddSession(options =>
        
            options.IdleTimeout = TimeSpan.FromMinutes(double.Parse(Configuration["Session:IdleTimeout"]));
        );
        services.AddMemoryCache();
        services.Configure<FormOptions>(x => x.MultipartBodyLengthLimit = 5368709120);
        AddMapperProfile(services, Configuration);
    

知道这里可能是什么问题吗?

【问题讨论】:

请不要截图代码 --> idownvotedbecau.se/imageofcode @gsharp 代码编辑删除了屏幕截图 【参考方案1】:

使用 AddRazorPages 重载配置 Razor Pages 约定,该重载在 Startup.ConfigureServices 中配置 RazorPagesOptions。

路线顺序 路由指定一个Order 进行处理(路由匹配)。

路由处理是按约定建立的:

1.Routes按顺序处理(-1,0,1,2,...n)。

2.当路由具有相同的Order时,首先匹配最具体的路由,然后是不太具体的路由。

3.当具有相同Order和相同数量参数的路由匹配请求URL时,路由将按照它们添加到PageConventionCollection的顺序进行处理。

具体例子可以看官方文档:

Razor Pages route and app conventions in ASP.NET Core

【讨论】:

【参考方案2】:

根目录中的索引始终是默认页面。要更改它,请添加一个新的根目录

ConfigureServices(IServiceCollection services)


.......

    services.AddRazorPages()
    .AddRazorPagesOptions(options => 
        options.RootDirectory = "/Home";
    );

......


【讨论】:

以上是关于Razor 页面路由到默认页面的问题的主要内容,如果未能解决你的问题,请参考以下文章

到基础 Razor 页面的多个别名路由

更改 ASP.NET Core Razor 页面中的默认登录页面?

无法在默认 Blazor 服务器端项目中找到 Razor 页面

迁移到 ASP.NET 3.1 - 从登录控制器路由到 Razor 页面主页索引页面不再工作

将子文件夹路由到根 URL

多租户 Razor 页面