You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

.NET Core MVC中GET表单提交时如何保留验证码变量值

解决.NET Core MVC提交表单后验证码值清空的问题

你的问题根源在于HTTP是无状态协议,每次点击提交按钮发起的都是全新请求:

  • ViewData仅在当前请求周期内有效,新请求到来时之前的ViewData数据会被清空,所以var rnumber = ViewData["captcha"];会得到null。
  • 如果randnumber是Controller的类成员变量,每次请求都会创建新的Controller实例,该变量会被重置为默认值(null)。

以下是两种可行的解决方案:

方案一:使用Session存储验证码

Session可以在多个请求间持久化数据,适合存储这类需要跨请求验证的信息。

1. 启用Session

  • .NET 6+(Program.cs):
builder.Services.AddSession(options =>
{
    options.IdleTimeout = TimeSpan.FromMinutes(5); // 设置验证码过期时间
    options.Cookie.HttpOnly = true;
    options.Cookie.IsEssential = true;
});

// 在app.UseRouting()之后添加
app.UseSession();
  • .NET Core 3.x及以前(Startup.cs):
    在ConfigureServices方法添加services.AddSession(...);,在Configure方法的app.UseRouting()之后添加app.UseSession();。

2. 修改后端Index方法

public IActionResult Index(string cap)
{
    // 从Session获取上一次生成的验证码
    var storedCaptcha = HttpContext.Session.GetString("captcha");
    
    // 验证用户输入的验证码
    if (!string.IsNullOrEmpty(cap) && !string.IsNullOrEmpty(storedCaptcha))
    {
        if (cap == storedCaptcha)
        {
            Isvisble = "visible";
        }
    }
    
    // 生成新的验证码并存入Session和ViewData
    var randnumber = RandomString(6);
    HttpContext.Session.SetString("captcha", randnumber);
    ViewData["captcha"] = randnumber;
    
    return View();
}

方案二:使用隐藏字段传递验证码

如果不想依赖Session,可以把验证码存入表单的隐藏字段,提交时和用户输入一起传递到后端。

1. 修改前端cshtml代码

添加一个隐藏字段存储当前验证码:

<form method="post" asp-action="Index">
    <div class="container">
        <h1 class="display-4">Welcome</h1>
        <label for="captcha"><b>Enter chaptcha -  </b></label>
        <label id="lblCapval" for="captchasym"><b>@ViewData["captcha"]</b></label>
        <!-- 新增隐藏字段存储验证码 -->
        <input type="hidden" name="storedCaptcha" value="@ViewData["captcha"]" />
        <input id="txtCapValue" type="text" placeholder="Enter captcha" name="cap" required>
        <br />
        <button class="button" type="submit">Login</button>
    </div>
</form>

注意:这里把请求方法改为post,避免验证码参数暴露在URL中,更安全。

2. 修改后端Index方法

拆分Get和Post方法,逻辑更清晰:

[HttpGet]
public IActionResult Index()
{
    // 首次加载生成验证码
    var randnumber = RandomString(6);
    ViewData["captcha"] = randnumber;
    return View();
}

[HttpPost]
public IActionResult Index(string cap, string storedCaptcha)
{
    // 验证验证码
    if (!string.IsNullOrEmpty(cap) && !string.IsNullOrEmpty(storedCaptcha))
    {
        if (cap == storedCaptcha)
        {
            Isvisble = "visible";
        }
    }
    
    // 生成新的验证码返回给页面
    var randnumber = RandomString(6);
    ViewData["captcha"] = randnumber;
    
    return View();
}

补充:RandomString方法的正确实现

确保你的随机字符串生成方法没有问题,示例如下:

private string RandomString(int length)
{
    const string chars = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789";
    var random = new Random();
    return new string(Enumerable.Repeat(chars, length)
                                .Select(s => s[random.Next(s.Length)])
                                .ToArray());
}

内容的提问来源于stack exchange,提问作者Arvind Chourasiya

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.16 06:55:18