Design

Design
asp.net mvc

2017年11月14日 星期二

2017/11/14 近況

因為工作的關系 一直在寫前端,已經好一陣子沒回去碰.Net的東西,也很久沒更新blogger,雖然前端變強了...哈哈,回頭翻發現自己之前寫了很多code 原本要拿來寫文章的都難產了,近期應該會想慢慢再去回顧一下並開始寫一些相關blog.

其實前端我也想寫,不過近期前端各種framework版本變化太快,要寫的話可能就後面再來處理,目前還是想惡補一下.net的部分 很多東西以前寫過 現在想講卻一時沒辦法講出很好的解釋.

其實滿有趣的.前端後端 我到底比較偏好哪邊,我是哪邊都無法割捨
回顧的話自己也算有進步了,更多解釋更多邏輯,現在比較能從以前經驗裡找到答案
我很佩服固定在寫blog的各位微軟MVP始終保持熱情,甚至是當作人生中的一個不可或缺的部分,我想朝著你們邁進,也給自己一個期許.

Mars 
2017/11/14



處理好我們每次的Web Api吧 Web Api Handlers Message

什麼是Handlers Message?
message handler is a class that receives an HTTP request and returns an HTTP response.
Typically, a series of message handlers are chained together. The first handler receives an HTTP request, does some processing, and gives the request to the next handler. At some point, the response is created and goes back up the chain. This pattern is called a delegating handler.

這樣做有什麼好處呢
我們從中處理拿到的資料 或是紀錄我們之間傳輸的值 我們就不必傻傻的在每個controller或是其他地方寫相同的邏輯 這時候我們就可以透過這種方式做處理

簡單說如下圖

public class RequestAndResponseLoggerDelegatingHandler : DelegatingHandler
{
    public IDataAccess Data { get; set; }

    protected override async Task SendAsync(
                            HttpRequestMessage request, 
                                 CancellationToken cancellationToken)
    {
        var started = DateTime.UtcNow;
        var requestContent = await request.Content.ReadAsStringAsync();

        var response = await base.SendAsync(request, cancellationToken);

        var responseContent = await response.Content.ReadAsStringAsync();
        await Log(started, request, response, requestContent, responseContent);
        return response;
    }

    private async Task Log(DateTime start, HttpRequestMessage request, 
                             HttpResponseMessage response, string requestContent, 
                                string responseContent)
    {
        var finished = DateTime.UtcNow;           
        var info = new ApiLogEntry(start, finished, requestContent, responseContent, 
                                        request, response);
        Data.Log(info);
    }
}
最後我們在註冊到我剛剛所寫的方法 當然也可以註冊很多層
public static class WebApiConfig
{
    public static void Register(HttpConfiguration config)
    {
        config.MessageHandlers.Add(new RequestAndResponseLoggerDelegatingHandler1());
        config.MessageHandlers.Add(new RequestAndResponseLoggerDelegatingHandler2());

        // Other code not shown...
    }
}
或者是我們在WebApiConfig綁定 特定的路徑 這都是不錯的處理方式
public static class WebApiConfig
{
    public static void Register(HttpConfiguration config)
    {
        config.Routes.MapHttpRoute(
            name: "Route1",
            routeTemplate: "api/{controller}/{id}",
            defaults: new { id = RouteParameter.Optional }
        );

        config.Routes.MapHttpRoute(
            name: "Route2",
            routeTemplate: "api2/{controller}/{id}",
            defaults: new { id = RouteParameter.Optional },
            constraints: null,
            handler: new MessageHandler2()  // per-route message handler
        );

        config.MessageHandlers.Add(new MessageHandler1());  // global message handler
    }
}
參考連結
https://stackoverflow.com/questions/27176329/web-api-request-content-empty 
https://docs.microsoft.com/en-us/aspnet/web-api/overview/advanced/http-message-handlers