2016-10-24 5 views
4

私はSpringブートアプリケーションを持っており、基礎となるSQLデータソースのタイプ(spring.datasource。*プロパティを使用して定義)に基づいて特定のリポジトリ実装を注入したいと考えています。Springブート:条件付きデータベースタイプ

私はここでカスタム条件を使用しようとしましたが、残念ながら、評価されると、データベースタイプをチェックするためにデータソースを取得できません。

私の条件は現在、次のようになります。

@Order(Ordered.LOWEST_PRECEDENCE - 10) 
class OnDatabaseTypeCondition implements Condition { 

    @Override 
    public boolean matches(ConditionContext context, AnnotatedTypeMetadata metadata) { 

     DataSource dataSource = context.getBeanFactory().getBean(DataSource.class); 
     // further matching code here 

} 

それはこのようなものを使用する必要があります。条件が評価されている場合しかし、私はデータソースがあるという例外を取得

@ConditionalOnDatabaseType(H2) 
public class MyCustomImplementation implements MyRepository { 
    // Code 
} 

を定義されていません:

Caused by: org.springframework.beans.factory.NoSuchBeanDefinitionException: No qualifying bean of type [javax.sql.DataSource] is defined 
    at org.springframework.beans.factory.support.DefaultListableBeanFactory.getBean(DefaultListableBeanFactory.java:348) 
    at org.springframework.beans.factory.support.DefaultListableBeanFactory.getBean(DefaultListableBeanFactory.java:335) 

私はこれが起こっていると仮定します。conditi onはすべてのBeanが構築される前に既にチェックされています。この条件が評価される前にデータソースを作成しなければならないことをSpringに伝える方法はありますか?または、これはSpring条件を使用しても可能ではありませんか?

私が解決したいユースケースは、次のとおりです。アプリケーションはさまざまなタイプのデータベースで実行でき、一部は(H2のように)ウィンドウ機能のような特定の機能を持たないものもあります。だから私は、遅いかもしれないが、機能的には正しいデータベースに特別なクエリを提供したい。このアプローチのアイデアは、特定のSpringプロファイルを導入する必要なしに、(org.springframework.jdbc.support.JdbcUtilsを使用して)基盤となるデータベースを調べるだけで、これらのJDBCリポジトリを簡単にマークする必要があるということでした。

おかげ

答えて

2

豆が実際に作成された場合、いくつかの条件が評価されています。 Beanの有無を確認する場合は、非常ににする必要があります。その段階でBeanを取得しようとすると、早期初期化が行われるためです。それが最初の問題です。

第二の問題は、あなたの設定(アプリ設定)常に完全に実行前に自動設定ということです。 Spring BootがDataSourceを作成する必要があるかどうかを判断する必要がある場合は、アプリの設定で提供する必要があります。

これは、自動構成を使用して実装できる唯一の方法です。あなたが探しているBeanを提供するはずのものの後で自動構成が実行されるようにしてください(@AutoconfigureAfter)。それにかかわらず、私はそのような文脈への直接の呼び出しをしませんでした。 OnBeanConditionをチェックして、Spring Bootがそのことをどのように行うかを確認してください。したがって、あなたのアプリの設定や、コンポーネントスキャンでスキャンされたコンポーネントにこのような条件を追加することはできません。

と言われていますが、使用例は私にとっては非常に奇妙に見えます。多分、私たちは一歩前に戻ることができ、あなたはなぜこれを行う必要があるのか​​を説明することができます。

+0

こんにちは@Stephane、私は元のユースケースで質問を更新しました。私の主な目的は、異なるデータベース(必要な場合)ごとに異なるリポジトリの実装を可能にする方法を作成することでした。 Springなどが使用しているベストプラクティスがあるかどうかはわかりません.Googleの調査では役に立たないものはありません。 –

+0

実装の詳細を尋ねるのではなく、 'spring-data'タグで別のスレッドを作成し、これをどのように達成できるかを尋ねます。私はいくつかのクエリを外部化することができますか、またはリポジトリを作成するファクトリを調整できると思います。それはあなたがしていると仮定して、使用している春のデータの機能に依存します。 –

+1

アプリケーションはバネデータとバネjdbc(JPAでは不十分です)が混在しており、アプリケーションのjdbc部分に問題があります。私は問題を別の方法で解決しようとし、問題にぶつかったら新しい質問に戻ります。 –