Copied to clipboard

Flag this post as spam?

This post will be reported to the moderators as potential spam to be looked at


  • Jonathan 19 posts 101 karma points
    Jan 07, 2015 @ 12:27
    Jonathan
    0

    Major performance issues when logged in as member

    Hi!

    We encountered a major performance issue in Forms on Umbraco 7.2.1. and hope this can be resolved in a short term because it's interfering big time with our development and deadline.

    summary: when logged in as a member there is an exponential growth of calls to the database compared to unauthenticated.

    result: We're building a rather large form with multiple pages and many fields. When logged in as a member, Opening the form and navigation through the form steps takes up to 40-60 seconds per click.


    To reproduce it we installed a clean Umbraco installation and installed Forms with the help of the install button in the Forms section. We created a simple form with three steps (pages) and two text input field on each page. We created a member and a simple login form with the help of:

    @using (Html.BeginUmbracoForm<UmbLoginController>("HandleLogin"))
    

    We used ANTS profiler. See the following two screenshots, especially the hit count column. This is only for a simple form with 6 fields. You can imagine what wil happen with larger forms with more fields.

    The first screenshot reflects the calls when you're logged in as a member. The second screenshot reflects if you're unauthenticated.

    Hope there is a solution or quick fix. Thanks in advance!


    Logged in as member


    Unauthenticated

  • Richard Barg 358 posts 532 karma points
    Jan 12, 2015 @ 20:13
    Richard Barg
    0

    My sympathies for your plight. We have been there, not for this issue, but for others.

  • Jonathan 19 posts 101 karma points
    Jan 13, 2015 @ 15:14
    Jonathan
    101

    In the meantime we have developed a quick fix which might come in handy for people who also experience this issue.

    The issue

    Using DotTrace we analysed the following snapshot:

    DotTrace snapshot

    We see that the ParsePlaceHolders is being requested a lot (in the Build(Form) method in 4 foreach loops). And the Membership.GetUser is requested foreach ParsePlaceHolder.

    public static string ParsePlaceHolders(HttpContext Context, Umbraco.Forms.Core.Record record, string value)
    {
      string str = StringHelper.(DictionaryHelper.GetText(value), Context);
      if (record != null)
        str = StringHelper.(str, record);
      if (Member.InUmbracoMemberMode())
      {
        HttpContext.Current.Trace.Write("In member mode");
        str = record == null || record.MemberKey == null ? (Context == null || Context.Session == null || Context.Session["ContourMemberKey"] == null ? (Context == null || Context.User == null || !Context.User.Identity.IsAuthenticated || Membership.GetUser() == null ? StringHelper.(str, (object) 0) : StringHelper.(str, Membership.GetUser().ProviderUserKey)) : StringHelper.(str, Context.Session["ContourMemberKey"])) : StringHelper.(str, (object) record.MemberKey);
      }
      return str;
    }
    

    The Quick fix

    Create a new class that inherits MembersMembershipProvider and overrides the GetUser(string, bool) method.

    public class CustomMembersMembershipProvider : MembersMembershipProvider
    {
        public override System.Web.Security.MembershipUser GetUser(string username, bool userIsOnline)
        {
            //get the user from HttpContext Items if available.
            if (HttpContext.Current.Items.Contains(username))
            {
                return HttpContext.Current.Items[username] as System.Web.Security.MembershipUser;
            }
    
            var user = base.GetUser(username, userIsOnline);
            //Only cache if the authenticated user is equal to the user that needs to be received. (prevents misuse of HttpContext Items)
            if (HttpContext.Current.User.Identity.Name == username)
            {
                //we cache the user in the HttpContext Items to prevent roundtripping to the database.
                HttpContext.Current.Items.Add(username, user);
            }
            return user;
        }
    }
    

    Also, override the existing configuration setting for UmbracoMembershipProvider in the web.config /configuration/system.web/membership/providers to use your class (change the namespace and library name):

    <add name="UmbracoMembershipProvider" type="[YourLibrary.NameSpace].CustomMembersMembershipProvider, [YourLibrary]" minRequiredNonalphanumericCharacters="0" minRequiredPasswordLength="4" useLegacyEncoding="true" enablePasswordRetrieval="false" enablePasswordReset="true" requiresQuestionAndAnswer="false" defaultMemberTypeAlias="Member" passwordFormat="Hashed"  />
    
  • Comment author was deleted

    Jan 22, 2015 @ 15:05

    Thanks for reporting, has been fixed and will be in new release 4.0.1 coming tomorrow

  • This forum is in read-only mode while we transition to the new forum.

    You can continue this topic on the new forum by tapping the "Continue discussion" link below.

Please Sign in or register to post replies