3

私はこれがコンパイルされることを知っていますが、私の質問は、それは良い考えですか?なぜそれが良い考えではないのか、私は主に興味があります。さらに良いことに、がの場合、代替手段はありますが、それSomeStaticClass@Componentの静的メンバーでなければなりませんMyComponent。私の理解では、Springautowire静的メンバーを使用するための設計が貧弱です。私が読んだものに基づいて、私はまだその理由を完全には理解していません。私が次を持っているとしましょう:

@Component
public final class MyComponent {

  private static SomeStaticClass someStaticClass;

  @Autowired
  MyComponent(SomeStaticClass someStaticClass) {
    MyComponent.someStaticClass = someStaticClass;
  }

}
4

6 に答える 6

8

それが悪い設計であるいくつかの理由:

  • static可変フィールドは一般的に悪い設計です

  • テストが難しくなります - このフィールドが設定されると、次のテストでも設定されたままになり、潜在的な相互依存関係が作成される可能性があります

  • MyComponentそれぞれが異なるの 2 つのインスタンスが必要な場合はどうすればよいでしょうSomeStaticClassか。混沌。

  • staticフィールドまたはセッターの自動配線を介して値を注入することはできません。明示的に禁止されています。それには理由があるはずです。

  • なぜそれが必要なのですか?にstaticメソッドはありMyComponentますか? なんで?

  • MyComponent.staticMethod()上記が当てはまる場合、コンストラクターがそのフィールドを初期化する前に呼び出しを防ぐにはどうすればよいですか? Spring の要点は、完全に実装された安全な Bean を返すことです

于 2012-12-18T19:40:37.580 に答える
2

Spring Bean はデフォルトでシングルトンであるためsomeStaticClass、インスタンス フィールドを作成し、コードをクリーンでテスト可能な状態に保ちます。someStaticClass静的である理由はありません。非最終的な静的フィールドは臭いです。

于 2012-12-18T19:38:36.500 に答える
0

設計上の欠陥にもかかわらず、静的変数をコンテキストで初期化する必要がある場合は、できるだけ早く実行する必要があります。

いくつかの可能性があり、互換性のあるものは次の@Autowiredとおりです。

  • クラスに実装さApplicationListenerせるか、 を使用しApplicationListenerて更新させます。
  • メソッドをオーバーライドonRefresh()してリフレッシュします。
  • Bean 定義を最初のものにします。シングルトンは、登録されたのと同じ順序でインスタンス化されます。
  • 他の初期にインスタンス化された Bean で使用depends-onします。MessageSource は良い機会です。

かなり暗いですが、本当に必要な場合は...

他のオプションは、BeanFactoryPostProcessor を記述し、静的フィールドを手動で注入することです

于 2012-12-18T22:09:54.373 に答える
0

@Component基本的に、Bean はデフォルトでシングルトンであることを意味します。そのため、静的な依存関係を持つことはあまり意味がありません。しかし、あなたが言ったようにコンパイルされます。

于 2012-12-18T19:38:35.073 に答える
0

デフォルトでは、すべての Spring Bean はシングルトンであるためstatic、クラスを設計するときにここは必要ありません。

于 2012-12-18T19:38:54.700 に答える
0

ライフサイクルが異なるため、これは不適切な設計です。静的変数は、一度初期化されると、アプリケーション コンテキストが閉じられても存在し続けます。

もう 1 つの不一致は、複数のアプリケーション コンテキストが存在する可能性があることです。SomeStaticClassレジストリの場合はどうなりますか? そうなると、トマシュが指摘したように、これは混乱につながります。

また、コンテナが初期化される前に変数がアクセスされる可能性もあります。可能性は予想よりも大きい: コンテナー内の一部の Bean は、MyComponent初期化中に の静的メソッドを呼び出す可能性がありますが、 の初期化はMyComponent後で実行されます (これは、この場合、Bean の依存関係が暗黙的であるため、IoC コンテナーが実行するためです)。正しい順序がわからない -@DependsOn注釈を使用する必要があります)

于 2012-12-18T19:56:42.797 に答える