Set connection string of membership dynamically from code

前端 未结 2 1199
慢半拍i
慢半拍i 2020-12-19 09:41

I am having a .net web application which uses membership for users validations. The membership has a definition in the web.config file and refer to a connection string in th

相关标签:
2条回答
  • 2020-12-19 10:23

    There is a much easier solution to this.

    1. Create a child class extending SqlMembershipProvider class.
    2. Override Initialize method
    3. Set connectionString property config["connectionString"]
    4. Let the base.Initialize logic continue
    5. In the web.config file, instead of SqlMembershipProvider, use your custom class. (if you give it a different name, make sure to set the defaultProvider attribute to match that)
    0 讨论(0)
  • 2020-12-19 10:31

    The following C# sample code demonstrates how to configure a .NET membership provider programmatically by Jacques L. Chereau. This code requires that you also configure a connection string named MyDatabase

    NameValueCollection objConfig = new NameValueCollection();
    objConfig.Add("connectionStringName", "MyDatabase");
    objConfig.Add("enablePasswordRetrieval", "false");
    objConfig.Add("enablePasswordReset", "true");
    objConfig.Add("requiresQuestionAndAnswer", "true");
    objConfig.Add("applicationName", "MyApp");
    objConfig.Add("requiresUniqueEmail", "true");
    objConfig.Add("maxInvalidPasswordAttempts", "5");
    objConfig.Add("passwordAttemptWindow", "10");
    objConfig.Add("commandTimeout", "30");
    objConfig.Add("passwordFormat", "Hashed");
    objConfig.Add("name", "AspNetSqlMembershipProvider");
    objConfig.Add("minRequiredPasswordLength", "8");
    objConfig.Add("minRequiredNonalphanumericCharacters", "2");
    objConfig.Add("passwordStrengthRegularExpression", "(?=^.{8,25}$)(?=.*\\d)(?=.*[a-z])(?=.*[A-Z])(?=.*[!@#$%^&*()_+}{\\":;'?/>.<,])(?!.*\\s).*$"));
    
    SqlMembershipProvider objSqlMembershipProvider = new SqlMembershipProvider();
    objSqlMembershipProvider.Initialize(objConfig["name"], objConfig);
    MembershipProviderCollection colMembershipProviders = new MembershipProviderCollection();
    colMembershipProviders.Add(objSqlMembershipProvider);
    colMembershipProviders.SetReadOnly();
    
    BindingFlags enuBindingFlags = BindingFlags.NonPublic | BindingFlags.Static;
    Type objMembershipType = typeof(Membership);
    objMembershipType.GetField("s_Initialized", enuBindingFlags).SetValue(null, true);
    objMembershipType.GetField("s_InitializeException", enuBindingFlags).SetValue(null, null);
    objMembershipType.GetField("s_HashAlgorithmType", enuBindingFlags).SetValue(null, "SHA1");
    objMembershipType.GetField("s_HashAlgorithmFromConfig", enuBindingFlags).SetValue(null, false);
    objMembershipType.GetField("s_UserIsOnlineTimeWindow", enuBindingFlags).SetValue(null, 15);
    objMembershipType.GetField("s_Provider", enuBindingFlags).SetValue(null, objSqlMembershipProvider);
    objMembershipType.GetField("s_Providers", enuBindingFlags).SetValue(null, colMembershipProviders);
    

    Assuming you have the following library references:

    using System.Web.Security;
    using System.Collections.Specialized;
    using System.Reflection;
    

    EDIT:

    This method sets the connection string in the Membership providers early enough in the request's lifecycle

    private void SetMembershipProviderConnectionString(string connectionString)
    {
       // Set private property of Membership. Untested code!!
       var connectionStringField = Membership.Provider.GetType().GetField("_sqlConnectionString", BindingFlags.Instance | BindingFlags.NonPublic);
       if (connectionStringField != null)
          connectionStringField.SetValue(Membership.Provider, connectionString);
    
    }
    

    Not tested but calling this method from Global.asax.cs inside Application_PreRequestHandlerExecute does the job.

    0 讨论(0)
提交回复
热议问题