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

ASP.NET MVC中如何在Application_start加载主数据及登录时缓存用户数据?

在ASP.NET MVC中实现全局主数据与用户专属数据的缓存加载

这两个需求刚好对应全局应用级缓存和用户会话/专属级缓存,咱们分开来实现就很清晰:

一、Application_Start加载全局主数据(应用生命周期内共享)

ASP.NET的Application_Start事件是应用程序启动时仅执行一次的入口,非常适合加载那些不常变化、全应用共享的主数据(比如字典表、系统配置项这类)。这里推荐用HttpRuntime.Cache来存储,比传统的Application对象更灵活,支持过期策略、依赖项等特性。

实现步骤:

  1. 在Global.asax.cs的Application_Start方法中添加加载逻辑:
protected void Application_Start()
{
    AreaRegistration.RegisterAllAreas();
    FilterConfig.RegisterGlobalFilters(GlobalFilters.Filters);
    RouteConfig.RegisterRoutes(RouteTable.Routes);
    BundleConfig.RegisterBundles(BundleTable.Bundles);

    // 加载全局主数据并缓存
    LoadGlobalMasterData();
}

private void LoadGlobalMasterData()
{
    // 从数据库/配置文件读取主数据,这里模拟示例数据
    var globalMasterData = new List<MasterItem>
    {
        new MasterItem { Id = 1, Name = "产品类别A" },
        new MasterItem { Id = 2, Name = "产品类别B" }
    };

    // 存入HttpRuntime缓存,设置永不过期(如果数据不会变更),也可添加过期策略
    HttpRuntime.Cache.Insert(
        key: "GlobalMasterData",
        value: globalMasterData,
        dependencies: null,
        absoluteExpiration: Cache.NoAbsoluteExpiration,
        slidingExpiration: Cache.NoSlidingExpiration,
        priority: CacheItemPriority.NotRemovable,
        onRemoveCallback: null
    );
}
  1. 在任意控制器/视图中读取缓存数据:
// 控制器中读取
var globalData = HttpRuntime.Cache["GlobalMasterData"] as List<MasterItem>;

// 视图中读取(推荐先在控制器处理后传递,也可直接读取)
@{
    var globalData = HttpRuntime.Cache["GlobalMasterData"] as List<MasterItem>;
}

小提示:如果主数据需要定期更新,可以给缓存添加绝对过期时间,或者开发一个手动刷新接口,调用时重新加载数据覆盖缓存即可。

二、用户登录时加载专属数据(用户会话/全局共享)

用户登录成功后,我们需要加载该用户的专属数据(比如个人配置、权限列表),这里分两种常用场景:

  • 场景1:仅当前会话可用 → 用Session存储
  • 场景2:同一用户的多个会话共享 → 用HttpRuntime.Cache结合用户ID作为唯一键

实现步骤(以登录后缓存为例):

  1. 在AccountController的Login方法中,验证用户成功后加载并缓存数据:
[HttpPost]
[AllowAnonymous]
[ValidateAntiForgeryToken]
public async Task<ActionResult> Login(LoginViewModel model, string returnUrl)
{
    if (!ModelState.IsValid)
    {
        return View(model);
    }

    // 验证用户身份
    var result = await SignInManager.PasswordSignInAsync(model.Email, model.Password, model.RememberMe, shouldLockout: false);
    switch (result)
    {
        case SignInStatus.Success:
            // 登录成功,加载用户专属数据
            var userId = User.Identity.GetUserId();
            LoadUserData(userId);
            return RedirectToLocal(returnUrl);
        // 其他状态分支省略...
        default:
            ModelState.AddModelError("", "无效的登录尝试。");
            return View(model);
    }
}

private void LoadUserData(string userId)
{
    // 从数据库读取用户专属数据,模拟示例数据
    var userData = new UserProfile
    {
        UserId = userId,
        Nickname = "张三",
        Permissions = new List<string> { "编辑内容", "查看报表" }
    };

    // 场景1:存入Session,仅当前会话可用
    Session["UserData"] = userData;

    // 场景2:存入HttpRuntime.Cache,同一用户多会话共享,用用户ID作为键的一部分
    HttpRuntime.Cache.Insert(
        key: $"UserData_{userId}",
        value: userData,
        dependencies: null,
        absoluteExpiration: DateTime.Now.AddHours(2), // 2小时过期,可按需调整
        slidingExpiration: Cache.NoSlidingExpiration,
        priority: CacheItemPriority.Default,
        onRemoveCallback: null
    );
}
  1. 在后续请求中读取用户数据:
// 读取Session中的数据
var userDataFromSession = Session["UserData"] as UserProfile;

// 读取Cache中的数据(需要当前用户ID)
var userId = User.Identity.GetUserId();
var userDataFromCache = HttpRuntime.Cache[$"UserData_{userId}"] as UserProfile;

小提示:如果用户注销,记得清理对应的缓存项,比如在AccountController的Logout方法中添加:

public ActionResult Logout()
{
    var userId = User.Identity.GetUserId();
    Session.Remove("UserData");
    HttpRuntime.Cache.Remove($"UserData_{userId}");
    AuthenticationManager.SignOut();
    return RedirectToAction("Index", "Home");
}

这样就能完美实现你要的两个需求啦:全局主数据在应用启动时加载一次,全应用共享;用户数据在登录时加载,缓存后供后续请求使用。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.21 07:42:04