隨著 IIS 7.0 內建 URL Rewrite 模組、.NET Framework 3.5 SP1 導入 ASP.NET Routing,開發者常困惑:兩者差異何在?該用哪一個?本文基於 Ruslan Yakushev (IIS 團隊) 經典文章,從管線位置、處理器感知、適用範圍、擴充性、效能五大維度深度比較,提供明確選型指引。
核心架構差異:管線位置決定一切
| 特性 | IIS URL Rewrite | ASP.NET Routing |
| 管線階段 | **極早期** (Pre-Handler),請求進入 Managed 管線前 | **較晚期** (Post-Handler Mapping),`UrlRoutingModule` 在 `PostResolveRequestCache` |
| 對處理器感知 | **完全不知** 後續由誰處理 | **必須知曉** 目標處理器 (Page/Controller/Handler) |
| 客戶端可見性 | **不可見** (伺服器端內部重寫) | 可見 (URL 即路由樣板,雙向生成) |
| 本質角色 | URL **轉換/重寫** 引擎 | 請求 **分派/對應** 系統 |
視覺化流程對比
IIS URL Rewrite 流程
HTTP 請求
→ HTTP.sys (核心模式)
→ IIS 核心認證/壓縮/快取
→ **URL Rewrite 模組** (重寫 URL 路徑、Header、Server Variables)
→ 處理器對應 (Handler Mapping) → ASP.NET / PHP / 靜態檔案 / ...
→ 目標處理器執行 (不知 URL 已被重寫)
ASP.NET Routing 流程
HTTP 請求
→ ... (同上前置階段)
→ 處理器對應 → **UrlRoutingModule** (IHttpModule)
→ 比對 RouteCollection → 選擇 IRouteHandler
→ 取得 IHttpHandler (Page/Controller/自訂)
→ 執行處理器
→ (可選) 路由產生輸出 URL (Html.ActionLink 等)
五大維度詳細比較
| 維度 | IIS URL Rewrite | ASP.NET Routing |
| 適用應用類型 | **所有**:ASP.NET、PHP、ASP、靜態檔案、Node.js、Python... | **僅 .NET Managed**:WebForms、MVC、Web API、WCF、SignalR |
| 管道模式相容性 | **整合/經典** 模式皆完美支援 | **偏好整合模式**;經典模式需 `*.mvc` 副檔名或 `*` 萬用字元對應 |
| 比對依據 | URL 路徑、**網域名、HTTP Header、Server Variables、Query String** | 預設**僅 URL 路徑**;可擴充 `IRouteConstraint` 檢查 Header 等 |
| 動作類型 | 重寫、**HTTP 重導向 (301/302/307)**、自訂狀態碼、**中止請求 (Abort)** | **僅分派至處理器**;重導向需在 Controller/Handler 內自行 `Response.Redirect` |
| 擴充性 | **規則基礎**,透過 Provider 擴充 (官方提供 Rewrite Maps、Custom Providers) | **完全物件導向**:自訂 `IRouteHandler`、`IRouteConstraint`、`RouteBase`、擴充方法 |
| URL 產生能力 | 無 (單向重寫) | **雙向**:`UrlHelper.Action`、`RouteUrl` 依路由表產生 URL |
| 效能特徵 | 原生 C++ 實作,**極低延遲**,規則編譯快取 | Managed 程式碼,**較高延遲** (反射、路由表遍歷),但可快取 |
選型決策矩陣
| 情境 | 推薦方案 | 理由 |
| 舊版 ASP.NET WebForms 想要 SEO 友善 URL | IIS URL Rewrite | 無需修改程式碼、相容經典模式、支援 .html 靜態化 |
| 新專案 ASP.NET Core / MVC / Web API | ASP.NET Core Routing / MVC Routing | 原生整合、雙向 URL 產生、屬性路由、強型別參數綁定 |
| 混合技術棧站點 (PHP + ASP.NET + 靜態) | IIS URL Rewrite | 統一入口、跨技術重寫、集中管理 |
| 需根據 Header/Cookie/GeoIP 重寫 | IIS URL Rewrite | 支援 Server Variables 比對、Rewrite Maps 查表 |
| 需中止惡意請求 / 回傳 403/404 | IIS URL Rewrite | ``、`` |
| WebForms 專案漸進式現代化 | 雙軌並行:Rewrite 處理舊 .html → Routing 處理新功能 | 平滑遷移、互不干擾 |
共存最佳實踐
- **IIS URL Rewrite 負責「邊界」**:靜態化副檔名 `.html` → `.aspx`、舊網址 301 導向、安全防護 (封鎖 IP/UA)
- **ASP.NET Routing 負責「內部」**:Controller/Action 對應、區域、API 版本、參數約束
- **避免衝突**:Rewrite 規則排除 Routing 管理的路徑 (如 `/api/`、`/admin/`)
- **測試驗證**:`Failed Request Tracing` 觀察管線順序、`RouteDebugger` 檢視路由比對
現代化展望:ASP.NET Core 統一管線
- Core 中 `app.UseRewriter()` (Microsoft.AspNetCore.Rewrite) 移植 IIS Rewrite 功能至 Managed 管線
- `app.UseRouting()` + `app.UseEndpoints()` 取代傳統 Routing,支援端點路由、OpenAPI 整合
- **YARP (Yet Another Reverse Proxy)**:新一代反向代理,整合路由、負載平衡、重寫、健康檢查
- 雲端原生:Azure Front Door / Application Gateway / API Management 在邊緣層完成重寫/路由
理解「重寫」與「路由」的本質差異——**前者是透明的 URL 變換,後者是感知處理器的請求分派**——是架構師在遷移、整合、現代化決策時的關鍵判斷力。選對工具,事半功倍;混用得當,新舊共榮。