WebApi - ActionFilter
ActionFilter內建 Action FilterPipeline執行時間記錄統一回傳格式統一錯誤處理輸入驗證 (Model Validation Filter)防止重複送出請求 (Idempotency Filter)ASP.NET Core 中的註冊方式Filter 不要存狀態!summary在 ASP.NET MVC / Web API 裡,Action Filter(動作篩選器)就像是一個「小保全」或「攔截器」。它可以在 Action 執行前 或 Action 執行後 插入邏輯,幫你做額外的事情
把它想像成一場活動
活動開始前檢查門票 → OnActionExecuting
活動結束後收拾場地 → OnActionExecuted
結果要交給觀眾前再整理一次 → OnResultExecuting / OnResultExecuted
活動中如果出意外要處理 → OnException
好處是不用每個 Controller / Action 都重複寫相同程式,邏輯可以集中管理,讓程式更乾淨
123456789101112131415161 ...
MODEL Binding
Model Binding[FromQuery] – 查詢字串[FromRoute] – 路由參數[FromForm] – 表單欄位IFormFile – 檔案上傳[FromBody] – Request Body (JSON)[FromHeader] – HTTP Header[FromServices] – 依賴注入 (DI)案例:複合來源summary這一切其實都圍繞著一個核心:溝通與理解
HTTP 的世界裡,Request 扮演著使用者「開口說話」的角色,而 Model Binding 則像是一位貼心的翻譯員,幫我們把這些話語準確地轉換成程式可以理解的變數或物件
商品搜尋 + 分頁1GET /products?keyword=phone&page=2&pageSize=20
設定
12345678[HttpGet("products")]public IActionResult Search( [FromQuery] string keyword, [FromQuery] int page = 1, [FromQuer ...
WebAPI
WebAPIControllerBase 與 ControllerControllerBase ReturnAttributes自訂 Controller 行為 - 加入 Logging停用自動 400Buffering IEnumerableStreaming IAsyncEnumerableIActionResultIResultTypedResults + Results格式特定的回傳summmary在我眼中,Web API 就像是一座小小的「橋樑」,一邊是使用者,他們可能透過手機、網頁,甚至 IoT 裝置提出需求,一邊則是我們的系統,安靜地等待著請求,準備回應。Controller 與 ControllerBase 就像這座橋樑的守門人,決定了資訊要如何被傳遞、如何被呈現
而我們依據「交付介質」決定地基:HTML 畫面需要完整的 View 引擎支援,而純數據傳輸應保持輕量無負擔,有些橋樑華麗,鋪上了燈飾與雕花(Controller,帶著 View 的世界),適合人群來往、熱鬧非凡;有些橋樑則簡單而純粹(ControllerBase,專注於 API),只管讓資料穩穩地走過去,沒有 ...
RateLimit
超過時回 429 Too Many Requests
限流演算法Fixed Window:最好懂,像「每分鐘 60 次」適合大多數一般 API
Sliding Window:比固定視窗平滑,邊界比較不會突然爆量適合你很在意公平性
Token Bucket:比較像流量池,適合有突發流量的情境很多公開 API 會偏愛這個
Concurrency:保護重 CPU / 重 I/O API例如報表匯出、影像處理、AI 推論
把 RateLimiter 掛進 Program.cs用 AddRateLimiter 註冊政策
用 OnRejected 統一處理超限時的回應
回 429
有 Retry-After 就寫到 header
記結構化 log,後面好做告警
12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970using System.Globalization;u ...
Routing
Routing為什麼需要 Routing?Conventional RoutingMapControllerRoute 順序問題Endpoint RoutingAttribute RoutingOrderBidirection專用路由MVC 可以同時支援 View 和 API保留字案例們Routing 就像是 應用程式的地圖導航。每一個進來的 HTTP Request(請求)都有一個 URL,而 Routing 的工作就是判斷這個 URL 該交給哪段程式(Endpoint)來處理。Endpoint 就像門牌號碼,實際處理請求的程式(例如某個 Controller 的 Action、Razor Page、或 API 方法)。
而 Routing 系統就像導航系統,它會根據你定義的規則,把 Request 送到正確的 Endpoint。更棒的是,Routing 不只單向,它不僅能 URL → Endpoint(使用者輸入網址,找到對應程式)。還能 Endpoint → URL(由程式自動產生正確的網址)
傳統的網站(像早期 ASP / PHP)網址通常長這樣
1/products ...
Model
Model 是系統「知道什麼」的部分,負責描述資料的結構與規則,是整個應用程式的資料核心
🎃 Seed在開發或測試階段,我們常常會希望資料庫一開始就有資料方便測試,這時候就可以使用「Seed」方法。
12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758public class SchoolInitializer{ public static void Initialize(SchoolContext context) { // 確保資料庫存在(如果不存在就建立) context.Database.EnsureCreated(); // 如果已經有學生資料就略過(避免重複加資料) if (context.Students.Any()) { return; } ...
MVC - View
在茂密的森林中,鳥兒會築巢 🐦,蜜蜂會傳花粉 🐝,松鼠會儲存堅果 🐿️。
其實網站開發也一樣,每一個畫面(View)就像是一個生命體,它有自己的「家」(Layout)、需要不同的「資訊傳遞方式」(ViewData / ViewBag),甚至還要有準備完善的「儲藏糧食系統」(ViewModel)。
這篇文章,我們就從自然界的角度,帶你用全新的視角理解:
🐦 Layout 是如何像鳥巢一樣包住每個頁面
🐝 ViewData / ViewBag 如何像蜜蜂快速傳遞資訊
🐿️ ViewModel 為什麼像松鼠預先打包好資料,確保整潔與安全
MVC 的 View,是一個「純粹負責呈現資料的角色」,它不處理邏輯、不處理資料,只專注「怎麼顯示」。
MVC vs Razor Pages(.NET 內建)
MVC View
Razor Page
View 是獨立的、由 Controller 控制
View 和處理邏輯寫在一起(PageModel)
較適合大型應用程式分層設計
較適合小型頁面導向開發
分離更清楚:Controller/M ...
Except
🐛 比較問題在 .NET 裡,Distinct()、Except()、Intersect() 這些方法都依賴物件的 相等性判斷。問題是,自訂類別沒有覆寫 Equals/HashCode 時,預設只會用「參考相等」來判斷。
也就是說,就算兩個 User 物件的內容 (Id, Name) 一模一樣,只要它們是從不同 JSON 反序列化回來的,記憶體位址不同 → 就被視為「不同物件」。結果就是:Except() 無法正確比對出差異。
Dictionary、HashSet、Distinct、Except 這些操作的底層共通點:都要先決定「兩個物件是否相等」、「如何計算 HashCode」。預設情況:C# 類別若沒覆寫,會使用物件的參考相等 → 兩個內容相同的物件仍被視為不同。正確做法:告訴系統如何判斷相等:
IEqualityComparer → 外部策略,適合偶爾需要、不同情境可切換。
IEquatable + Equals/GetHashCode → 內建策略,適合固定規則,讓所有集合操作一律遵守。
本質就是「給集合一個可靠的相等性規則」,否則系統只能退回到「記憶 ...
LINQ - SelectMany
艾倫家的地下室有三個抽屜,每個抽屜都要世界的秘密,我們想將它們都攤開
最外層是地下室
次一層表示抽屜們
下一層表示機密文件
Select
1[[照片,日記],[戰爭情報,國家情報],[美女照]]
使用 Select,我們等於搬著三個抽屜離開
SelectMany
1[照片,日記,戰爭情報,國家情報,美女照]
SelectMany,讓我們每一樣任務物品都可以輕易地取出排列整齊,還可以偷偷把美女照藏起來
🐛 如果世界上沒有 SelectMany今天我們有這樣一個集合,有 7 個老師,每位老師有 3 名學生,共 21 個學生
123456789101112List<Teacher> teachers = new List<Teacher> { new Teacher("Allen",new List<Student>{ new Student(100),new Student(90),new Student(80) }), new ...
Extension Method
ExtensionIEnumerable 擴充問題把「由右而左」改寫成「由左到右」字串反轉字串移除特定字元DI 的語法糖:建立可讀的註冊 APIAntiPattern 1 - 綁死生命週期物件AntiPattern 2 - IEnumerable 上做副作用(寄信、寫檔、打 API)AntiPattern 3 - 擴充承載過多業務意義AntiPattern 4 - 在 object 上加「萬能」擴充(例如 ToJson())AntiPattern 5 - 擴充方法包「重策略」:Retry、Timeout、Circuit BreakerSummary語言層級的能力讓我們在不修改原本 source code 的前提下,就能為 class 增加新 method,寫起來像 instance method,C# 編譯器幫你 static method + syntactic sugar
開放封閉原則(OCP)對「不能改、也不該改」的型別開放擴充,例如 .NET Framework、第三方 package、legacy code
123456789101112131415161718void Ma ...









