2016-09-05 6 views
1

(春3.2.5を使用して)次のコードを考える:Javaの春のジェネリックコレクションの依存

@org.springframework.context.annotation.Configuration 
public class MyConfiguration { 

    @Bean 
    public MyClass myClass(@Qualifier("messageFeeders") List<MessageFeeder> messageFeeders) { 
     return new MyClass(messageFeeders); 
    } 

    @Bean 
    public MessageFeederSubclassOne messageFeeder1() { 
     return new MessageFeederSubclassOne(); 
    } 

    @Bean 
    public MessageFeederSubclassTwo messageFeeder2() { 
     return new MessageFeederSubclassTwo(); 
    } 

    @Bean 
    @Qualifier("messageFeeders") 
    public List<MessageFeeder> messageFeeders(MessageFeederSubclassOne messageFeeder1, MessageFeederSubclassTwo messageFeeder2) { 
     return ImmutableList.of(messageFeeder1, messageFeeder2); 
    } 
} 

私はこの例外を取得:

org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'myClass' defined in class path resource [com/company/configuration/MyConfiguration.class]: Unsatisfied dependency expressed through constructor argument with index 0 of type [java.util.List]: : No qualifying bean of type [com.company.messagebroker.MessageFeeder] found for dependency [collection of com.company.messagebroker.MessageFeeder]: expected at least 1 bean which qualifies as autowire candidate for this dependency. Dependency annotations: {@org.springframework.beans.factory.annotation.Qualifier(value=messageFeeders)} 
    at org.springframework.beans.factory.support.ConstructorResolver.createArgumentArray(ConstructorResolver.java:738) 
Caused by: org.springframework.beans.factory.NoSuchBeanDefinitionException: No qualifying bean of type [com.company.messagebroker.MessageFeeder] found for dependency [collection of com.company.messagebroker.MessageFeeder]: expected at least 1 bean which qualifies as autowire candidate for this dependency. Dependency annotations: {@org.springframework.beans.factory.annotation.Qualifier(value=messageFeeders)} 
    at org.springframework.beans.factory.support.DefaultListableBeanFactory.raiseNoSuchBeanDefinitionException(DefaultListableBeanFactory.java:988) 
    at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:816) 

、私は春が発見しようとして実現MessageFeeder型のBeanをこのリストに入れておいてください。しかし、私が望むのは、修飾子が実際に自分が定義したリストを実際に挿入することです。

DefaultListableBeanFactoryコードを見ると、修飾子は完全に無視されているようです。

また、なぜ失敗するのですか?修飾子を無視しても、MessageFeederを継承して使用する2つのBeanを検出してはいけませんか?

私はそれを使用する唯一の人ではないので、私はmessageFeeders beanを変更したくないと思います。 Springに修飾子を考慮させる簡単な方法はありますか?

+0

stacktraceから明らかに 'MyClass'doに問題があります。リスト引数を持つコンストラクタもありますか? –

+0

もちろんあります。それ以外の場合は、イベントはコンパイルされません。あなたはその誤解を誤解しました。 MyClassをまったく参照していないのですが、上記のコードで定義されているBeanの依存関係を満たすことに問題があります。 – Tolstoyevsky

答えて

1

はここにあなたのソリューションです:

@Bean 
@Autowired 
@Qualifier("messageFeeders")` 
public MyClass myClass(List<MessageFeeder> messageFeeders) 
{ 
    return new MyClass(messageFeeders);` 
} 

説明:

私は最初にSpringバージョン4.3.2でそれをやろうとしましたが、定義したとおりにうまく機能しました。しかし、私はSpringの依存関係をバージョン3.2.5に変更しました。あなたの例外を受け取りました。

@Autowiredは、アノテーションでBeanを挿入する適切な方法です。これは、タイプごとに行います。 @Autowired注釈の場合、IOCコンテナは型認識によってBeanを挿入します。

IOCコンテナに同じタイプの複数のBeanがある場合はどうなりますか?どのBeanを注入するのか

単純に、@Qualifier注釈によって。

でも、@Autowiredアノテーションを使用する必要があります。

+0

ありがとう!これは広告されたように働いた。 – Tolstoyevsky

1

それは

@Bean 
@Resource(name = "messageFeeders") 
public MyClass myClass(List<MessageFeeder> messageFeeders) { 
    return new MyClass(messageFeeders); 
} 
+0

javax.annotation.Resourceを意味しますか?もしそうなら、それはパラメータに適用できないようです。また、それは@Resource(name = "messageFeeders") – Tolstoyevsky

+0

それを指摘してくれてありがとう、それに応じて変更を加えました – Mudassar

+0

これも働いた – Tolstoyevsky

0

は、新しいクラスを使用して、追加する豆の作成を変更、メッセージフィーダのリストのための新たなラッパークラスを作成し、問題を解決する可能性がありますよう@Resourceを使用してみてください「@Autowired」あなたにコンストラクタ呼び出し

class MessageFeederList extends ArrayList<MessageFeeder>{} 

@Bean 
public MessageFeederList messageFeeders(
    MessageFeederSubclassOne messageFeeder1, 
    MessageFeederSubclassTwo messageFeeder2){ 
    return ImmutableList.of(messageFeeder1, messageFeeder2); 
} 

@Bean 
public MyClass myClass(@Autowired MessageFeederList messageFeeders) { 
    return new MyClass(messageFeeders); 
} 
+0

ありがとう、私はこのソリューションが動作することを実現しますが、 (context.getBean( "messageFeeders")を直接呼び出すことによって)それを使用することを管理する多くの場所を変更する必要があるため、messageFeeders beanを使用します。 この場合、2つのサブクラスを手動でMyClass Beanに手動で注入する方が簡単です – Tolstoyevsky

関連する問題