Server cannot modify cookies after HTTP headers have been sent, how Fix?

旧时模样 提交于 2020-01-24 02:24:47

问题


i want to auto login my users at page_load of masterpage if UserName and Password exist in cookies!
so i wrote the code below :

        protected void Page_Load(object sender, EventArgs e)
        {
            LoadDataFromCookieIfExistAndLogin();
        }

private void LoadDataFromCookieIfExistAndLogin()
{
    string Query = Request.Url.Query.ToString();
    string[] Ar_Query = new string[2];
    string[] splitter = { "%2f" };
    Ar_Query = Query.Split(splitter, System.StringSplitOptions.None);
    string[] Ar_new_Query = new string[2];
    int minLength = Math.Min(Ar_Query.Length, Ar_new_Query.Length);
    Array.Copy(Ar_Query, Ar_new_Query, minLength);
    if (string.IsNullOrEmpty(Ar_new_Query[1]))
    {
        Ar_new_Query[1] = string.Empty;
    }

    if ((Request.QueryString["ReturnURL"] != null) && (Ar_new_Query[1].ToString().ToUpper() == "ADMIN"))
    {
        Session.Clear();
        FormsAuthentication.SignOut();
    }
    else if ((Request.QueryString["ReturnURL"] != null) && (Ar_new_Query[1].ToString().ToUpper() == "ELMAH.AXD"))
    {
        Session.Clear();
        FormsAuthentication.SignOut();
    }
    else
    {
        HttpCookie Situation_Cookie = Request.Cookies["Situation"];
        if (Situation_Cookie != null)
        {
            if (Situation_Cookie["Login"] == "Yes")
            {
                HttpCookie Data_Cookie = Request.Cookies["Data"];
                if (Data_Cookie != null)
                {
                    string UserName = Data_Cookie["UserName"].ToString();
                    string PassWord = ata_Cookie["PassWord"].ToString();

                    string HashedPass = FormsAuthentication.HashPasswordForStoringInConfigFile(PassWord, "MD5");
                    DataSet dsUsers = DataLayer.Users.SelectRowForLogin_FromCookie(UserName, HashedPass);
                    if (dsUsers.Tables["Users"].Rows.Count > 0)
                    {
                        DataRow drUsers = dsUsers.Tables["Users"].Rows[0];

                        if (Session["User_ID"] == null)
                        {
                            Session["UserName"] = UserName;
                            Session["Password"] = PassWord;
                            Session["User_ID"] = drUsers["ID"].ToString();
                            Session["UserType_ID"] = drUsers["UserType_ID"].ToString();
                            DataLayer.OnlineUsers.UpdateRow_UserID_By_SessionID(
                                                                                 Session["User_ID"],
                                                                                 Session.SessionID);
                        }
                        if (!HttpContext.Current.User.Identity.IsAuthenticated)
                        {
                            FormsAuthentication.SetAuthCookie(drUsers["ID"].ToString(), true);
                        }
                    }
                }
            }
        }
    }
}

also for understanding my login codes i am using RoleProvider Like Below :

  using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Web;
    using System.Web.Security;
    using System.Data;

    namespace NiceFileExplorer.Classes
    {
        public class NiceFileExplorerRoleProvider : RoleProvider
        {
            public override void AddUsersToRoles(string[] usernames, string[] roleNames)
            {
                throw new NotImplementedException();
            }

            public override string ApplicationName
            {
                get
                {
                    throw new NotImplementedException();
                }
                set
                {
                    throw new NotImplementedException();
                }
            }

            public override void CreateRole(string roleName)
            {
                throw new NotImplementedException();
            }

            public override bool DeleteRole(string roleName, bool throwOnPopulatedRole)
            {
                throw new NotImplementedException();
            }

            public override string[] FindUsersInRole(string roleName, string usernameToMatch)
            {
                throw new NotImplementedException();
            }

            public override string[] GetAllRoles()
            {
                throw new NotImplementedException();
            }

            //public override string[] GetRolesForUser(string username)
            public override string[] GetRolesForUser(string User_ID)
            {
                string[] UserTypes = new string[1];
                DataSet dsUser = DataLayer.Users.SelectRowWithUserTypeInfo(int.Parse(User_ID));
                if (dsUser.Tables["Users"].Rows.Count > 0)
                {
                    DataRow drUser = dsUser.Tables["Users"].Rows[0];
                    UserTypes[0] = drUser["Name"].ToString();
                }
                if (User_ID == "-255")
                {
                    UserTypes[0] = "Administrators";
                }
                return UserTypes;
            }

            public override string[] GetUsersInRole(string roleName)
            {
                throw new NotImplementedException();
            }

            public override bool IsUserInRole(string username, string roleName)
            {
                throw new NotImplementedException();
            }

            public override void RemoveUsersFromRoles(string[] usernames, string[] roleNames)
            {
                throw new NotImplementedException();
            }

            public override bool RoleExists(string roleName)
            {
                throw new NotImplementedException();
            }
        }

}

sometimes i have the error below :

System.Web.HttpException: Server cannot modify cookies after HTTP headers have been sent.

System.Web.HttpUnhandledException (0x80004005): Exception of type 'System.Web.HttpUnhandledException' was thrown. ---> System.Web.HttpException (0x80004005): Server cannot modify cookies after HTTP headers have been sent.
   at System.Web.HttpCookieCollection.Add(HttpCookie cookie)
   at System.Web.Security.FormsAuthentication.SetAuthCookie(String userName, Boolean createPersistentCookie, String strCookiePath)
   at NiceFileExplorer.en.Site1.Page_Load(Object sender, EventArgs e)
   at System.Web.Util.CalliHelper.EventArgFunctionCaller(IntPtr fp, Object o, Object t, EventArgs e)
   at System.Web.UI.Control.LoadRecursive()
   at System.Web.UI.Control.LoadRecursive()
   at System.Web.UI.Page.ProcessRequestMain(Boolean includeStagesBeforeAsyncPoint, Boolean includeStagesAfterAsyncPoint)
   at System.Web.UI.Page.HandleError(Exception e)
   at System.Web.UI.Page.ProcessRequestMain(Boolean includeStagesBeforeAsyncPoint, Boolean includeStagesAfterAsyncPoint)
   at System.Web.UI.Page.ProcessRequest(Boolean includeStagesBeforeAsyncPoint, Boolean includeStagesAfterAsyncPoint)
   at System.Web.UI.Page.ProcessRequest()
   at System.Web.UI.Page.ProcessRequest(HttpContext context)
   at System.Web.HttpApplication.CallHandlerExecutionStep.System.Web.HttpApplication.IExecutionStep.Execute()
   at System.Web.HttpApplication.ExecuteStep(IExecutionStep step, Boolean& completedSynchronously)

it seems the problem is for the line below :

FormsAuthentication.SetAuthCookie(drUsers["ID"].ToString(), true);

what this error mean and how can i prevent it?


回答1:


"System.Web.HttpException: Server cannot modify cookies after HTTP headers have been sent."

That error indicates that you are trying modify cookies after the http response is completed.

I think the problem is you trying to modify the cookies after executing FormsAuthentication.SignOut().

As per MSDN, this what happens when SignOut() method is called

When the SignOut method is called, a redirect to the application's login page is made by calling the Redirect method with the endResponse parameter set to false. The redirect does not take place until the current page has finished executing, so additional code can be run. If the code does not contain an explicit redirect to another page, the user is redirected to the login page configured in the application's configuration file.

So you are trying to modify the cookies after redirection happens. You can avoid this error by setting the cookie value before redirection.




回答2:


If you are using ASP.Net standard form authentication, this feature is available for Form authentication if you use persistent cookies. See MSDN article here. Check the 'Creating the Forms Authentication Cookie' section of the document.

You do not need to keep username\password combination is cookie. It's not a good practice as anyone can sniff this username\password from the cookie. I strongly recommend that you read the above article to understand how Form authentication work.




回答3:


for quick testing I have cleared my browser history and works fine on my end..



来源:https://stackoverflow.com/questions/8287331/server-cannot-modify-cookies-after-http-headers-have-been-sent-how-fix

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!