19

関連するすべての質問を読みましたが、何らかの理由でまだ正しい解決策を得ることができません。何かが正しくありませんが、何が原因なのかわかりません。

カスタム メンバーシップ プロバイダーを作成し、web.config を次のように変更しました。

   <membership defaultProvider="MyMemberShipProvider">
      <providers>
        <clear />
        <add name="MyMemberShipProvider" 
                  type="MyNameSpace.MyMemberShipProvider" 
                  connectionStringName="ApplicationServices" 
                  enablePasswordRetrieval="false" 
                  enablePasswordReset="true" 
                  requiresQuestionAndAnswer="false" 
                  requiresUniqueEmail="false" 
                  passwordFormat="Hashed" 
                  maxInvalidPasswordAttempts="5" 
                  minRequiredPasswordLength="6" 
                  minRequiredNonalphanumericCharacters="0" 
                  passwordAttemptWindow="10" 
                  passwordStrengthRegularExpression="" 
                  applicationName="MyApplication" />
      </providers>
    </membership>

私の Initialize メソッドのコードは次のとおりです。

public override void Initialize(string name, NameValueCollection config)
{
    if (config == null)
    { throw new ArgumentNullException("config"); }

    if (string.IsNullOrEmpty(name))
    { name = "MyMemberShipProvider"; }

    if (string.IsNullOrEmpty(config["description"]))
    {
        config.Remove("description");
        config.Add("description", "My Membership Provider");
    }

    base.Initialize(name, config);

    _applicationName = GetConfigValue(config["applicationName"], System.Web.Hosting.HostingEnvironment.ApplicationVirtualPath);
    _maxInvalidPasswordAttempts = Convert.ToInt32(GetConfigValue(config["maxInvalidPasswordAttempts"], "5"));
    _passwordAttemptWindow = Convert.ToInt32(GetConfigValue(config["passwordAttemptWindow"], "10"));
    _minRequiredNonAlphaNumericCharacters = Convert.ToInt32(GetConfigValue(config["minRequiredAlphaNumericCharacters"], "1"));
    _minRequiredPasswordLength = Convert.ToInt32(GetConfigValue(config["minRequiredPasswordLength"], "7"));
    _passwordStregthRegularExpression = Convert.ToString(GetConfigValue(config["passwordStrengthRegularExpression"], String.Empty));
    _enablePasswordReset = Convert.ToBoolean(GetConfigValue(config["enablePasswordReset"], "true"));
    _enablePasswordRetrieval = Convert.ToBoolean(GetConfigValue(config["enablePasswordRetrieval"], "true"));
    _requiredQuestionAndAnswer = Convert.ToBoolean(GetConfigValue(config["requiresQuestionAndAnswer"], "false"));
    _requiredUniqueEmail = Convert.ToBoolean(GetConfigValue(config["requiresUniqueEmail"], "true"));

    string temp_format = config["passwordFormat"];
    if (temp_format == null)
    {
        temp_format = "Hashed";
    }

    switch (temp_format)
    {
        case "Hashed":
            _passwordFormat = MembershipPasswordFormat.Hashed;
            break;
        case "Encrypted":
            _passwordFormat = MembershipPasswordFormat.Encrypted;
            break;
        case "Clear":
            _passwordFormat = MembershipPasswordFormat.Clear;
            break;
        default:
            throw new ProviderException("Password format not supported.");
    }

    ConnectionStringSettings _connectionStringSettings = ConfigurationManager.ConnectionStrings[config["connectionStringName"]];

    if (_connectionStringSettings == null || _connectionStringSettings.ConnectionString.Length == 0)
    {
        throw new ProviderException("Connection String Cannot Be Blank.");
    }

    _connectionString = _connectionStringSettings.ConnectionString;

    //Get Encryption and Decryption Key Information From the Information.

    System.Configuration.Configuration cfg = WebConfigurationManager.OpenWebConfiguration(System.Web.Hosting.HostingEnvironment.ApplicationVirtualPath);
    _machinekey = cfg.GetSection("system.web/machineKey") as MachineKeySection;

    if (_machinekey.ValidationKey.Contains("AutoGenerate"))
    {
        if (PasswordFormat != MembershipPasswordFormat.Clear)
        {
            throw new ProviderException("Hashed or Encrypted passwords are not supported with auto-generated keys.");
        }
    }

}

そして、Initialize メソッドが呼び出されていないことに気付きました。ここで質問を読んだところ、web.config を正しく配線していれば手動で呼び出す必要はないと人々は言っていました。手動で呼び出そうとしましたが、NameValueCollection をキャストしようとしたときに InvalidCastException が発生しました。

誰でも私を助けることができますか?ありがとう

4

8 に答える 8

46

Initialize() を呼び出すには、カスタム メンバーシップ プロバイダーを特定の方法でインスタンス化する必要があります。そのようです:

MyCustomMembershipProvider myProvider = (MyCustomMembershipProvider)Membership.Providers["NameOfMembershipProviderInConfig"];

myProvider を使用すると、カスタム プロバイダーの Initialize() が呼び出されます。

于 2009-10-20T20:14:27.423 に答える
3

プロバイダーが正しく構成されている限り、Initialize メソッドを自動的に呼び出す必要があるのは事実です (コード サンプルにあるようです)。

「手動で呼び出した」方法と、NameValueCollection をキャストしようとした場所を明確にする必要があります。Initialize 内で発生しましたか?

overrideおそらく、Initialize メソッドを表示する必要があります (キーワードを忘れていませんか? ;-)

編集:まあ、 Initialize メソッドも問題ないようです。

注意:Membershipは静的クラスであり、構成されたプロバイダーを遅延してロードおよび初期化します。したがって、プロバイダーの構築とそのメソッドの呼び出しは、またはプロパティInitializeの呼び出しが行われるまで発生しません。他のほとんどの静的メソッド ( など) はこれを行いますが、結論としては、メンバーシップ API が実際に使用されるまで Initialize メソッドは呼び出されません。Membership.ProviderMembership.ProvidersGetUser()

明示的に、またはログイン コントロールなどを使用してこれを行いましたか?

于 2009-03-08T13:37:17.900 に答える
2

私はあなたが何をしたかを理解しようとしています....あなたは次のように進んだと思います:

  • MembershipProvider から継承して MyMembershipProvider というカスタム クラスを作成しました。
  • 構成された web.config (私には正しいように見えます)
  • イベントを発生させて何かを実行する Web コントロールを作成しました (ログインの認証など)。
  • このイベント内で、次のようなことをしようとしましたが、コードのステップ実行中に Initialize() が呼び出されないのはなぜですか?

    MyNameSpace.MyMemberShipProvider msp = new MyNameSpace.MyMemberShipProvider();
    bool IsAuthorized = msp.ValidateUser(txtLogin, txtPass);

解決策: - 代わりにこれを使用してください:

bool IsAuthorised = Membership.ValidateUser(txtLogin, txtPass);
  • 自分でクラスのインスタンスを作成しないでください。代わりに、Membership 静的クラスを使用して .NET に作成させます。これにより、アプリケーションの有効期間を通じて MyMemberShipProvider のインスタンスが 1 つだけ存在することが保証されます。独自のクラスをインスタンス化して Initialize() を呼び出すと、コードはスレッド セーフになりません。
于 2009-05-30T12:28:46.777 に答える
1

大まかな流れとしては、

メンバーシップ クラス (静的クラス) は、SqlMembershipProvider が実装する MembershipProvider (ProviderBase から派生した抽象クラス) を呼び出して使用します (この場合は MyMemberShipProvider)。したがって、データ アクセス コードの実装を MyMemberShipProvider のデータ ソースに与えましたが、そうではありません。自分で初期化を呼び出す必要はありません。

Initialize() は ProviderBase の仮想メソッドです。MyMemberShipProvider を作成するときに、以下のようにオーバーライドします

class MyMemberShipProvider : MembershipProvider
{
    private string _connectionStringName;

    public override void Initialize(string name, NameValueCollection config)
    {
       // see the config parameter passed in is of type NameValueCollection 
       // it gives you the chance to get the properties in your web.config
       // for example, one of the properties is connectionStringName

        if (config["connectionStringName"] == null)
        {
            config["connectionStringName"] = "ApplicationServices";
        }
        _connectionStringName = config["connectionStringName"];
        config.Remove("connectionStringName");          
    }
}

コードを見ずに、NameValueCollection に関係する例外があると言うと、上記のこの方法を思い出します。

これが役に立てば幸いです、レイ。

于 2009-03-08T14:12:03.493 に答える
1

少し前にこの Initialize() メソッドで問題が発生しました。ここに投稿します。誰かの役に立つかもしれません。

カスタム プロバイダーを次のように実装しているとします。

MyEnterprise.MyArea.MyProviders.CustomProvider

そして、あなたが望むのは、プロバイダー実装内にあるメソッド GetUserNameByEmail を使用することです。このメソッドを呼び出すには、次の 2 つの方法があります。

MyEnterprise.MyArea.MyProviders.CustomProvider.GetUserNameByEmail(email)

一方、呼び出しが次の場合、自分で呼び出しているため、 Initialize メソッドは起動しません。

Membership.GetUserNameByEmail(email)

必要に応じて Initialize メソッドが呼び出されます。これは、基本コンストラクターまたは何かにあると思います (これ以上は掘り下げませんでした)。

お役に立てれば。- E.

于 2014-02-21T17:29:51.187 に答える
0

カスタム メンバーシップ プロバイダーは自動的に初期化され、手動で初期化することは意図されていません。

私の実装では、以下のように Initialize メソッドがあります。

public override void Initialize(string name, NameValueCollection config)
{
    if (config == null)
        throw new ArgumentNullException("config");


    // Initialize the abstract base class.
    base.Initialize(name, config);
}

base.Initialize メソッドは、次の例外が定義されている ProviderBase クラスにあることに注意してください。

例外:

  • System.ArgumentNullException: プロバイダーの名前が null です。
  • System.ArgumentException: プロバイダーの名前の長さがゼロです。

  • System.InvalidOperationException: プロバイダーが既に初期化された後で、プロバイダーで System.Configuration.Provider.ProviderBase.Initialize(System.String,System.Collections.Specialized.NameValueCollection) を呼び出そうとしました。

最後の例外はあなたが得るものではありませんか?

于 2009-03-08T14:23:28.210 に答える
0

プロバイダを初期化するコードは次のとおりです。

                System.Collections.Specialized.NameValueCollection adProviderConfig;
                adProviderConfig = membershipSection.Providers[adProviderName].Parameters;
                var _ADProvider = new ActiveDirectoryMembershipProvider();
                _ADProvider.Initialize(adProviderName, adProviderConfig);
于 2014-01-01T12:08:50.397 に答える
0

これにより、初期化が強制的に呼び出されます

private readonly Provider _provider;

public AccountMembershipService(Provider provider)
{
   _provider = provider ?? (Provider) Membership.Provider;
}
于 2013-03-07T14:54:59.783 に答える