2017-07-08 86 views
1

我的樣本項目是基於Maven的結構,下src/main/resources夾中的所有我的應用程序proeprties文件。以下是完整的示例代碼。我不明白爲什麼我的代碼無法正確查找配置文件,除非我使用@PropertySource註釋。春型材org.springframework.beans.factory.NoSuchBeanDefinitionException

我的實際疑問是:我已經在application.properties文件中很好地配置了彈簧屬性,但爲什麼它找不到配置文件及其各自的屬性文件?除非我正在使用@PropertySource註釋,IAM不env.getProperty獲得價值(「mysql.url」)。我的意思是Environment類無法從配置文件屬性文件中獲取值。 爲什麼?下面

蔭收到錯誤爲:

Jul 08, 2017 7:54:26 PM org.springframework.context.annotation.AnnotationConfigApplicationContext prepareRefresh 
INFO: Refreshing org.spring[email protected]300ffa5d: startup date [Sat Jul 08 19:54:26 IST 2017]; root of context hierarchy 
helloBean 
Exception in thread "main" org.springframework.beans.factory.NoSuchBeanDefinitionException: No bean named 'datasource' available 
    at org.springframework.beans.factory.support.DefaultListableBeanFactory.getBeanDefinition(DefaultListableBeanFactory.java:687) 
    at org.springframework.beans.factory.support.AbstractBeanFactory.getMergedLocalBeanDefinition(AbstractBeanFactory.java:1207) 
    at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:284) 
    at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:202) 
    at org.springframework.context.support.AbstractApplicationContext.getBean(AbstractApplicationContext.java:1084) 
    at com.oreilly.datasource.Main2.main(Main2.java:15) 

DatasourceConfig.java

package com.oreilly.datasource; 

import javax.sql.DataSource; 

import org.apache.commons.dbcp.BasicDataSource; 
import org.springframework.beans.factory.annotation.Autowired; 
import org.springframework.context.annotation.Bean; 
import org.springframework.context.annotation.Configuration; 
import org.springframework.context.annotation.Profile; 
import org.springframework.context.annotation.PropertySource; 
import org.springframework.context.annotation.PropertySources; 
import org.springframework.core.env.Environment; 

@Configuration 
/*@PropertySource("classpath:/application.properties") 
@PropertySource("classpath:/dev/application-dev.properties") 
@PropertySource("classpath:/prod/application-prod.properties")*/ 
public class DatasourceConfig { 

    @Autowired 
    private Environment env; 

    @Bean(name="helloBean") 
    public String helloWorld() { 
     System.out.println("helloBean"); 
     return "helloWorld...."; 
    } 

    @Bean(name="datasource") 
    @Profile("dev") 
    public DataSource datasourceForDev(){ 
     BasicDataSource dataSource = new BasicDataSource(); 
     System.out.println(env.getProperty("mysql.url")); 
     return dataSource; 
    } 

    @Bean(name="datasource") 
    @Profile("prod") 
    public DataSource datasourceForProd(){ 
     BasicDataSource dataSource = new BasicDataSource(); 
     System.out.println(env.getProperty("mysql.url")); 
     return dataSource; 
    } 
} 

Main2.java

package com.oreilly.datasource; 

import javax.sql.DataSource; 

import org.apache.commons.dbcp.BasicDataSource; 
import org.springframework.beans.factory.annotation.Value; 
import org.springframework.context.annotation.AnnotationConfigApplicationContext; 

public class Main2 { 


    public static void main(String[] args) { 
     AnnotationConfigApplicationContext context = new AnnotationConfigApplicationContext(DatasourceConfig.class); 

     DataSource dataSource = context.getBean("datasource", DataSource.class); 
     String helloBean = context.getBean("helloBean", String.class); 


    } 

} 

application.properties

spring.profiles.active=prod 
spring.config.name=application 
spring.config.location=classpath:/application.properties,classpath:/dev/application-dev.properties,classpath:/prod/application-dev.properties 

下面是該項目的文件夾結構:

enter image description here

請告訴我哪裏出了問題?在相同的位置application.property

回答

0

我剛纔通過如下修改解決了我的問題:

@PropertySource("classpath:/${spring.profiles.active}/application-${spring.profiles.active}.properties") 

現在我能夠以皮卡application-dev.properties(或)application-prod.properties動態。

注意Environment類需要@PropertySource註釋,否則我們爲env.get('someproperty')獲得null。

0
@Configuration 
@PropertySource("classpath:application.properties") 
public class DatasourceConfig { 
.... 
} 

put屬性文件,並按照命名規則應用程序 - {}輪廓像的.properties application-dev.properties,application-prod.properties。


「我想屬性文件被自動拾取基於我的個人資料在application.properties聲明。」

使用-Dspring.profiles.active = dev/prod運行您的應用程序。 Spring load 1)application.property,2)應用程序-dev/prod.properties文件,其中包含來自application.property的value的值

+0

我想要根據我在application.properties中聲明的配置文件自動拾取屬性文件。任何想法? – John

+0

不使用@PropertySource應該如何工作,如何?我的意思是它應該自動拾取我的application-dev.properties,如何? – John

1

Spring很聰明,它選擇application-x.properties(其中x是環境),具體取決於值分配到application.properties到spring.profiles.active,所以你不必擔心註冊在不同的@PropertySource標註的所有文件。

您可以在這裏更多的信息:https://docs.spring.io/spring-boot/docs/current/reference/html/boot-features-external-config.html#boot-features-external-config-profile-specific-properties

我建議你刪除所有@profile註解,讓只有一個數據源,這將是可變的(取決於從application.properties的seleced環境)。您可以與我把這個帖子末尾的例子明白這一點。

如果你想爲一個特定的配置文件(讓開發者說)定義一個mysql.url,你需要在application-dev.properties文件中添加「mysql.url」,然後設置spring.profiles。在application.properties中開發的活動值。

然後,在你DatasourceConfig.java,你可以這樣執行的東西:

@Autowired 
private Environment env; 

//Takes the mysqlUrl from application-x.properties (where x is the value of spring.profiles.active that comes from application.properties) 
@Value("${mysql.url}") 
private String mysqlUrl; 

@Bean(name="helloBean")... 

@Bean(name="datasource") 
public DataSource datasource() { 
    BasicDataSource dataSource = new BasicDataSource(); 
    System.out.println(mySqlUrl); //This value is variable depending of the profile that you're pointing on. 
    return dataSource; 
} 

請讓我知道這是對您有用。

+0

附加評論:您需要在資源根目錄中定義application.properties和application-x.properties文件,以便Spring自動檢測它們。 –

+0

我認爲你應該正確理解我的查詢。我們應該使用Environment類而不是像「mysql.url」那樣聲明每個屬性變量......我使用@Profile註釋來聲明2個配置文件(dev和prod)使用2種方法。 。 – John

相關問題