我要MVC潜规则之配置Routing4文档格式.docx
《我要MVC潜规则之配置Routing4文档格式.docx》由会员分享,可在线阅读,更多相关《我要MVC潜规则之配置Routing4文档格式.docx(8页珍藏版)》请在冰豆网上搜索。
将路由添加到Routes集合中的顺序。
已经提供给路由的所有默认值。
已经提供给路由的任意约束。
是否定义路由来处理匹配物理文件的请求。
为避免错误的处理程序处理请求,必须在定义路由时考虑以上所有条件。
出现在Routes集合中的Route对象的顺序是很重要的。
路由将在集合的整个路由过程中一直尝试匹配。
当匹配发生时,无法计算更多的路由。
通常,按从路由定义的具体性递减的顺序将路由添加到Routes属性。
实例说明
假定您使用以下模式添加路由:
路由1设置为{controller}/{action}/{id}
路由2设置为products/show/{id}
路由2将不再处理请求,这是因为首先计算路由1,路由1始终匹配同样适用于路由2的请求。
对http:
//server/application/products/show/bikes的请求似乎能更好地匹配路由2,但它是由路由1使用下列值处理的:
controller为products。
action为show。
id为bikes。
如果请求缺少参数,则会使用默认值。
因此,可能导致路由匹配意外的请求。
例如,假定您使用以下模式添加路由:
路由1:
{report}/{year}/{month},对于year和month使用默认值。
路由2:
{report}/{year},对于year使用默认值。
路由2将永远不处理请求。
路由1可能用于月度报表,而路由2可能用于年度报表。
但是,路由1中的默认值意味着将匹配同时适用于路由2的所有请求。
可以通过在模式中包括例如annual/{report}/{year}和monthly/{report}/{year}/{month}的常量来避免二义性。
如果URL与在RouteTable集合中定义的任何Route对象都不匹配,ASP.NET路由将不处理请求。
相反,会将处理传递给ASP.NET页、Web服务或其他ASP.NET终结点。
向MVC程序中添加路由
如果你想通过创建派生自ControllerBase类的类,并赋予它们以“Controller”结尾的名称来采纳实现控制器的MVC实例,此时您就不需要在MVC应用程序中再手动添加路由规则。
因为MVC程序已经预先配置了默认的路由规则,该规则将调用您在Controller类中实现的操作方法。
如果您想要在MVC应用程序中添加自定义路由,则要使用MapRoute(RouteCollection,String,String)方法,不要使用MapPageRoute(String,String,String)方法。
RouteCollectionExtensions.MapRoute方法(RouteCollection,String,String)
映射指定的URL路由。
参数(应用程序的路由的集合,要映射的路由的名称,路由的URL模式)返回类型为System.Web.Routing.Route对映射路由的引用
RouteCollection.MapPageRoute方法(String,String,String)
提供用于定义Web窗体应用程序的路由的方法。
参数(路由的名称,
路由的URL模式,路由的物理URL)
提供此方法是为了方便编码。
它等效于调用Add方法,然后传递使用PageRouteHandler类创建的Route对象。
下面的示例演示在Global.asax文件(该文件是在MVC应用程序的VisualStudio项目模板中定义的)中创建默认MVC路由的代码。
publicstaticvoidRegisterRoutes(RouteCollectionroutes)
{
//忽略对.axd文件的Route,也就是和WebForm一样直接去访问.axd文件
routes.IgnoreRoute("
{resource}.axd/{*pathInfo}"
);
routes.MapRoute(
"
Default"
//路由名称
"
{controller}/{action}/{id}"
//带有参数的URL
new{controller="
Home"
action="
Index"
id=UrlParameter.Optional}//参数默认值
);
}
protectedvoidApplication_Start()
//在程序启动的时候注册我们前面定义的Route规则
RegisterRoutes(RouteTable.Routes);
设置URL参数默认值
定义路由时可以为参数分配一个默认值。
如果URL没有包括该参数的值,则会使用默认值。
通过将字典对象分配给Route类的Defaults属性,可以设置路由的默认值。
下面的示例演示如何使用MapPageRoute(String,String,String,Boolean,RouteValueDictionary)方法添加具有默认值的路由。
如下:
MVC应用程序的VisualStudio项目模板中默认MVC路由的代码
RouteCollection.MapPageRoute方法(String,String,String,Boolean,RouteValueDictionary)
参数(路由的名称,路由的URL模式,路由的物理URL,一个值该值指示ASP.NET是否应验证用户是否有权访问物理URL(始终会检查路由URL),路由参数的默认值)
返回类型为System.Web.Routing.Route将添加到路由集合的路由
自定义默认路由
如下代码:
routes.MapPageRoute("
"
Category/{action}/{categoryName}"
~/categoriespage.aspx"
true,
newRouteValueDictionary{{"
categoryName"
"
food"
},{"
action"
show"
}});
运行上面示例中演示的路由定义(使用针对categoryName的food的默认值和针对action的show的默认值)得到下表列出的结果。
URL
参数值
/Category
action="
(默认值)categoryName="
(默认值)
/Category/add
add"
categoryName="
/Category/add/beverages
categoryName="
beverages"
对于MVC应用程序,通过RouteCollectionExtensions.MapRoute方法的重载(例如MapRoute(RouteCollection,String,String,Object,Object))可以指定默认值。
在URL模式中处理可变数量的段
有时我们需要处理包含可变数量的URL段的URL请求。
定义路由时,可以指定URL是否具有比模式中更多的段,是否将额外的段视为最后一个段的一部分。
若要以此方式处理额外的段,可以用星号(*)标记最后一个参数。
该参数称为“可用于放置各种信息的”参数。
具有全部捕捉参数的路由也将与那些不包含最后一个参数的任意值的URL相匹配。
下面的示例演示一个与未知数量的段匹配的路由模式。
query/{queryname}/{*queryvalues}
ASP.NET路由处理URL请求时,在示例中演示的路由定义得到下表列出的结果。
/query/select/bikes/onsale
queryname="
select"
queryvalues="
bikes/onsale"
/query/select/bikes
bikes"
/query/select
queryvalues=Emptystring
添加路由约束
除了按照URL中的参数数量将URL请求匹配到路由定义中,还可以指定参数中的值满足特定约束。
如果一个URL包含路由的约束以外的值,则该路由不用于处理请求。
添加约束以确保URL参数包含将在应用程序中起作用的值。
约束是通过使用正则表达式或使用实现IRouteConstraint接口的对象来定义的。
将路由定义添加到Routes集合时,同时也通过创建一个包含验证测试的RouteValueDictionary对象添加了约束。
字典中的关键字标识约束适用的参数。
字典中的值可以是表示正则表达式的字符串,也可以是实现IRouteConstraint接口的对象。
提供字符串后,路由将视字符串为正则表达式,并通过调用Regex类的IsMatch方法检查参数值是否有效。
总是将正则表达式视为不区分大小写。
提供IRouteConstraint对象后,ASP.NET路由将通过调用IRouteConstraint对象的Match方法检查参数值是否有效。
Match方法返回一个布尔值,该值指示参数值是否有效。
通过使用正则表达式可以规定参数格式,比如controller参数只能为4位数字:
new{controller=@"
\d{4}"
}
通过第IRouteConstraint接口目前可以限制请求的类型.因为System.Web.Routing中提供了HttpMethodConstraint类,这个类实现了IRouteConstraint接口.我们可以通过为RouteValueDictionary字典对象添加键为"
httpMethod"
值为一个HttpMethodConstraint对象来为路由规则添加HTTP谓词的限制,比如限制一条路由规则只能处理GET请求:
httpMethod=newHttpMethodConstraint("
GET"
POST"
)
完整的代码如下:
//带有参数的URL
id="
},//参数默认值
new{controller=@"
httpMethod=newHttpMethodConstraint("
)}
);
当然我们也可以在外部先创建一个RouteValueDictionary对象在作为MapRoute的参数传入,这只是语法问题.
示例:
演示如何使用MapPageRoute方法创建具有约束的路由,该约束限制可在locale和year参数中包括的值。
(在MVC应用程序中,使用MapRoute方法。
)
}},
locale"
[a-z]{2}-[a-z]{2}"
year"
@"
}}
路由处理URL请求时,在上一示例中演示的路由定义生成下表列出的结果。
结果
/US
无匹配。
locale和year都是必需的。
/US/08
对year的约束需要4个数字。
/US/2008
locale="
US"
year="
2008"
实例:
下面是自定义的一些路由规则
//URL匹配
//Details/list/CQ/100,200-3
routes.MapRoute(
Details"
Details/{action}/{city}/{price}-{star}"
new{controller="
list"
city="
CQ"
price="
-1,-1"
star="
-1"
},
new{city=@"
[a-zA-Z]*"
price=@"
(\d)+\,(\d)+"
[-1-5]"
//Details/所有匹配
Details/{*values}"
new{controller="
default"
//Home/.
{*values}"
index"
没有路由怎么办?
在某些情况下,即使为网站启用了请求,ASP.NET路由也不处理请求。
本节介绍路由不处理请求的一些情况。
找到匹配URL模式的物理文件
默认情况下,路由不处理映射到Web服务器上现有物理文件的请求。
例如,如果Products/Beverages/Coffee.aspx上存在物理文件,则路由不处理对http:
//server/application/Products/Beverages/Coffee.aspx的请求。
即使匹配一个定义的模式(例如{controller}/{action}/{id}),路由也不处理该请求。
如果希望路由处理所有请求(包括指向文件的请求),可以通过将RouteCollection对象的RouteExistingFiles属性设置为true来重写默认行为。
将该值设置为true后,与定义的模式匹配的所有请求都将由路由处理。
为URL模式显式禁用路由
还可以指定路由不应处理某些URL请求。
通过定义路由并指定应使用StopRoutingHandler类来处理该模式,来阻止路由处理某些特定请求。
当StopRoutingHandler对象处理请求时,StopRoutingHandler对象会阻止以任何其他方式将该请求处理为路由。
而是会将该请求处理为ASP.NET页、Web服务或其他ASP.NET终结点。
可以使用RouteCollection.Ignore方法(对于MVC应用程序,为RouteCollectionExtensions.IgnoreRoute)创建使用StopRoutingHandler类的路由。
下面的示例演示如何阻止路由处理WebResource.axd文件的请求。