【轉】jquery文件上傳插件uploadify在.NET中session丟失的解決方案

基於jQuery和Flash的多文件上傳插件uploadify的確很好用,具體配置和使用方法見之前的一篇文章: 《一款基於jQuery的文件上傳插件(.NET版)》。但今天在用這個插件的時候遇到了一個很是頭痛的問題,上傳文件的時候,我後臺的session忽然都丟失了,我進入調試去查看session變量發現爲null。悲劇,難道我不能用這個插件了嗎?固然不可能,這麼好的東西固然要用起來,因而就去找解決方案了。

終於,答案有了,原來通常狀況下(非IE瀏覽器),由於諸如uploadify,swfupload採用的都是flash客戶端,這樣它們產生的useragent與用戶使用瀏覽器的 user-agent必然不一樣。因此,雖然用戶登陸了你的系統產生了一個session,可是當觸發上傳程序時會產生另外一個session(在上述 useragent選項開啓的狀況下)。因此,不是session丟失了,而是當你上傳文件時,CI爲uploadify另外建立了一個session。好了,既然找到問題的根源,咱們就想辦法讓服務器在session判空以前將session值手動傳遞過去。html

在ASP.NET中的解決方案以下:web

在上傳的那個頁面中加入如下代碼瀏覽器


var auth = "<% = Request.Cookies[FormsAuthentication.FormsCookieName]==null ? string.Empty : Request.Cookies[FormsAuthentication.FormsCookieName].Value %>" ;
var ASPSESSID = "<%= Session.SessionID %>" ;

而後初始化插件的代碼改爲以下形式服務器

$( "#fileInput1" ).uploadify({
             'uploader' : '/Scripts/uploader/uploadify.swf' ,
             'method' : 'GET' ,
             'script' : '/mystudio/GoUploadAvatar' ,
             'cancelImg' : '/Scripts/uploader/cancel.png' ,
             'sizeLimit' : 2048000,
             'multi' : false ,
             'fileDesc' : '選擇jpg,png,gif' ,
             'fileExt' : '*.jpg;*.png;*.gif' ,
   
             'onComplete' : function (e, queueId, fileObj, response, data) {
   
             },
            'onSelectOnce' : function (e, data) {
                 $( '#fileInput1' ).uploadifySettings( 'scriptData' , { 'ASPSESSID' : ASPSESSID, 'AUTHID' : auth });
             }
  });


注意上面有一句,很關鍵cookie


$( '#fileInput1' ).uploadifySettings( 'scriptData' , { 'ASPSESSID' : ASPSESSID, 'AUTHID' : auth });

接下來咱們必須在服務端Session判空並建立以前,將傳遞過來的SessonID強制賦給當前請求的Cookies,這樣服務端就認爲仍是原來的Session傳遞過來了。具體作法咱們能夠在Global.asax文件中加入以下代碼session

protected void Application_BeginRequest( object sender, EventArgs e)
         {
             /* we guess at this point session is not already retrieved by application so we recreate cookie with the session id... */
             try
             {
                 string session_param_name = "ASPSESSID" ;
                 string session_cookie_name = "ASP.NET_SessionId" ;
  
                 if (HttpContext.Current.Request.Form[session_param_name] != null )
                 {
                     UpdateCookie(session_cookie_name, HttpContext.Current.Request.Form[session_param_name]);
                 }
                 else if (HttpContext.Current.Request.QueryString[session_param_name] != null )
                 {
                     UpdateCookie(session_cookie_name, HttpContext.Current.Request.QueryString[session_param_name]);
                 }
             }
             catch
             {
             }
  
             try
             {
                 string auth_param_name = "AUTHID" ;
                 string auth_cookie_name = FormsAuthentication.FormsCookieName;
  
                 if (HttpContext.Current.Request.Form[auth_param_name] != null )
                 {
                     UpdateCookie(auth_cookie_name, HttpContext.Current.Request.Form[auth_param_name]);
                 }
                 else if (HttpContext.Current.Request.QueryString[auth_param_name] != null )
                 {
                     UpdateCookie(auth_cookie_name, HttpContext.Current.Request.QueryString[auth_param_name]);
                 }
  
             }
             catch
             {
             }
         }
  
         private void UpdateCookie( string cookie_name, string cookie_value)
         {
             HttpCookie cookie = HttpContext.Current.Request.Cookies.Get(cookie_name);
             if ( null == cookie)
             {
                 cookie = new HttpCookie(cookie_name);
             }
             cookie.Value = cookie_value;
             HttpContext.Current.Request.Cookies.Set(cookie);
         }



這時候你訪問上傳文件的那個頁面時可能會報「會話狀態已建立一個會話 ID,但因爲響應已被應用程序刷新而沒法保存它」的錯誤,這時,你能夠在web.config文件改變session的存儲方式,通常默認都是以 「inproc」存儲的,咱們把它改爲stateserver模式,即在system.web節點下加入app


< sessionstate mode = "StateServer" stateconnectionstring = "tcpip=127.0.0.1:42424" timeout = "30" ></ sessionstate >
相關文章
相關標籤/搜索