zoukankan      html  css  js  c++  java
  • ASP.NET Core 入门笔记4,ASP.NET Core MVC路由入门

    敲了一部分,懒得全部敲完,直接复制大佬的博客了,如有侵权,请通知我尽快删除修改

    摘抄自https://www.cnblogs.com/ken-io/p/aspnet-core-tutorial-mvc-route.html

    一、前言

    1、本文主要内容

    • ASP.NET Core MVC路由工作原理概述
    • ASP.NET Core MVC带路径参数的路由示例
    • ASP.NET Core MVC固定前/后缀的路由示例
    • ASP.NET Core MVC正则表达式匹配路由示例
    • ASP.NET Core MVC路由约束与自定义路由约束
    • ASP.NET Core MVC RouteAttribute绑定式路由使用介绍

    2、本教程环境信息

    软件/环境说明
    操作系统 Windows 10
    SDK 2.1.401
    ASP.NET Core 2.1.3
    IDE Visual Studio Code 1.27
    浏览器 Chrome 69

    本篇代码基于上一篇进行调整:https://github.com/ken-io/asp.net-core-tutorial/tree/master/chapter-02

    3、前置知识

    你可能需要的前置知识

    • MVC框架/模式介绍

    https://baike.baidu.com/item/mvc

    • 正则表达式

    http://www.runoob.com/regexp/regexp-tutorial.html

    二、ASP.NET Core MVC 路由简介

    1、ASP.NET Core MVC路由工作原理概述

    ASP.NET Core MVC路由的作用就是将应用接收到请求转发到对应的控制器去处理。

    应用启动的时候会将路由中间件(RouterMiddleware)加入到请求处理管道中,并将我们配置好的路由加载到路由集合(RouteCollection)中。当应用接收到请求时,会在路由管道(路由中间件)中执行路由匹配,并将请求交给对应的控制器去处理。

    另外,需要特别注意的是,路由的匹配顺序是按照我们定义的顺序从上之下匹配的,遵循是的先配置先生效的原则。

    2、路由配置参数说明

    参数名说明
    name 路由名称,不可重复
    template 路由模板,可在模板中以{name}格式定义路由参数
    defaults 配置路由参数默认值
    constraints 路由约束

    在路由配置中,MVC框架内置了两个参数,controller,action。
    路由匹配通过后,需要根据这两个参数将当前请求交由对应的Controller+Action去处理。所以,这两个参数缺少任何一个,都会导致路由无法正常工作。
    通常我们有两个选择:

    • 在template中指定{controller},{action}参数
    • 在默认值中为controller、action指定默认值

    三、ASP.NET Core MVC 路由示例

    1、准备工作

    为了方便我们进行测试,我们先准备好承接路由的Controller&Action

    • 创建TutorialController

    在Controllers文件夹下新增控制器TutorialController.cs并继承于Controller

    using System;
    using Microsoft.AspNetCore.Mvc;
    
    namespace Ken.Tutorial.Web.Controllers
    {
        public class TutorialController : Controller
        {
          
        }
    }
    
    
    • 增加Action:Index
    public IActionResult Index()
    {
        return Content("ASP.NET Core Tutorial by ken from ken.io");
    }
    
    • 增加Action:Welcome
    public IActionResult Welcome(string name, int age)
    {
        return Content($"Welcome {name}(age:{age}) !");
    }
    

    2、带路径参数的路由

    路由配置:

    routes.MapRoute(
            name: "TutorialPathValueRoute",
            template: "{controller}/{action}/{name}/{age}"
        );
    

    此路由适配URL:

    • /tutorial/welcome/ken/20

    不适配URL:

    • /tutorial/welcome/ken

    如果我们希望不在路径中设置age,也可以被路由到,那么可以将age指定为可选参数,将模板中的{age}修改为{age?}即可

    routes.MapRoute(
            name: "TutorialPathValueRoute",
            template: "{controller}/{action}/{name}/{age?}"
        );
    

    此路由适配URL:

    • /tutorial/welcome/ken/20
    • /tutorial/welcome/ken
    • /tutorial/welcome/ken?age=20

    3、固定前后缀的路由

    固定前缀路由配置:

    routes.MapRoute(
        name: "TutorialPrefixRoute",
        template: "jiaocheng/{action}",
        defaults: new { controller = "Tutorial" }
    );
    

    此路由适配URL:

    • /jiaocheng/index
    • /jiaocheng/welcome

    由于路径参数中不包含controller参数,所以需要在默认值中指定。

    固定后缀路由配置

    routes.MapRoute(
        name: "TutorialSuffixRoute",
        template: "{controller}/{action}.html"
    );
    

    此路由适配URL:

    • /tutorial/index.html
    • /tutorial/welcome.html
    • /home/index.html
    • /home/time.html

    固定后缀的路由适用于伪静态等诉求
    固定前后缀可以根据自己的需求结合起来使用。
    当然,你也可以在路由模板中间设定固定值。

    四、ASP.NET Core MVC 路由约束

    1、路由约束介绍

    路由约束主要是用于约束路由参数,在URL格式满足路有模板要求之后,进行参数检查。如果参数不满足路由约束,那么依然会返回未匹配该路由。最常用的可能就是参数类型校验、参数长度校验、以及通过正则满足的复杂校验。

    在开始之前需要在Startup.cs中引用相关命名空间

    using Microsoft.AspNetCore.Routing;
    using Microsoft.AspNetCore.Routing.Constraints;
    

    2、参数长度约束

    路由配置:约束name长度不能>5

    routes.MapRoute(
        name: "TutorialLengthRoute",
        template: "hello/{name}/{age?}",
        defaults: new { controller = "Tutorial", action = "Welcome", name = "ken" },
        constraints: new { name = new MaxLengthRouteConstraint(5) }
    );
    

    此路由适配

    • /hello
    • /hello/ken
    • /hello/ken/1000

    次路由不适配

    • /hello/kenaaaa

    我们也可以直接在模板中配置路由约束:

    routes.MapRoute(
        name: "TutorialLengthRoute2",
        template: "hello2/{name:maxlength(5)}/{age?}",
        defaults: new { controller = "Tutorial", action = "Welcome", name = "ken" }
    );
    

    3、参数范围约束

    路由配置:约束 1<=age<=150

    routes.MapRoute(
        name: "TutorialLengthRoute",
        template: "hello/{name}/{age?}",
        defaults: new { controller = "Tutorial", action = "Welcome", name = "ken" },
        constraints: new {  age = new CompositeRouteConstraint(new IRouteConstraint[] { 
                                new IntRouteConstraint(), 
                                new MinRouteConstraint(1), 
                                new MaxRouteConstraint(150) }) }
    );
    

    此路由适配:

    • /hello/ken/1
    • /hello/ken/150

    此路由不适配

    • /hello/ken/1000

    我们也可以直接在模板中配置路由约束:

    routes.MapRoute(
        name: "TutorialLengthRoute2",
        template: "hello2/{name}/{age:range(1,150)?}",
        defaults: new { controller = "Tutorial", action = "Welcome", name = "ken" }
    );
    

    4、带有正则表达式约束的路由

    路由配置:

    routes.MapRoute(
        name: "TutorialRegexRoute",
        template: "welcome/{name}",
        defaults: new { controller = "Tutorial", Action = "Welcome" },
        constraints: new { name = @"k[a-z]*" }
    );
    

    此路由适配:

    • /welcome/k
    • /welcome/ken
    • /welcome/kevin

    此路由不适配

    • /welcome/k1
    • /welcome/keN
    • /welcome/tom

    这里我们用正则表达式约束了参数name,必须通过正则k[a-z]*匹配通过,即:以小写字母k开头,且后续可跟0到多个小写字母

    我们也可以直接在模板中配置路由约束:

    routes.MapRoute(
        name: "TutorialRegexRoute2",
        template: "welcome2/{name:regex(@"k[a-z]*")}",
        defaults: new { controller = "Tutorial", Action = "Welcome" }
    );
    

    5、自定义路由约束

    1、创建自定义约束

    在项目根目录创建目录Common,并在目录创建类:NameRouteConstraint.cs,然后实现接口:IRouteConstraint

    using System;
    using Microsoft.AspNetCore.Http;
    using Microsoft.AspNetCore.Routing;
    
    namespace Ken.Tutorial.Web.Common
    {
        public class NameRouteConstraint : IRouteConstraint
        {
            public bool Match(HttpContext httpContext, IRouter route, string routeKey, RouteValueDictionary values, RouteDirection routeDirection)
            {
                string name = values["name"]?.ToString();
                if (name == null) return true;
                if (name.Length > 5 && name.Contains(",")) return false;
                return true;
            }
        }
    }
    
    

    这里我们约束当name长度>5时,name中不能包含,

    2、路由配置

    引入命名空间

    using Ken.Tutorial.Web.Common;
    

    在ConfigureServices引入路由约束

    public void ConfigureServices(IServiceCollection services)
        {
            //引入MVC模块
            services.AddMvc();
    
            //引入自定义路由约束
            services.Configure<RouteOptions>(options =>
            {
                options.ConstraintMap.Add("name", typeof(NameRouteConstraint));
            });
        }
    

    配置路由

    routes.MapRoute(
        name: "TutorialDiyConstraintRoute",
        template: "diy/{name}",
        defaults: new { controller = "Tutorial", action = "Welcome" },
        constraints: new { name = new NameRouteConstraint() }
    );
    

    此路由适配:

    • /diy/ken
    • /diy/ken,
    • /diy/kenny

    此路由不适配

    • /diy/kenny,

    当然,按照惯例,依然可以在模板中配置路由约束

    routes.MapRoute(
        name: "TutorialDiyConstraintRoute2",
        template: "diy2/{name:name}",
        defaults: new { controller = "Tutorial", action = "Welcome" }
    );
    

    五、ASP.NET Core MVC 绑定式路由配置

    1、路由配置风格

    • 集中式配置

    前面章节提到的路由配置都是在Startup类中进行的集中式路由配置,集中配置的路由,除了template中没有配置{controller}参数,默认都是对所有控制器(Controller)生效的。这种集中配置的方式一般我们只要配置一个默认路由,其他情况我们只需要不满足默认模板的情况下进行配置即可。尤其是对URL没有友好度要求的应用,例如:后台管理系统

    • 分散式配置/绑定式配置

    对于集中式路由配置的方式,如果某个Controller/Action配置了特殊路由,对于代码阅读就会不太友好。不过没关系,ASP.NET Core MVC也提供了RouteAttribute可以让我们在Controller或者Action上直接指定路由模板。

    不过要强调的是,一个控制器只能选择其中一种路由配置,如果控制器标记了RouteAttribute进行路由配置,那么集中式配置的路由将不对其生效。

    2、绑定式路由配置

    在项目Controllers目中新建TestController.cs继承与Controller
    并配置Action与路由

    using System;
    using Microsoft.AspNetCore.Mvc;
    
    namespace Ken.Tutorial.Web.Controllers
    {
        [Route("/test")]
        public class TestController : Controller
        {
            [Route("")]
            [Route("/test/home")]
            public IActionResult Index()
            {
                return Content("ASP.NET Core RouteAttribute test by ken from ken.io");
            }
    
            [Route("servertime")]
            [Route("/t/t")]
            public IActionResult Time(){
                return Content($"ServerTime:{DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss")} - ken.io");
            }
        }
    }
    
    
    配置项说明
    [Route("/test")] 表示该Controller访问路由前缀为/test,必须以/开头
    [Route("")] 表示以Controller的路由配置为前缀访问该Action;可以通过/test路由到该Action
    [Route("/test/home")] 表示忽略Controller的路由配置;可以通过/test/home路由到该Action
    [Route("servertime")] 表示以Controller的路由配置为前缀访问该Action;可以通过/test/servertime路由到该Action
    [Route("/t/t")] 表示忽略Controller的路由配置;可以通过/t/t路由到该Action

    RouteAttribute中配置的参数,就相当于我们集中式配置中的路由模板(template),最终框架还是帮我们初始化成路由规则,以[Route("/test/home")]为例,相当于生成了以下路由配置:

    routes.MapRoute(
        name: "Default",
        template: "test/home",
        defaults: new { controller = "Test", action = "Index" }
    );
    

    当然,我们也可以在[Route]配置中使用模板参数,而且依然可以在模板中使用约束,自定义约束也没问题。

    [Route("welcome/{name:name}")]
    public IActionResult Welcome(string name){
        return Content($"Welcome {name} !");
    }
    

    最大的区别就是不能定义默认值了,可能也不需要了,你说是吧。_

  • 相关阅读:
    Maidsafe-去中心化互联网白皮书
    The Top 20 Cybersecurity Startups To Watch In 2021 Based On Crunchbase
    Top 10 Blockchain Security and Smart Contract Audit Companies
    The 20 Best Cybersecurity Startups To Watch In 2020
    Blockchain In Cybersecurity: 11 Startups To Watch In 2019
    004-STM32+BC26丨260Y基本控制篇(阿里云物联网平台)-在阿里云物联网平台上一型一密动态注册设备(Android)
    涂鸦开发-单片机+涂鸦模组开发+OTA
    000-ESP32学习开发-ESP32烧录板使用说明
    03-STM32+Air724UG远程升级篇OTA(阿里云物联网平台)-STM32+Air724UG使用阿里云物联网平台OTA远程更新STM32程序
    03-STM32+Air724UG远程升级篇OTA(自建物联网平台)-STM32+Air724UG实现利用http/https远程更新STM32程序(TCP指令,单片机程序检查更新)
  • 原文地址:https://www.cnblogs.com/xiaoahui/p/11723782.html
Copyright © 2011-2022 走看看