2016年2月14日 星期日

ASP.NET Web API - Import a Postman Collection Part.1

之前介紹了幾篇在開發 ASP.NET Web API 專案時會使用到的功能:
ASP.NET Web Api - Help Page
ASP.NET Web API 文件產生器 - 使用 Swagger
Swashbuckle - Swagger for Web Api 顯示內容的調整

雖然 Help Page 可以提供專案 API 功能說明文件的查看,而 Swagger 除了涵蓋 Help Page 所提供的文件查看功能外,也可以直接在頁面上操作 API 並且立即得到執行結果。

在開發過程中,開發人員主要還是會透過 Postman 進行開發的偵錯、測試、操作等,如果開發人員只有一個人的時候,在 Postman 裡增加或管理 Collection, API 都還算是可以控制,但如果是多人開發團隊共同開發一個 Web API 專案時,就會發現到每個人所使用的 API Collection 內容都有很大的出入與差異,所以就必須要有一個能夠一致化 API Collection 的功能,讓團隊的每個開發人員都使用一樣的 API Collection 進行操作。

 


其實相同功能的文章已經有人寫過了:

KingKong Bruce記事: 匯出ASP.NET Web API公開API方法至PostMan Collections
[ASP.NET] Web API - 匯入API資訊到Postman | No.18 - 點部落

兩篇的內容其實都是講一樣的功能,不過兩位 MS MVP 的文章是 VB.NET 與 C# 各一篇,所以專案是使用 VB.NET 所開發的就可以參考 Bruce 的文章, 如果是用 C# 的話,可以參考 Ian Chen 的文章,或是就繼續往下看。

參考的原始來源是來自於以下的這一篇文章:

Using ApiExplorer to export API information to PostMan, a Chrome extension for testing Web APIs - Yao's blog

 

為何要有這個功能?

當 Web API 專案的 API 項目越來越多的時候,使用 Postman 進行開發測試操作就會有管理的問題,前前面一開始有說過,當一個人開發的時候還不會有太大的問題,但多人共同開發就必須要保持 API Collection 內容的一致,否則團隊裡的每個人都使用不同版本的 API Collection 就會出狀況,初期可以由 Team Leader 去做管理,定時整理最新的 API Collection 然後匯出再提供給團隊成員。

如果版本更新相當頻繁而且東西又多的話,那 Team Leader 成天只要維護 API Collection 的資料,其他事情就可以不用做了。所以必須要有一個更為簡單且快速的替代方案,讓團隊成員可以在更新專案原始碼版本後就可以取得最新的 API Collection,並且自行匯入 Postman。

接下來要說明的就是怎麼做出這個功能。

 

ASP.NET Web API Help Page 與 XML Document

這邊必須要先做以下這一篇文章的內容,要加入 Help Page 以及產生 XML Document

ASP.NET Web Api - Help Page

image

image

要記得修改 ~/Areas/HelpPage/App_Start/HelpPageConfig.cs 內容

image

開啟 Help Page 查看 API 文件內容,確認各個 API 的 Controller 與 Action 方法都有顯示

image

加入 Postman 匯出功能

參考 Yao 的文章,建立相關類別和程式內容

Using ApiExplorer to export API information to PostMan, a Chrome extension for testing Web APIs - Yao's blog

在 Models 建立兩個類別:PostmanCollection.cs, PostmanRequestGet.cs

image

類別的內容與來源文章的參考內容稍有不同,因為我不習慣類別裡的公開成員為小寫格式,不應該為了要輸出 JSON 而讓屬性名稱使用英文小寫,應該保持 Pascal 命名格式,而屬性則可以使用 JsonProperty Attribute 去讓輸出 JSON 時可以輸出小寫英文的格式。

PostmanRequest.cs

using System;
using Newtonsoft.Json;
 
namespace WebApplication1.Models.Postman
{
    public class PostmanRequest
    {
        [JsonProperty(PropertyName = "collectionId")]
        public Guid CollectionId { get; set; }
 
        [JsonProperty(PropertyName = "id")]
        public Guid Id { get; set; }
 
        [JsonProperty(PropertyName = "name")]
        public string Name { get; set; }
 
        [JsonProperty(PropertyName = "description")]
        public string Description { get; set; }
 
        [JsonProperty(PropertyName = "url")]
        public string Url { get; set; }
 
        [JsonProperty(PropertyName = "method")]
        public string Method { get; set; }
 
        [JsonProperty(PropertyName = "headers")]
        public string Headers { get; set; }
 
        [JsonProperty(PropertyName = "data")]
        public string Data { get; set; }
 
        [JsonProperty(PropertyName = "dataMode")]
        public string DataMode { get; set; }
 
        [JsonProperty(PropertyName = "timestamp")]
        public long Timestamp { get; set; }
    }
}

PostmanCollection.cs

using System;
using System.Collections.Generic;
using Newtonsoft.Json;
 
namespace WebApplication1.Models.Postman
{
    public class PostmanCollection
    {
        [JsonProperty(PropertyName = "id")]
        public Guid Id { get; set; }
 
        [JsonProperty(PropertyName = "name")]
        public string Name { get; set; }
 
        [JsonProperty(PropertyName = "timestamp")]
        public long Timestamp { get; set; }
 
        [JsonProperty(PropertyName = "requests")]
        public ICollection<PostmanRequest> Requests { get; set; }
    }
}

 

新增 PostmanController.cs

using System;
using System.Collections.ObjectModel;
using System.Net;
using System.Net.Http;
using System.Web;
using System.Web.Http;
using System.Web.Http.Description;
using WebApplication1.Models.Postman;
 
namespace WebApplication1.Controllers
{
    [ApiExplorerSettings(IgnoreApi = true)]
    public class PostmanController : ApiController
    {
        public HttpResponseMessage Get()
        {
            var collection = Configuration.Properties.GetOrAdd(
                "postmanCollection", k =>
                {
                    var requestUri = Request.RequestUri;
                    string baseUri = requestUri.Scheme + "://" + requestUri.Host + ":" + requestUri.Port +
                                     HttpContext.Current.Request.ApplicationPath;
 
                    var postManCollection = new PostmanCollection();
                    postManCollection.Id = Guid.NewGuid();
                    postManCollection.Name = "ASP.NET Web API Service";
                    postManCollection.Timestamp = DateTime.Now.Ticks;
                    postManCollection.Requests = new Collection<PostmanRequest>();
 
                    foreach (var apiDescription in Configuration.Services.GetApiExplorer().ApiDescriptions)
                    {
                        var request = new PostmanRequest
                                      {
                                          CollectionId = postManCollection.Id,
                                          Id = Guid.NewGuid(),
                                          Method = apiDescription.HttpMethod.Method,
                                          Url = baseUri.TrimEnd('/') + "/" + apiDescription.RelativePath,
                                          Description = apiDescription.Documentation,
                                          Name = apiDescription.RelativePath,
                                          Data = "",
                                          Headers = "",
                                          DataMode = "params",
                                          Timestamp = 0
                                      };
                        postManCollection.Requests.Add(request);
                    }
                    return postManCollection;
                }) as PostmanCollection;
 
            return Request.CreateResponse<PostmanCollection>(HttpStatusCode.OK, collection, "application/json");
        }
    }
}

 

Postman - Import From URL

建立完成並且重新建置專案後執行,Web API 專案的執行 URL 使用 Postman,例如「localhost:20620/api/postman」,應該可以看到輸出的 API Collection 的 JSON 格式的資料內容,

image

 

開啟 Postman 並且使用 Import 功能,選擇使用 Import From URL,

image

image

匯入結果

image

P.S.
API Collection 的名稱可以在「PostmanController.cs」裡去修改 PostmanCollection.Name 內容

 


這樣就完成了嗎?

當然沒有,請看看最後一張圖,如果你的 Web API 服務裡有一堆的 API 項目,全部的 API 項目就這樣一次列出來,當我們要找尋其中一個 API 的時候就會碰上麻煩,因為真的很難可以馬上找出來,所以下一篇就來說明如何解決。

 

延伸閱讀

ASP.NET Web Api - Help Page
ASP.NET Web API 文件產生器 - 使用 Swagger
Swashbuckle - Swagger for Web Api 顯示內容的調整

 

參考資料

Using ApiExplorer to export API information to PostMan, a Chrome extension for testing Web APIs - Yao's blog

KingKong Bruce記事: 匯出ASP.NET Web API公開API方法至PostMan Collections

[ASP.NET] Web API - 匯入API資訊到Postman | No.18 - 點部落

 

以上

1 則留言:

提醒

千萬不要使用 Google Talk (Hangouts) 或 Facebook 及時通訊與我聯繫、提問,因為會掉訊息甚至我是過了好幾天之後才發現到你曾經傳給我訊息過,請多多使用「詢問與建議」(在左邊,就在左邊),另外比較深入的問題討論,或是有牽涉到你實作程式碼的內容,不適合在留言板裡留言討論,請務必使用「詢問與建議」功能(可以夾帶檔案),謝謝。

最近的留言