2013-07-25 40 views
27

Theo mùa xuân documentation, các bước để sử dụng Spring JdbcTemplate là như sau:sử dụng Spring JdbcTemplate - tiêm nguồn dữ liệu vs JdbcTemplate

<?xml version="1.0" encoding="UTF-8"?> 
    <beans xmlns="http://www.springframework.org/schema/beans" 
     xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
     xmlns:context="http://www.springframework.org/schema/context" 
     xsi:schemaLocation=" 
      http://www.springframework.org/schema/beans 
      http://www.springframework.org/schema/beans/spring-beans-3.0.xsd 
      http://www.springframework.org/schema/context 
      http://www.springframework.org/schema/context/spring-context-3.0.xsd"> 

     <!-- Scans within the base package of the application for @Components to configure as beans --> 
     <context:component-scan base-package="org.springframework.docs.test" /> 

     <bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource" destroy-method="close"> 
      <property name="driverClassName" value="${jdbc.driverClassName}"/> 
      <property name="url" value="${jdbc.url}"/> 
      <property name="username" value="${jdbc.username}"/> 
      <property name="password" value="${jdbc.password}"/> 
     </bean> 

     <context:property-placeholder location="jdbc.properties"/> 

    </beans> 

Và sau đó,

@Repository 
    public class JdbcCorporateEventDao implements CorporateEventDao { 

     private JdbcTemplate jdbcTemplate; 

     @Autowired 
     public void setDataSource(DataSource dataSource) { 
      this.jdbcTemplate = new JdbcTemplate(dataSource); 
     } 

     // JDBC-backed implementations of the methods on the CorporateEventDao follow... 
    } 

Về cơ bản, JdbcTemplate được tạo ra bên trong lớp Component bằng cách sử dụng setter cho nguồn dữ liệu.

Có điều gì sai trái khi thực hiện theo cách này thay vì vậy có chính xác MỘT ví dụ về jdbcTemplate trong ứng dụng không?

<bean id="jdbcTemplate" class="org.springframework.jdbc.core.JdbcTemplate" 
    p:dataSource-ref="dataSource" 
/> 

Và sau đó tiêm JdbcTemplate bản thân trực tiếp vào phần

@Repository 
public class JdbcCorporateEventDao implements CorporateEventDao { 
    @Resource("jdbcTemplate") 
    private JdbcTemplate jdbcTemplate; 


    // JDBC-backed implementations of the methods on the CorporateEventDao follow... 
} 

Có một lý do tại sao các JdbcTemplate bản thân không được tiêm vào lớp thành phần trực tiếp?

SGB

+0

Có thể là một bản sao của http: // stackoverflo w.com/q/9460507/309399. Nhưng câu hỏi không được trả lời. – SGB

Trả lời

24

Bạn có thể làm những gì mình muốn. The javadoc of JdbcTemplate nói thậm chí rõ ràng nó:

có thể được sử dụng trong việc thực hiện dịch vụ thông qua instantiation trực tiếp với một tham chiếu DataSource, hoặc được chuẩn bị trong một bối cảnh ứng dụng và cung cấp cho các dịch vụ như tài liệu tham khảo đậu.

+2

++ cho liên kết. Cảm ơn câu trả lời ngắn gọn và trích dẫn từ javadoc. Câu hỏi cụ thể này đã làm phiền tôi khá lâu rồi - như tất cả các ví dụ tôi đã thấy trực tuyến dường như là tiêm nguồn dữ liệu - làm tôi băn khoăn liệu mình có thiếu cái gì đó ... – SGB

21

Vào mùa xuân-context.xml thêm dòng sau và

<bean id="jdbcTemplate" class="org.springframework.jdbc.core.JdbcTemplate"> 
    <property name="dataSource" ref="dataSource"/> 
</bean> 

và trực tiếp bạn có thể sử dụng JdbcTemplate bởi autowiring như

@Autowired JdbcTemplate jdbcTemplate; 

dụ:

this.jdbcTemplate.query("select * from ******",new RowMapper()); 
+0

Làm thế nào để làm tương tự cho nhiều nguồn dữ liệu? Tôi có thể chỉ định như thế này: và cho một nguồn dữ liệu khác như .Đây có phải là cách chính xác để đặt nhiều nguồn dữ liệu vào một Template JDBC – Analysts

+0

@Analysts, Bạn nên định nghĩa một jdbcTemplate riêng biệt cho mỗi nguồn dữ liệu, vì vậy nếu bạn có 2 nguồn dữ liệu, bạn sẽ có jdbcTemplate1 cho datasource1 và jdbcTemplate2 cho datasource2 và chèn jdbcTemplates một cách riêng biệt khi cần vào tầng dịch vụ của bạn – SGB

+0

Điều gì @SCB nói là đúng, bạn phải có nhiều bean cho nhiều cơ sở dữ liệu. – Odaiah

5

Bạn cũng có thể làm điều đó như

@Configuration 
@Import({PersistenceConfig.class}) 
@ComponentScan(basePackageClasses = { 
    ServiceMarker.class, 
    RepositoryMarker.class } 
) 
public class AppConfig { 

    /** 
    * To resolve ${} in @Values, you must register a static PropertySourcesPlaceholderConfigurer in either XML or 
    * annotation configuration file. 
    */ 
    @Bean 
    public static PropertySourcesPlaceholderConfigurer propertyConfigInDev() { 
     return new PropertySourcesPlaceholderConfigurer(); 
    } 
} 

PersistenceConfig

@Configuration 
@PropertySource(value = { "classpath:database/jdbc.properties" }) 
@EnableTransactionManagement 
public class PersistenceConfig { 

    @Autowired 
    private Environment env; 

/** 
    * The @Bean annotation is used to declare a Spring bean and the DI requirements. The @Bean annotation is equivalent to 
* the <bean> tag, the method name is equivalent to the id attribute within the <bean> tag. 
    * 
    * <bean id="mySqlDataSource" class="org.apache.commons.dbcp2.BasicDataSource" destroy-method="close" 
     p:driverClassName="${jdbc.mysql.driverClassName}" 
     p:url="${jdbc.mysql.url}" 
     p:username="${jdbc.mysql.username}" 
     p:password="${jdbc.mysql.password}" /> 
    * 
    * @return 
    */ 
    @Bean(destroyMethod = "close") 
    public DataSource mySqlDataSource() { 
     BasicDataSource dataSource = new BasicDataSource(); 
     dataSource.setDriverClassName(env.getProperty("jdbc.mysql.driverClassName")); 
     dataSource.setUrl(env.getProperty("jdbc.mysql.url")); 
     dataSource.setUsername(env.getProperty("jdbc.mysql.username")); 
     dataSource.setPassword(env.getProperty("jdbc.mysql.password")); 
     return dataSource; 
    } 

    @Bean(destroyMethod = "close") 
    public DataSource ls360DataSource() { 
     BasicDataSource dataSource = new BasicDataSource(); 
     dataSource.setDriverClassName(env.getProperty("jdbc.ls360.driverClassName")); 
     dataSource.setUrl(env.getProperty("jdbc.ls360.url")); 
     dataSource.setUsername(env.getProperty("jdbc.ls360.username")); 
     dataSource.setPassword(env.getProperty("jdbc.ls360.password")); 
     return dataSource; 
    } 
} 

MySqlDaoImpl

@Repository 
public class MySqlDaoImpl implements MySqlDao{ 

    private static final Logger logger = LogManager.getLogger(); 

    @Inject 
    private DataSource mySqlDataSource; 
    private JdbcTemplate mySqlJdbcTemplate; 

    @PostConstruct 
    public void afterPropertiesSet() throws Exception { 
     if (mySqlDataSource == null) { 
      throw new BeanCreationException("Must set mySqlDataSource on " + this.getClass().getName()); 
     } 
     this.mySqlJdbcTemplate = new JdbcTemplate(mySqlDataSource); 
    } 

    @Override 
    public void callStoredProcedure(String storedProcedureName, Map<String, Object> inParamMap) throws Exception { 

     SimpleJdbcCall simpleJdbcCall = new SimpleJdbcCall(mySqlJdbcTemplate).withProcedureName(storedProcedureName); 
     SqlParameterSource in = new MapSqlParameterSource(inParamMap); 

     logger.info("Calling stored Procedure: " + storedProcedureName); 
     Map<String, Object> simpleJdbcCallResult = simpleJdbcCall.execute(in); 
     logger.info("Stored Procedure Result: " + simpleJdbcCallResult); 
    } 
} 

chính

public static void main(String[] args) { 
    try (GenericApplicationContext springContext = new AnnotationConfigApplicationContext(AppConfig.class)) { 
     MySQLDao mySqlDao = springContext.getBean(MySQLDaoImpl.class); 
     try { 
      Map<String, Object> inParamMap = new HashMap<String, Object>(); 
      inParamMap.put("iCourseId", 1); 
      mySqlCourseRenewalDao.callStoredProcedure("usp_processCourseRenewal", inParamMap); 
     } catch (Exception e) { 
      logger.error("Exception occurs", e); 
     } 
    } catch (Exception e) { 
     logger.error("Exception occurs in loading Spring context: ", e); 
    } 
} 

Cảm ơn

Các vấn đề liên quan