HTTP 本質是無狀態協定,每次請求對伺服器而言都是獨立的。ASP.NET 提供多種「狀態管理」機制,讓開發者能在頁面跳轉、Postback 或跨請求間保留資料。選擇正確的方法,關係到安全性、效能、資料壽命、開發複雜度。本文系統整理九大主流傳值方式,並依「跳轉情境」給出選型建議。
| 方法 | 儲存位置 | 資料型別 | 生命週期 | 安全性 | 適用場景 | 缺點/注意 |
|---|---|---|---|---|---|---|
1. QueryStringResponse.Redirect("B.aspx?id=123") |
URL 參數 | 字串 | 單次請求 | 低(明文、可竄改) | 非敏感、少量、需書籤/分享的參數 | 長度限制 ~2KB;不可傳物件 |
2. 隱藏欄位<asp:HiddenField> |
頁面 HTML | 字串 | 單次 Postback | 低(檢視原始碼可見) | 同頁 Postback 需保留的簡單值 | 增加頁面大小;防火牆可能攔截大量資料 |
3. ViewStateViewState["Key"] = val |
頁面隱藏欄位 (__VIEWSTATE) | 可序列化物件 | 同頁多次 Postback | 中(Base64 + MAC 驗證) | 控制項狀態、同頁跨 Postback 保留資料 | 過大拖慢載入;不可跨頁 |
4. CookieResponse.Cookies["k"]="v" |
客戶端瀏覽器 | 字串 | 可設定過期日 | 低(明文、用戶可禁用/刪除) | 記住登入帳號、個人化偏好、追蹤匿名用戶 | 單 Cookie 4KB、域限制 20~50 個;不可存敏感資訊 |
5. ApplicationApplication["Key"] = val |
伺服器記憶體 (進程級) | 任意物件 | 應用程式存活期間 | 中(伺服器端) | 全域唯讀設定、快取公共資料(如字典表) | 佔用記憶體;重啟 IIS 資料遺失;需 Lock/Unlock 同步 |
6. SessionSession["Key"] = val |
伺服器記憶體 / SQL / Redis | 任意物件 | 工作階段 (預設 20 分鐘閒置) | 高(伺服器端,SessionID 僅識別) | 用戶登入資訊、購物車、多步驟精靈暫存 | 佔用伺服器資源;Web Farm 需共享 Session (Redis/SQL) |
7. 靜態類別屬性MyStaticClass.Prop = val |
伺服器記憶體 (AppDomain 級) | 任意物件 | 應用程式存活期間 | 中 | 極簡單的跨頁共享、單例服務 | 非執行緒安全;重啟遺失;單元測試困難 |
8. Server.TransferServer.Transfer("B.aspx", true) |
伺服器端記憶體 (同一 Request) | 表單欄位、QueryString、前頁屬性 | 單次轉向 | 高(不經瀏覽器) | 同伺服器頁面間無縫轉向、保留原 Request 內容 | 網址列不變;僅限同應用程式;瀏覽器重整會重送目標頁 |
9. CacheCache.Insert("k", v, dep, ...) |
伺服器記憶體 | 任意物件 | 依相依/過期/回呼移除 | 高 | 高頻讀取、低頻寫入的資料快取(報表、下拉選單) | API 較複雜;誤用降低效能;需處理 Null 回傳 |
web.config 設定 mode="Custom" customProvider="Redis" 即可水平擴展。CacheDependency (檔案/資料庫/其他 Cache Key) 自動失效,避免髒讀。Response.Redirect + Session/Cache。// QueryString
Response.Redirect($"Detail.aspx?id={id}&cat={Server.UrlEncode(cat)}");
// 目標頁
var id = Request.QueryString["id"];
// Session
Session["Cart"] = cartList;
var cart = Session["Cart"] as List<CartItem>;
// Cache (含相依性自動失效)
Cache.Insert("ProductList", list, new SqlCacheDependency("connStr", "Products"));
// Cookie (加密)
var cookie = new HttpCookie("Pref", JsonSerializer.Serialize(pref)) { Expires = DateTime.Now.AddDays(30), HttpOnly = true, Secure = true };
Response.Cookies.Add(cookie);
// Server.Transfer (來源頁)
public string UserName { get; set; } // 公開屬性供目標頁存取
Server.Transfer("Target.aspx", true);
// 目標頁
var src = Context.Handler as SourcePage;
if (src != null) lbl.Text = src.UserName;
ASP.NET 提供豐富的狀態管理工具箱,關鍵在於根據資料敏感度、大小、生命週期、部署架構 選擇最合適的一種(或組合)。現代雲端部署建議:Session → Redis、Cache → IDistributedCache、敏感參數 → 加密 JWT/Token,並逐步從 Web Forms 遷移至 ASP.NET Core MVC / Razor Pages / Blazor,獲得更乾淨的關注點分離與測試性。