viewdata与tempdata

      ViewData并不是像网上有些说的那样只在当前视图内有效,他的有效范围是在一个请求的生命周期内,而tempdata生命周期可以延续到紧跟后面的一个请求。

      ViewData只是一个简单的字典,他的生存期跟Controller的生存期一样。请求进来被MvcHandler处理相应Controller被创建,这时Viewdata便存在,直到Controller被销毁,此时Viewdata也将不存在。因此只要是通过View()方法传递的视图名称都可以获得先前保存在其中的值。因为RedirectToAction最终调用的是RedirectToRouteResult()这样将会重新建立Controller因此当进行Redirect时Viewdata将不再可用。

      来看看Tempdata被处理的过程:

protected override void ExecuteCore() {
            TempData.Load(ControllerContext, TempDataProvider);

            try {
                string actionName = RouteData.GetRequiredString("action");
                if (!ActionInvoker.InvokeAction(ControllerContext, actionName)) {
                    HandleUnknownAction(actionName);
                }
            }
            finally {
                TempData.Save(ControllerContext, TempDataProvider);
            }
        }

该方法是Controller的成员就是说每次请求被处理的时候,在action执行前调用TempDataDictionary的Load()方法,

 public void Load(ControllerContext controllerContext, ITempDataProvider tempDataProvider) {
            IDictionary<string, object> providerDictionary = tempDataProvider.LoadTempData(controllerContext);
            _data = (providerDictionary != null) ? new Dictionary<string, object>(providerDictionary, StringComparer.OrdinalIgnoreCase) :
                new Dictionary<string, object>(StringComparer.OrdinalIgnoreCase);
            _initialKeys = new HashSet<string>(_data.Keys);
            __modifiedKeys.Clear();
        }

在该方法中又调用TempDataProvider的LoadTempData()方法将这个回话的上次请求的Tempdata返回并把它从session中移除:

public virtual IDictionary<string, object> LoadTempData(ControllerContext controllerContext) {
            HttpContextBase httpContext = controllerContext.HttpContext;
           
            if (httpContext.Session == null) {
                throw new InvalidOperationException(MvcResources.SessionStateTempDataProvider_SessionStateDisabled);
            }

            Dictionary<string, object> tempDataDictionary = httpContext.Session[TempDataSessionStateKey] as Dictionary<string, object>;

            if (tempDataDictionary != null) {
                // If we got it from Session, remove it so that no other request gets it
                httpContext.Session.Remove(TempDataSessionStateKey);
                return tempDataDictionary;
            }
            else {
                return new Dictionary<string, object>(StringComparer.OrdinalIgnoreCase);
            }
        }

然后开始执行action,在action中可能会把某些信息存放到Tempdata中,这时响应的键值会被添加到Tempdata的__modifiedKeys中。然后执行TempData.Save(ControllerContext, TempDataProvider)

public void Save(ControllerContext controllerContext, ITempDataProvider tempDataProvider) {
            if (_modifiedKeys.Count > 0) {

                // Apply change tracking.
                foreach (string x in _initialKeys) {
                    if (!_modifiedKeys.Contains(x)) {
                        _data.Remove(x);
                    }
                }

                // Store the dictionary
                tempDataProvider.SaveTempData(controllerContext, _data);
                _modifiedKeys.Clear();
            }
        }

在该方法中将把没有修改的上次请求的Tempdata键值对移除然后调用 tempDataProvider.SaveTempData(controllerContext, _data)把Tempdata存放到Session中。

 

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值