Environment
春はアプリケーション環境の抽象コンテナは二つの重要な要因であるです。彼らは以下の通りですProfiles
とproperties
。
Profile
ビーン定義は、名前の論理的なグループです。複数の容器であってもよいProfile
が、指定する必要があるprofile
だけこのProfile
コンテナにビーンで定義された登録パケットを。豆をに割り当てることのできるXMLまたは注釈で定義されているかどうかProfile
。Environment
オブジェクトのProfile
関係が決定することですProfiles(if any)
何を、現在アクティブなProfiles
デフォルトで有効である必要があり、次の(もしあれば)。
Properties
ほとんどすべてのアプリケーションでは、それは重要な役割を果たしてきた、とさまざまなソースから来ることができます:properties 文件
、JVM系统属性
、系统环境变量
、JNDI
、Servlet Context 参数
、ad-hoc Properties 对象
、Map
などなど。Environment
そして、Properties
の関係は、彼らから、ソースと解析プロパティの属性を設定するための便利なサービス・ユーザー・インターフェースを提供することです。
1、ビーンは、プロファイルを定義しました
Beanが定義Profiles
異なるビーンは異なる環境に登録可能コアコンテナのためのメカニズムを。environment
単語がユーザーごとに異なるものを意味し、この機能は、以下を含む多くの状況で非常に便利です。
- 開発環境でのデータソースを使用して、メモリ、QAまたは本番環境を使用してJNDIからデータソース
- アプリケーションは、環境性能に配備されているのみだけ登録した監視インフラストラクチャ
- クライアントや顧客のためにカスタマイズされたB登録Bean実装を展開します
それが必要とする、私たちは最初のユースケースでの実用化を考えてみましょうDataSource
。次のようにテスト環境では、構成であってもよいです。
@Bean
public DataSource dataSource() {
return new EmbeddedDatabaseBuilder()
.setType(EmbeddedDatabaseType.HSQL)
.addScript("my-schema.sql")
.addScript("my-test-data.sql")
.build();
}
私たちは今、アプリケーションがJNDIデータソースカタログ本番アプリケーション・サーバに登録されることを想定し、QAまたは本番環境に、このアプリケーションをデプロイする方法を考えてみましょう。私たちはdataSource
今、このようになります豆:
@Bean(destroyMethod="")
public DataSource dataSource() throws Exception {
Context ctx = new InitialContext();
return (DataSource) ctx.lookup("java:comp/env/jdbc/datasource");
}
問題は、現在の環境で、どのようにこれら二つの変数の間で切り替えるようにスイッチするということです。時間が経つにつれて、春のユーザーは、このタスクを達成するために多くの方法を考案しました。一般的には、システム環境変数に依存しあって${placeholder}[占位符]
XMLの<import />
組み合わせコード断片。環境変数に応じて正しい値に分析プロファイルパス。Bean定義Profiles
、それはこの問題に対する解決策を提供し、コンテナのコア機能です。
@プロフィール
@Profileコンポーネントのアノテーションを使用すると、1つまたは複数の指定の登録を宣言することを可能にするProfile
内部を。上記の例を使用して、我々は、書き換え可能
dataSource
な構成を次のようになります。
@Configuration
@Profile("dev")
public class StandaloneDataConfig {
@Bean
public DataSource dataSource() {
return new EmbeddedDatabaseBuilder()
.setType(EmbeddedDatabaseType.HSQL)
.addScript("classpath:com/bank/config/sql/schema.sql")
.addScript("classpath:com/bank/config/sql/test-data.sql")
.build();
}
}
@Configuration
@Profile("production")
public class JndiDataConfig {
@Bean(destroyMethod="")
public DataSource dataSource() throws Exception {
Context ctx = new InitialContext();
return (DataSource) ctx.lookup("java:comp/env/jdbc/datasource");
}
}
@profile
メタアノテーションとして使用することができ、目的は、カスタムの組み合わせのコメントを作成することです。次の例では、カスタム定義され@Production
た注釈を、代わりに使用することができます@Profile("production")
。
@Target(ElementType.TYPE)
@Retention(RetentionPolicy.RUNTIME)
@Profile("production")
public @interface Production {
}
@profile
また、この方法のアップが1つの特定のコンフィグレーションBeanが含まれて宣言することができます。
@Configuration
public class AppConfig {
@Bean
@Profile("dev")
public DataSource devDataSource() {
return new EmbeddedDatabaseBuilder()
.setType(EmbeddedDatabaseType.HSQL)
.addScript("classpath:com/bank/config/sql/schema.sql")
.addScript("classpath:com/bank/config/sql/test-data.sql")
.build();
}
@Bean
@Profile("production")
public DataSource productionDataSource() throws Exception {
Context ctx = new InitialContext();
return (DataSource) ctx.lookup("java:comp/env/jdbc/datasource");
}
}
XMLビーン定義プロファイル
対応するラベルは、XML内にあるprofile
要素。上記の設定例では、2つのXMLファイルで上書きすることができます。
<beans profile="development"
xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:jdbc="http://www.springframework.org/schema/jdbc"
xsi:schemaLocation="...">
<jdbc:embedded-database id="dataSource">
<jdbc:script location="classpath:com/bank/config/sql/schema.sql"/>
<jdbc:script location="classpath:com/bank/config/sql/test-data.sql"/>
</jdbc:embedded-database>
</beans>
<beans profile="production"
xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:jee="http://www.springframework.org/schema/jee"
xsi:schemaLocation="...">
<jee:jndi-lookup id="dataSource" jndi-name="java:comp/env/jdbc/datasource"/>
</beans>
また、別のファイルで定義された回避は同じファイルに入れ子にすることができます<beans />
レーベル:
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:jdbc="http://www.springframework.org/schema/jdbc"
xmlns:jee="http://www.springframework.org/schema/jee"
xsi:schemaLocation="...">
<!-- other bean definitions -->
<beans profile="development">
<jdbc:embedded-database id="dataSource">
<jdbc:script location="classpath:com/bank/config/sql/schema.sql"/>
<jdbc:script location="classpath:com/bank/config/sql/test-data.sql"/>
</jdbc:embedded-database>
</beans>
<beans profile="production">
<jee:jndi-lookup id="dataSource" jndi-name="java:comp/env/jdbc/datasource"/>
</beans>
</beans>
spring-bean.xsd
一つ以上の許可<beans />
ような要素が、<beans />
唯一の要素と他の<beans />
要素と同じレベル。
これは、XMLファイル内の混乱を引き起こすことなく、柔軟性を提供するのに役立つはずです。
豆の法的定義
<beans>
<beans profile="development">
...
</beans>
<beans profile="production">
...
</beans>
</beans>
違法ビーンの定義
<beans>
<bean />
<beans profile="development">
...
</beans>
<bean />
</beans>
活性化プロフィール
今、私たちは、コンフィギュレーションを更新したことを、我々はまだ春に指示する必要がProfile
効果的であるが。私たちは今、私たちのサンプルアプリケーションを起動した場合、我々は、スロー表示されますNoSuchBeanDefinitionException
コンテナと呼ばれる、見つけることができないので、例外をdataSource
のSpring Bean。
これは、いくつかの方法によって活性化することができるProfile
が、最も直接的な方法は、プログラムにあるApplicationContext
内部のEnvironment API
プログラミング:
AnnotationConfigApplicationContext ctx = new AnnotationConfigApplicationContext();
ctx.getEnvironment().setActiveProfiles("development");
ctx.register(SomeConfig.class, StandaloneDataConfig.class, JndiDataConfig.class);
ctx.refresh();
また、Profile
それはまた、可能spring.profile.active
宣言起動します。システム環境変数、JVMシステムプロパティでweb.xml
のServletContextパラメータ
にもエントリ(第2節「PropertySource抽象化」)JNDI。統合ではで、テストspring-test
モジュール@activeprofiles
アクティブ注釈へprofile
。
ノート、してくださいProfile
いない「非そのため、ある」命題、同時に複数起動することができるProfile
の。あなたが呼び出すことによって、方法をプログラムすることができるsetActiveProfiles()
プロフィールの複数の活性化方法。可変のパラメータ文字列を受信する方法(String…)
:
ctx.getEnvironment().setActiveProfiles("profile1", "profile2");
することができますspring.profiles.active
あなたは、カンマ区切り受け取ることができる、宣言することがprofile
名前のリストを:
-Dspring.profiles.active="profile1,profile2"
デフォルトのプロフィール
通常の状況下で、我々は設定されていないBeanを定義するprofile
ことで、ヘルプたち春のデフォルト設定、profile
にdefault
:
@Configuration
@Profile("default")
public class DefaultDataConfig {
@Bean
public DataSource dataSource() {
return new EmbeddedDatabaseBuilder()
.setType(EmbeddedDatabaseType.HSQL)
.addScript("classpath:com/bank/config/sql/schema.sql")
.build();
}
}
いない場合はProfile
起動し、それは上記を作成しますdataSource
。これは、一つ以上のBeanとして定義されたデフォルトを提供する方法として見ることができます。他が有効になっている場合はprofile
、デフォルトではprofile
適用されません。
通したりすることにより、デフォルトの属性変更の名前を。Environment
setDefaultProfiles()
spring.profiles.default
profile
2、PropertySource抽象化
SpringのEnvironment
抽象は、構成階層の元の属性の検索操作を提供します。完全に説明するために、次の例を考えてみます。
ApplicationContext ctx = new GenericApplicationContext();
Environment env = ctx.getEnvironment();
boolean containsFoo = env.containsProperty("foo");
System.out.println("Does my environment contain the 'foo' property? " + containsFoo);
上記のコードでは、我々は、高レベル問い合わせ春の道を参照して、そのfoo
属性は、現在の環境として定義されます。この質問に答えるために、Environment
オブジェクトがセットになりますPropertySource
検索するオブジェクトを。PropertySource
これは、任意の源であるkey-value(键-值)
のシンプルな抽象.Spring StandardEnvironment
2つのオブジェクト構成PropertySource
JVMシステムプロパティ変数の1( -オブジェクト通过 system.getproperties() 获取
)、別のシステム環境変数の代わりに(通过 system.getenv() 获取)
。
これらのデフォルト属性は、ソースに存在し
StandardEnvironmen
、別のアプリケーションインチStandardServletEnvironment
それはを含むソースの追加のデフォルトのプロパティが含まservlet配置
とをservlet上下文参数
。同様に、StandardPortletEnvironment
あなたもアクセスできるportlet
構成とし、portlet上下文参数
財産ソースとして。どちらも、選択的に有効にすることができますJndiPropertySource
。詳細については、を参照してくださいjavadocs
。
具体的には、使用中にStandardEnvironment
、システムは、システムのプロパティ変数またはシステム環境変数が含まれている実行されている場合はfoo
、プロパティを、その後の呼び出しがenv.containsProperty("foo")
返されますtrue
。
検索プロパティは、階層構造を持っています。デフォルトでは、システムプロパティはそうならば、環境変数よりも優先されます
foo
プロパティはに起こったenv.getproperty(“foo”)
、セットコール、システムプロパティの値が「勝利」とは、環境変数に戻るに優先権を与えます。プロパティの値がマージされていませんが、完全に前のエントリを覆われていることをしてくださいノート。
共通のためStandardServletEnvironment
、完全な階層が優先度がトップダウンで、次のとおりです。
- (例えば、コンテキストのDispatcherServletで)のServletConfigパラメータ
- ServletContextパラメータ(web.xmlのラベル)
- JNDI環境変数(「で、java:comp / env /」词目)
- JVMシステムプロパティ(「-D」コマンドラインパラメータ)
- JVMシステム環境(システム環境変数)
最も重要なのは、全体のメカニズムが設定可能です。たぶん、あなたは検索にそれらを統合することを期待して、カスタム属性のソースを持っています。これは問題ありません-単に実装されており、自身のインスタンス化PropertySource
し、現在に追加Environment
のPropertySource
コレクション:
ConfigurableApplicationContext ctx = new GenericApplicationContext();
MutablePropertySources sources = ctx.getEnvironment().getPropertySources();
sources.addFirst(new MyPropertySource());
上記のコードでは、MyPropertySource
検索で最高の優先順位を添加します。それが含まれている場合foo
の特性を、それが他のどのになりますPropertySource
任意のされfoo
検出され、前のプロパティに戻ります。MutablePropertySources API
多くの方法が開示され、これらの方法は、ソースの特性の組の正確な操作を可能にします。
3、@ PropertySource
@PropertySource
注意事項は、宣言するための便利な機構を提供するPropertySource
春に追加Environment
です。
キー/値ペアが与えられtestbean.name=myTestBean
た文書をapp.properties
。次@configuration
のクラスが使用Springコンテキストにロードを内部。その後、呼び出しが返されます。@propertysource
app.properties
Environment
estBean.getName()
myTestBean
@Configuration
@PropertySource("classpath:/com/myco/app.properties")
public class AppConfig {
@Autowired
Environment env;
@Bean
public TestBean testBean() {
TestBean testBean = new TestBean();
testBean.setName(env.getProperty("testbean.name"));
return testBean;
}
}
で@propertysource
リソースパス位置を添加することができる${...}
プレースホルダ。これは、環境に登録されているソースの性質に応じて解決されます。例えば:
@Configuration
@PropertySource("classpath:/com/${my.placeholder:default/path}/app.properties")
public class AppConfig {
@Autowired
Environment env;
@Bean
public TestBean testBean() {
TestBean testBean = new TestBean();
testBean.setName(env.getProperty("testbean.name"));
return testBean;
}
}
仮定するmy.placeholder
ようなシステムプロパティまたはシステム環境変数のプレースホルダとしてすでにソースに登録されているプロパティに存在するが、適切な値に解決されます。そうでない場合には、default/path
それがデフォルトとして使用されます。デフォルト値を指定して、いないプロパティを解決できない場合は、それがスローされますIllegalArgumentException
例外を。
Javaでは8つのプロパティの
@propertysource
注釈は反復可能です。しかし、すべてのこれらの@propertysource
いずれの構成クラスで、直接メタアノテーションと同じカスタム注釈に:ノートは、同じレベルで宣言する必要があります。直接のコメントは、元のノートをカバーしますので、直接コメントや混合のメタアノテーションは、推奨されません。
4、書類上のプレースホルダの解決
過去には、プレースホルダ要素の値は、JVMシステム属性または環境変数によって解決することができます。これはもはやケースです。環境抽象化が容器全体で統合されているので、プレースホルダを解析することによってそれを解決するのは簡単です。適切な時期に独自の属性のソースを追加し、システムプロパティと環境変数の優先順位によって検索を変更、または完全に削除:あなたが好きなように解決プロセスを構成することができますことをこれが意味。
どのような具体的には、関係なく、ユーザー定義属性の、環境で使用可能な限り、次の文が動作することができます:
<beans>
<import resource="com/bank/service/${customer}-config.xml"/>
</beans>
オリジナル住所: