ASP.NET Core Attribute 路由

ASP.NET Core中我们可以使用C# Attribute特性给Controller和Actions方法添加路由,如果Program类中定义了契约路由,我们可以使用Attribute路由来重写契约路由

1 Attribute路由例子

和之前一样,我们通过一个例子来了解Attribute路由,在Visual Studio中创建一个ASP.NET Core MVC项目.

ASP.NET Core Attribute 路由

默认的契约路由定义在Program类中,如下代码所示:

app.MapControllerRoute(    name: "default",    pattern: "{controller=Home}/{action=Index}/{id?}");
如何设置Attribute路由呢?在C#中有[Route()] 特性,我们可以把该特性应用到Controller或者Action 方法,例如 提交一个特性-[Route("CallRoute")]在Home控制器的Index方法上,这将针对这个方法添加一个attribute路由,现在Inedx方法将使用/CallRoute路由,代码如下:
using AspNetCore.AttributeRoute.Models;using Microsoft.AspNetCore.Mvc;using System.Diagnostics;namespace AspNetCore.AttributeRoute.Controllers{    public class HomeController : Controller    {        private readonly ILogger<HomeController> _logger;        public HomeController(ILogger<HomeController> logger)        {            _logger = logger;        }        [Route("CallRoute")]        public IActionResult Index()        {            return View();        }    }}
运行程序并访问https://localhost:7073/CallRoute,我们发现HomeController中的Index方法被调用,这是因为使用路由特性访问这个方法的url               

ASP.NET Core Attribute 路由

使用契约路由,打开https://localhost:7073/Home/Index,我们发现这个地址不再工作,这是因为Attribute路由的重写契约路由,因此老的路由不再工作 

ASP.NET Core Attribute 路由

这里我们必须记住,当我们使用Attribute路由时,并不意味着所有契约路由将不能工作,当契约路由和Attribute路由都被应用时,在ASP.NET Core中Attribute路由具有更高的优先级,你可以测试一下,当我们打开https://localhost:7073/Home/Privacy,HomeController中的Privacy方法被调用

ASP.NET Core Attribute 路由

2 Attribute路由中的[controller]和[action]标记

[controller]和[action]标记作为路由特性引用Controller和Action名字,为了更容易理解,我们创建一个例子,添加AdminController.cs,在Controller中添加如下代码:

using Microsoft.AspNetCore.Mvc;namespace AspNetCore.AttributeRoute.Controllers{    public class AdminController : Controller    {        [Route("[controller]/CallMe")]        public string Index()        {            return "'Admin' Controller, 'Index' View";        }        public string List()        {            return "'Admin' Controller, 'List' View";        }    }}
我们将这个路由特性提交到Index方法,这个路由包含了Controller段,这个段会使用Controller名字替换掉,这个路由的特性被替换为Admin,后面跟着CallMe的字符串,因此调用这个方法的url是/Admin/CallMe

运行程序来,打开https://localhost:7073/Admin/Callme,你会发现Admin控制器中的Index方法被调用,如下图所示:

ASP.NET Core Attribute 路由

注意,我们没有给List方法添加Attribute特性,因此它将使用 https://localhost:7073/Admin/List

我们将[action]标记应用到路由特性,添加一个新的action方法叫Show在AdminController并且在该方法上使用Attribute路由:
[Route("[controller]/CallMe/[action]")]public string Show(){    return "'Admin' Controller, 'Show' View";}

我们使用https://localhost:7073/admin/callme/show 调用这个action方法

3 在Controller上使用路由特性

我们也可以在Controller上使用路由特性,因此控制器里面的所有方法将继承这个路由特性,修改AdminController代码如下:

using Microsoft.AspNetCore.Mvc;namespace AspNetCore.AttributeRoute.Controllers{    [Route("News/[controller]/USA/[action]/{id?}")]    public class AdminController : Controller    {        //[Route("[controller]/CallMe")]        public string Index()        {            return "'Admin' Controller, 'Index' View";        }        public string List()        {            return "'Admin' Controller, 'List' View";        }        //[Route("[controller]/CallMe/[action]")]        public string Show()        {            return "'Admin' Controller, 'Show' View";        }    }}

我们在Controller上应用了Attribute路由,因此该类的所有方法会会自动继承它,下面URL将调用Index方法

/News/Admin/USA/Index/News/Admin/USA/Index/100/News/Admin/USA/Index/Hello

下面URL将调用List方法

/News/Admin/USA/List/News/Admin/USA/List/100/News/Admin/USA/List/Hello

4 Attribute路由约束

Attribute路由可以使用路由约束,例如在下面代码中我们Attribute路由中给id段添加Int约束,这将只允许id段使用int值
[Route("[controller]/[action]/{id:int}")]public class AdminController : Controller{}

因此上面的URL将匹配

/Admin/Index/10/Admin/List/4/Admin/Privacy/5

下面URL将不会被匹配

/Admin/Index/Jack/Admin/List/Admin/Privacy/USA/100

我们在上一节中创建一个户自定约束叫OnlyGodsConstraint,它也可以被应用到路由特性,代码如下:

using Microsoft.AspNetCore.Mvc;namespace URLRouting.Controllers{    [Route("News/[controller]/USA/[action]/{id:allowedgods?}")]    public class AdminController : Controller    {        public string Index()        {            return "'Admin' Controller, 'Index' View";        }        public string List(string id)        {            return "'Admin' Controller, 'List' View";        }    }}
使用https://localhost:7073/News/Admin/USA/Index/Shiv调用Index方法,如下图所示:

ASP.NET Core Attribute 路由

总结

这节我们主要了解了Attribute路由
源代码地址
https://github.com/bingbing-gui/Asp.Net-Core-Skill/tree/master/Fundamentals/AspNetCore.Route/AspNetCore.AttributeRoute