Web API-路由(一)

這一篇文章描述了ASP.NET API如何將HTTP請求路由到控制器。web

若是你熟悉ASP.NET MVC,Web API路由和MVC路由很是類似,主要的不一樣地方是Web API使用HTTP方法,而不是URI路徑去選擇action。你也可以在WebAPI中使用MVC風格的路由,這一篇文章不討論任何有關MVC的知識。api

路由表:框架

在ASP.NET Web API 中,一個控制器是一個處理HTTP請求的類,Controller中的公共方法稱做action方法或者簡單方法,當Web API框架接收到一個請求,框架將請求路由到一個action。asp.net

Web API框架使用路由表(route table)來決定哪個action被調用。VS的Web API 項目模版建立了一個默認的路由模版:spa

routes.MapHttpRoute(
    name: "API Default",
    routeTemplate: "api/{controller}/{id}",
    defaults: new { id = RouteParameter.Optional }
);

這個路由模版定義在 App_Start目錄下的WebApiConfig.cs文件中。更多關於WebApiConfig的信息 能夠看:Configuring ASP.NET Web API ..net

若是使用自寄宿(self-host)的Web API,必須經過HttpSelfHostConfiguration本身設置路由表,更多信息能夠參考:Self-Host a Web API.code

路由表中的每一個條目包含一個模板,默認的Web API路由模版是「api/{controller}/{id}」。這個模版裏,「api」是一個純文本路徑段,{controller}和{id}是佔位符(參數變量)。當Web API框架接收到一個請求時,嘗試將URI與路由表中的項(路由模版)匹配,若是沒有能夠匹配的路由項,則返回一個404錯誤,好比下面三個uri能夠和默認的路由模版進行匹配。blog

/api/contactsci

/api/contacts/1路由

/api/products/gizmo1

可是/contacts/1這個就匹配不了由於缺乏「api"段。

:Web API 路由模版使用「api」開頭是爲了不與MVC的路由模版衝突,這樣你可以使用"/contacts"URI去路由到一個MVC controller,而使用"api/contacts" 路由到一個Web API controller。固然,若是你不喜歡,能夠修改默認的路由模版。


 

一旦找到匹配的路由,Web API則進行controller和action的選擇

--To find the controller, Web API adds "Controller" to the value of the {controller} variable.

--匹配action,Web API 查看本次HTTP 方法,好比:若是是GET方法,則在controller中查找Get開頭的方法,這種查詢以HTTP請求方式開頭的action的方式只適合GET , POST , PUT 和 DELETE 方式Http請求???,你能夠經過爲action添加標識屬性的方法來指定action可匹配的HTTP請求方式以及容許其餘的HTTP請求方式。

--其餘的路由模版中的佔位符變量,好比{id},映射爲一個action參數。

下面看一個例子:定義一個以下的controller

public class ProductsController : ApiController
{
    public void GetAllProducts() { }
    public IEnumerable<Product> GetProductById(int id) { }
    public HttpResponseMessage DeleteProduct(int id){ }
}

下面表格展現了不一樣的URI所調用的action

HTTP Method

URI Path

Action

參數

GET

api/products

GetAllProducts

GET

api/products/4

GetProductById

4

DELETE

api/products/4

DeleteProduct

4

POST

api/products

沒有匹配的action

 

注意:這裏的{id}段,若是指定了{id}的值,則調用有id參數的action方法 GetProductById。

由於沒有定義Post開頭的aciton方法,因此POST方式的請求找不到匹配的action。


 

路由拓展

--使用Http Methods 標識屬性:除了定義以HTTP請求方式開頭的action方法外,咱們可使用HttpGet  , HttpPut  ,  HttpPost  或者 HttpDelete標識屬性來指定一個action方法匹配的HTTP請求方式(與使用HTTP請求方式開頭的方法名效果同樣),例如,下面這個方法能夠和GET請求方式的HTTP請求匹配。

public class ProductsController : ApiController
{
    [HttpGet]
    public Product FindProduct(id) {}
}

若是一個action方法須要匹配多種HTTP請求方式,或者須要匹配除GET,POST,PUT,DELETE請求方式外的其餘請求,可使用AccptVerbs標識屬性。例如:FindProduct方法能夠同時匹配 GET 和 HEAD請求。

public class ProductsController : ApiController
{
    [AcceptVerbs("GET", "HEAD")]
    public Product FindProduct(id) { }

    // WebDAV method
    [AcceptVerbs("MKCOL")]
    public void MakeCollection() { }
}

--使用MVC風格的路由

定義路由模版:

routes.MapHttpRoute(
    name: "ActionApi",
    routeTemplate: "api/{controller}/{action}/{id}",
    defaults: new { id = RouteParameter.Optional }
);

在這個路由模版中,{action}參數指定controller中的action的名稱,使用這種風格的路由,須要使用標識屬性指定action容許匹配的HTTP請求方式,好比:必須使用[HttpGet]、[HttpPost]等標識屬性。

public class ProductsController : ApiController
{
    [HttpGet]
    public string Details(int id);
}

上面的例子中一個「api/products/details/1」的GET請求,將映射到Details方法。這種風格很像MVC,可能更適合用在一個RPC-style API中。

--使用ActionName屬性定義action的別名:

public class ProductsController : ApiController
{
    [HttpGet]
    [ActionName("Thumbnail")]
    public HttpResponseMessage GetThumbnailImage(int id);

    [HttpPost]
    [ActionName("Thumbnail")]
    public void AddThumbnailImage(int id);
}

咱們能夠發送uri爲 "api/products/thumbnail/id"的GET請求 map to GetThumbnailImage方法。

發送uri爲"api/products/thumbnail/id"的POST請求 map to AddThumbnailImage 方法。

經過上面幾個例子能夠看出,可使用標識屬性,配置一個action方法用做匹配路由的名稱和方法。

--使用[NonAction]標識屬性來指定一個方法不爲action方法

相關文章
相關標籤/搜索