【WebApi系列】詳解WebApi如何傳遞參數

WebApi系列文章html

【01】淺談HTTP在WebApi開發中的運用ajax

【02】聊聊WebApi體系結構json

【03】詳解WebApi參數的傳遞api

【04】詳解WebApi測試和PostMan數組

【05】淺談WebApi Cores安全

【06】詳解WebApi 異常處理架構

【07】用WebAPI寫個基於EF的CURDapp

【08】淺談WebAPI身份認證框架

【09】詳解系列化和模型綁定post

【10】淺談WebApi如何配合Mvc有效工做

【11】淺談API Reference

【12】淺談接口在軟件架構中的做用

【13】淺談WebApi和WebService的比較

【14】淺談如何設計一個良好的接口

                                                                     

 


閱讀目錄

一     概述

二    Get

    1   基礎數據類型

        1.1  方法只含一個形參

        1.2  方法含多個形參

    2   實體對象類型

    3   實體對象和基礎數據類型混合

    4   最小知足原則

    5   url長度限制

    6   Get規範化

    7    關於實體做爲參數傳遞的拓展

         7.1   藉助[FromUri]特性傳遞實體

         7.2   系列化和反系列化傳遞實體

三    Post

    1   基本數據類型傳遞

         1.1   [FromBody]單個參數傳遞

         1.2  Dynamic單個參數傳遞

    2   實體做爲參數傳遞

    3   實體集合做爲參數傳遞

    4   數組做爲參數傳遞

    5   小結

四   總結

 

 一 概述

通常地,咱們在研究一個問題時,常規的思路是爲該問題建模;咱們在研究類似問題時,常規思路是找出這些問題的共性和異性。基於該思路,咱們如何研究WebApi參數傳遞問題呢?

首先,從參數自己來講,種類較爲多(如int,double,float,string,array,Object等),且有些類型較爲複雜(如值類型和引用類型的機制等);

其次,從基於WebApi的Http請求方法來講,種類多且不盡相同(如Get,post,Delete,put,head等),在上一篇文章 :【WebApi系列】淺談HTTP在WebApi開發中的運用  中,咱們簡要描述了Http請求的20個方法;

..........

如此複雜且不盡相同,關於WebApi參數傳遞,咱們該選擇什麼做爲切入點來研究呢?基於咱們上面提到的研究思路,咱們想到了.NET Framework框架,那麼,咱們來看看基於.NET Framework框架的的WebApi

模板是怎樣的呢?

請按圖中步驟操做

咱們來看看Values控制器是怎樣的

 1  public class ValuesController : ApiController
 2     {
 3         // GET api/values
 4         public IEnumerable<string> Get()
 5         {
 6             return new string[] { "value1", "value2" };
 7         }
 8 
 9         // GET api/values/5
10         public string Get(int id)
11         {
12             return "value";
13         }
14 
15         // POST api/values
16         public void Post([FromBody]string value)
17         {
18         }
19 
20         // PUT api/values/5
21         public void Put(int id, [FromBody]string value)
22         {
23         }
24 
25         // DELETE api/values/5
26         public void Delete(int id)
27         {
28         }
29     }

從Values控制器,咱們不可貴出以下幾個結論:

(1)WebApi常規方法爲四個:Get,Post,Put和Delete;

(2)四種方法的參數可歸結爲兩大類:url傳遞(Request-url)和Body(Request-body)傳遞;

(3)基於(2),咱們將四種方法的參數傳遞歸爲兩大類,而這兩大類又集中在Get和Post中體現了(Put是Get和Post的組合,Delete與Get相似);

 

其實,分析到如今,咱們很容易找獲得了研究WebApi參數傳遞的切入點?研究Get和Post方法參數傳遞便可。是的,沒錯,咱們本篇文章就是基於Get和Post方法的參數傳遞,前者對應Request-url,後者對應Reqeust-Body。

二  Get

1  基礎數據類型


 

1.1  方法只含一個形參(參數傳得進去)

ajax

$(document).ready(function () {
   $("#FindProdcutDetail").click(function () {
       $.ajax({
               type: "Get",
               //url: "/api/Default/GetProductDetails?ProductCode=JX80869"
               url: "/api/Default/GetProductDetails",
               data: { "ProductCode":"JX80869"}
            })
        })           
   })

Result

 總結

(1)當Get方法形參爲一個且爲基本數據類型時,Get方法能接受外部傳遞的值

(2)Get傳值的本質是經過url字符串拼接,如上兩兩種url形式的傳遞的結果都是同樣

url形式1

url: "/api/Default/GetProductDetails?ProductCode=JX80869"

url形式2

url: "/api/Default/GetProductDetails",
data: { "ProductCode":"JX80869"}

咱們用Goole Chrome來看看結果,發現url形式1和url形式2均一致

(3)Get傳遞參數本質是url字符串拼接,Request-Head頭部傳遞,Request-Body中不能傳遞(這是與Post方法的本質區別),咱們舉兩個例子

例子1:咱們將形參添加[FromBody]屬性後,值傳遞不進去

例子2:咱們用PostMan來測試,發現PostMan中,Get方法參數Body爲灰色,是不能選中的

 

1.2  方法含有多個形參(參數傳得進去)

$(document).ready(function () {
   $("#FindProdcutDetail").click(function () {
      $.ajax({
               type: "Get",
               url: "/api/Default/GetProductDetails",
               data: { "ProductCode": "JX80869","ProductName":"YaGao"}
            })
        })
  })

result

2   實體對象類型(參數傳不進去)


 model

 1  public class ProductDetail
 2     {
 3         //產品編碼
 4         [Required]
 5         public string ProductCode { get; set; }
 6         //產品名稱
 7         [Required]
 8         public string ProductName { get; set; }
 9         //產品價格
10         [Required]
11         public double  ProductPrice{ get; set; }
12     }

ajax

$(document).ready(function () {
    var productDetail = { "ProductName": "YaGao", "ProductCode": "JX80869", "ProductPrice": 40.5};
        $("#FindProdcutDetail").click(function () {
            $.ajax({
                    type: "Get",
                    url: "/api/Default/ProductDetails",
                    data: productDetail
                })
            })
        })

result:

 分析

3   實體對象和基礎數據類型混合(實體傳不進去,基礎數據能傳遞進去)


 ajax

1 $(document).ready(function () {
2    $("#FindProdcutDetail").click(function () {
3        $.ajax({
4                 type: "Get",
5                 url: "/api/Default/GetProductDetails",
6                 data: { "_productDetail": "ObjectEntity","ProductName":"YaGao"}
7              })
8         })
9     })

 result

4  最小知足原則(參數傳得進去)


 所謂「最小知足原則」,指外部參數必須至少知足被調用方法的形參(形參個數,形參類型和形參名字),換句話說,被調用方法具備的形參,外部參數必須傳遞進來,被調用方法沒有

的形參,外部參數傳遞與否均可以,不然將會產生狀態碼404錯誤,用數學集合的思路來理解的話,被調用方法的形參至關於外部參數的子集。以下例子,咱們舉一個真子集的例子,

即外部傳遞參數的個數大於被調方法的的形參個數。

Ajax

 $(document).ready(function () {
    $("#FindProdcutDetail").click(function () {
       $.ajax({
                type: "Get",
                url: "/api/Default/GetProductDetails",
                data: {"ProductCode": "JX00034", "ProductName": "YaGao", "ProductPrice": 20.5, "PrudcutType": "Daily Necessities"}
                })
            })
        })

result

 分析:主要緣由是路由規則,路由從url裏面取參數與aciton參數匹配,直到匹配知足爲止,具體詳細深刻內容,在【WebApi系列】路由章節分析。

5  url長度限制


 url參數長度是有必定限制的,當超過必定長度,會報404錯誤

ajax

 $(document).ready(function () {
            $("#FindProdcutDetail").click(function () {
                $.ajax({
                    type: "Get",
                    url: "/api/Default/GetProductDetails",
                    data: {
                        "ProductCode":
                        "JX00034xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" +
                        "JX00034xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" +
                        "JX00034xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" +
                        "JX00034xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" +
                        "JX00034xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" +
                        "JX00034xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" +
                        "JX00034xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" +
                        "JX00034xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" +
                        "JX00034xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" +
                        "JX00034xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" +
                        "JX00034xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" +
                        "JX00034xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" +
                        "JX00034xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" +
                        "JX00034xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" +
                        "JX00034xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" +
                        "JX00034xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" +
                        "JX00034xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" +
                        "JX00034xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" +
                        "JX00034xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" +
                        "JX00034xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" +
                        "JX00034xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" +
                        "JX00034xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" +
                        "JX00034xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" +
                        "JX00034xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" +
                        "JX00034xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" +
                        "JX00034xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" 
                    }
                })
            })
        })

result

6  Get規範化


 關於Get類型規範化,應注意兩點,避免沒必要要的錯誤或異常:(1)方法的命名儘可能採用:「Get+方法名」的形式 (2)在每一個方法上加上特性[HttpGet]。

例子:咱們去掉[HttpGet]特性和方法前的Get,看看狀況什麼怎樣的

ajax

$(document).ready(function () {
    $("#FindProdcutDetail").click(function () {
        $.ajax({
                 type: "Get",
                 url: "/api/Default/ProductDetails",
                 data: {"ProductCode": "JX00034 "}
             })
         })
    })

Controller

1 public class DefaultController : ApiController
2     {
3         4         //[HttpGet]
5         public string ProductDetails(string ProductCode)
6         {
7             return "values";
8         }
9     }

 Result

7  關於實體做爲參數傳遞的拓展


 

7.1  藉助[FromUri]特性傳遞實體

ajax

$(document).ready(function () {
   var GetEntityParam = { "ProductName": "YaGao", "ProductCode": "JX80869", "ProductPrice": 40.5};
      $("#FindProdcutDetail").click(function () {
        $.ajax({
                 type: "Get",
                 url: "/api/Default/ProductDetails",
                 data: GetEntityParam
               })
           })
      })

result

7.2  系列化與反系列化傳遞實體

ajax

$(document).ready(function () {
   $("#FindProdcutDetail").click(function () {
       $.ajax({
                type: "Get",
                url: "/api/Default/ProductDetails",
                data: { "productDetail": JSON.stringify({ "ProductName": "YaGao", "ProductCode": "JX80869", "ProductPrice": 40.5 }) }
             })
         })
     })

 result

 

8  小結


 (1)Get參數傳遞的本質是url字符串拼接;

 (2)url字符串長度受限制;

 (3)Get參數傳遞在Http請求頭部傳遞,而不支持Request-Body傳遞;

 (4)Get類型的方法支持參數爲基本類型,不支持實體類型;

 (5)Get類型的方法命名,應儘可能採用「Get+方法名」的命名方式,且習慣性地在方法前加上[HttpGet特性];

 (6)實參與形參的匹配,遵循路由規則;

(7)Get對應DB的Select操做,從這一點來理解,就知道爲何Http不支持實體對象傳遞的合理性了,由於通常狀況,咱們都是經過簡單的字段查詢信息(對應基本類型),

如ID號,用戶名等,而不會經過一個實體查詢數據;

 三    Post 

1  基本數據類型傳遞


 

1.1  [FromBody]單個參數傳遞

ajax

result

1.2 dynamic單個參數傳遞

 ajax

$(document).ready(function () {
   $("#FindProdcutDetail").click(function () {
      $.ajax({
               type: "Post",
               contentType: 'application/json',
               url: "/api/Default/PostParamToProducts",
               data: JSON.stringify({"ProductCode":"JX00039"})
           })
       })
   })

result

Googel Chrome查看

2 實體做爲參數傳遞


 ajax

$(document).ready(function () {
   $("#FindProdcutDetail").click(function () {
      $.ajax({
               type: "Post",
               url: "/api/Default/PostParamToProducts",
               data: { "ProductCode": "JX00036","ProductName":"YaGao","ProductPrice":20.5}
            })
        })
    })

result

咱們用Googel  Chrome看看

3 實體集合做爲參數傳遞


 ajax

$(document).ready(function () {
   var list_ProductDetail = [
       { "ProductCode": "JX00031", "ProductName": "ToothPaste", "ProductPrice": "20.5" },
       { "ProductCode": "JX00032", "ProductName": "ToothBrush ", "ProductPrice": "18.9" },
       { "ProductCode": "JX00033", "ProductName": "Pen", "ProductPrice": "199.9" },
       { "ProductCode": "JX00034", "ProductName": "computer", "ProductPrice": "15000.5" }
       ]
   $("#FindProdcutDetail").click(function () {
   $.ajax({
             type: "Post",
             contentType: 'application/json',
             url: "/api/Default/PostParamToProducts",
              data: JSON.stringify(list_ProductDetail)
          })
      })
  })

 result

Google Chrome 查看

4  數組做爲參數傳遞


 ajax

$(document).ready(function () {
   var arr = ["a", "b", "c", "d"];
   $("#FindProdcutDetail").click(function () {
      $.ajax({
               type: "Post",
               contentType: 'application/json',
               url: "/api/Default/PostParamToProducts",
               data: JSON.stringify(arr)
            })
       })
  })

Result

咱們用Google Chrome看看

5  小結


 (1)Post參數傳遞本事是在Request-Body內傳遞,而Get參數傳遞本質是url拼接;

(2)Post參數傳遞不是key/value形式,而Get參數是key/value形式;

(3)Post傳遞參數時,不管是單個參數仍是對象,均藉助[FromBody]特性(固然,某些狀況去掉[FromBody]特性也可把值傳遞進去,但未了規範化,儘可能加上該特性);

(4)Post沒長度限制,而Get有長度限制(通常爲1024b);

(5)Post相對Get,較安全;

(6)Post操做至關於DB的Insert操做;

四  總結

1.雖然HTTP請求方法有20多種,經常使用的大體爲4種,即Get,Post,Put,Delete(固然,像Trace,Head等也經常使用);

2.Get,Post,Put,Delete分別對應DB的Select,Insert,Update和Delete操做;

3.WebApi參數類型,大體分爲基本數據類類型和對象數據類型(固然你也能夠理解爲抽象數據類型);

4.研究WebApi參數傳遞,只需研究Get和Post便可,由於其餘http方法參數傳遞基本都是有這兩種組合而成(如Put有Get和Post組合而成),或者類似(如Delete與Get類似);

5.對於控制器方法,儘可能參照規範格式寫,如在相應控制器方法上加上對應的htt請求(Get對應[HttpGet],Post對應[HttpPost]),方法名儘可能採用「Http請類型+方法名」格式(如Get請求,建議採用Get+MethodName;Post請求對應Post+MethodName);

6.WebApi參數請求,大體分爲兩大類型,即Request-url和Request-body;

7.文中咱們還簡要分析了Get和Post區別;

8.關於如何設計一個良好的接口,在文章中,咱們觸及了一下,但未研究,會在後續的文章中單獨分析;

 

五   服務區

 有喜歡的朋友,能夠看一下,不喜歡的的朋友,勿噴,謝謝!!

 

六   版權區

 

  • 感謝您的閱讀,如有不足之處,歡迎指教,共同窗習、共同進步。
  • 博主網址:http://www.cnblogs.com/wangjiming/。
  • 極少部分文章利用讀書、參考、引用、抄襲、複製和粘貼等多種方式整合而成的,大部分爲原創。
  • 如您喜歡,麻煩推薦一下;如您有新想法,歡迎提出,郵箱:2098469527@qq.com。
  • 能夠轉載該博客,但必須著名博客來源。
相關文章
相關標籤/搜索