首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> .NET 網頁程式設計 >> ASP.NET 基礎 >> ASP.NET 基礎

ASP.NET「此頁的狀態資訊無效,可能已損壞」ViewState 錯誤根因與解決

     編輯:ASP.NET 基礎

錯誤重現場景

頁面 A (`a.aspx`) 透過 `WebRequest` 呼叫頁面 B (`b.aspx`),將 B 的完整 HTML 回應(含 `

`、``、`` 標籤)直接寫入 A 的 Label。第一次正常,第二次點擊按鈕 PostBack 時拋出:

System.Web.HttpException: 此頁的狀態資訊無效,可能已損壞

程式碼還原

a.aspx.cs - 呼叫端

string url = "https://localhost:1759/textWeb/b.aspx";
string result = ExecUrl(url);
Label1.Text = result; // 直接將完整 HTML 寫入 Label

public string ExecUrl(string url)
{
    var request = WebRequest.Create(url);
    request.Timeout = 20000;
    using (var response = request.GetResponse())
    using (var stream = response.GetResponseStream())
    using (var reader = new StreamReader(stream))
    {
        return reader.ReadToEnd(); // 回傳完整 HTML 文件
    }
}

b.aspx - 被呼叫端

<%@ Page Language="C#" AutoEventWireup="true" CodeBehind="b.aspx.cs" Inherits="TestWeb.b" %>
<html><head><title></title></head><body>
<form id="form1" runat="server">
<div></div></form></body></html>

b.aspx.cs

public partial class b : System.Web.UI.Page
{
    protected void Page_Load(object sender, EventArgs e)
    {
        Response.Write("你好 哈哈!");
    }
}

根因分析:巢狀 Form 標籤破壞 ViewState

  1. 第一次載入:A 頁面 Render 時,Label 輸出 B 的 HTML:
    `...你好 哈哈!
  2. ` → 瀏覽器容錯渲染,畫面正常。
  3. 使用者點擊 A 頁面按鈕 PostBack:瀏覽器提交 A 的 `
    `,包含 ``。
  4. 伺服器端再次執行 ExecUrl:Label 追加第二次 B 的回應:
    `...你好 哈哈!...你好 哈哈!` → **產生巢狀 `
    ` 標籤**。
  5. 瀏覽器再次 PostBack:巢狀 Form 導致表單欄位結構混亂,`__VIEWSTATE` 解析失敗,拋出「狀態資訊無效」。

解決方案

方案一:移除 B 頁面的 ``(最簡單)

<%@ Page Language="C#" %>
<html><head><title></title></head><body>
<!-- 移除 form 標籤 -->
<div></div>
</body></html>

適用於 B 純輸出片段、無 PostBack 需求的情境。

方案二:B 頁面輸出片段,不輸出完整 HTML 結構

protected void Page_Load(object sender, EventArgs e)
{
    Response.Clear();
    Response.Write("你好 哈哈!");
    Response.End(); // 避免輸出 master page / html 標籤
}

方案三:A 頁面使用 iframe / AJAX 載入片段(架構正確)

<!-- a.aspx 前端 -->
<iframe src="b.aspx" frameborder="0" width="100%" height="200"></iframe>

或 jQuery `

` → `$("#target").load("b.aspx #fragment");`

方案四:Web API / ASHX 回傳純資料(現代化)

// b.ashx
public void ProcessRequest(HttpContext context)
{
    context.Response.ContentType = "text/plain";
    context.Response.Write("你好 哈哈!");
}

A 頁面呼叫 `<%= ResolveUrl("~/b.ashx") %>` 取得純文字/JSON,避免 HTML 結構污染。

深度補充:ViewState 驗證機制

  • ASP.NET 預設啟用 ``,ViewState 經 HMAC 簽章。
  • 巢狀 Form 導致 `__VIEWSTATE` 隱藏欄位重複/位置錯位,解碼驗證失敗。
  • 若關閉 `enableViewStateMac="false"`(極不建議)可繞過驗證,但會有安全風險(ViewState 竄改攻擊)。

最佳實務檢查清單

  • [ ] 伺服器端 `WebRequest` 呼叫同域頁面 → 改用 `Server.Execute` / `Server.Transfer` / User Control / Partial View。
  • [ ] 跨系統整合 → 使用 Web API / REST / gRPC 回傳 JSON/XML,前端 AJAX 載入。
  • [ ] 必須抓取外部頁面 HTML → 用 HtmlAgilityPack / AngleSharp 解析提取片段,不要直接注入完整文件。
  • [ ] 確保單一頁面只有一個 ``。
  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved