Skip Navigation Links » Blog » Possible-pitfalls-of-automatic
  • Possible pitfalls of automatic profile saving that you may encounter!

    by
    Ok, first some basics of ProfileModule.ProfileAutoSaving Event:

    Basically this event is supposed to fire, if a subscription for this event has been made either in global.asax or a custom httpmodule. And if you didnt cancel ContinueWithProfileAutoSave explicitly in this event then it will go ahead and save your profile properties. The default SqlProfileProvider also checks to see if the profile properties are indeed dirty(have changed) before running the save operation. If you have complex properties, then this event will fire always since it wont know how to detect if the profile property has changes.

    This is what the documentation will tell you about this event :

    The ProfileAutoSaving event is raised at the end of page execution if the ProfileManager.AutomaticSaveEnabled property is true. You can access the ProfileAutoSaving event of the ProfileModule class in the Global.asax file for your ASP.NET application using the Profile_ProfileAutoSaving global event, as shown in the example for this topic.

    The SettingsBase.Save method checks the IsDirty property value for each SettingsPropertyValue in the user profile to determine whether properties that are made up of primitive types, strings, or DateTime objects have been changed. The Save method cannot explicitly determine whether a custom class has changed. You can use the ProfileAutoSaving event to determine whether a custom object has been changed and then either to continue with the automatic save for modified objects or to cancel the automatic save if no objects have been modified.

    To cancel the automatic profile save operation, set the ContinueWithProfileAutoSave property to false in the ProfileAutoSaving event; otherwise, set the ContinueWithProfileAutoSave property to true.

    There may be multiple subscribers to the ProfileAutoSaving event. The ProfileModule will use the last value that the ContinueWithProfileAutoSave property is set to. As a result, it is recommended that you explicitly set the ContinueWithProfileAutoSave property in the ProfileAutoSaving event whether you are canceling or continuing with the automatic save, as you may need to overwrite the value set by an earlier subscriber.

    What the documentation does not tell you is that this event only tries to save profiles, only* if you are actually editing the profile of the currently logged in user. After all this is the obvious, how can it know what other profiles you are trying to edit. You couldof edited 10 other different user profiles, so to speak.

    Lets look at a concrete definition of ProfileModule.ProfileAutoSaving Event in global.asax :
    C#
    
                  
    public void Profile_ProfileAutoSaving(object sender, 
    ProfileAutoSaveEventArgs args)
    {
    // pc is a profile of the currently logged in user.
    // If no user is logged in, and anonymous profiles

    // have been enabled

    // then pc holds that anonymous profile.

    ProfileCommon pc = args.Context.Profile;
    }
    This is an important distinction to make and mention, because its very possible that your code is not trying to edit the currently logged in user's profile, eg :
    C#
    
                  
    protected void Page_Load(object sender, EventArgs e)
    {
    if (!Request.IsAuthenticated)
    // login the user
    FormsAuthentication.SetAuthCookie("alessandro", true);
    // get a profile to edit, not current profile but a new profile
    ProfileCommon pc = (ProfileCommon)ProfileBase.Create("newdood1");
    pc.someProperty = "apples";
    // you must call save explicitly for profiles that are

    // not the profile of the currently logged
    // in user or anonymous user.
    //pc.Save();

    }

    You might think Profile_ProfileAutoSaving will fire anyway and save the property someProperty with the value "apples", but it wont. Because when Profile_ProfileAutoSaving fires, you can check the profile in the current context(HttpContext.Current.Profile) and its the profile of the currently logged in user. Not a reference to the profile you edited and this is the only profile that will get saved. Even better lets look at how the HttpContext.Current.Profile property is loaded :

    
                  
    HttpContext.Current.Profile = ProfileBase.Create(
    this
    .Request.IsAuthenticated ? this.User.Identity.Name :
    this
    .Request.AnonymousID, this.Request.IsAuthenticated);

    So, in such cases where the profile you are editing is not the currently logged in user's profile, or anonymous user then you must explicitly call Save() on the profile property after you edit it.

    Now as i write this, it all seems the most obvious, but really when you read the documentation for the first time on this feature, you think and demand that it should automatically save your profile. -->> "automatic profile saving" Smiley

    It's just not as automatic as you may think!

    A penny for your thoughts