Spring框架的作用和优点:

  1. spring是一个开源的轻量级的应用开发框架,其目的是用于简化企业级应用程序开发,减少侵入;
  2. spring提供的IoC 和AOP应用,可以将组建的耦合度降至最低,即解耦,便于系统日后维护和升级;
  3. spring为系统提供了一个整体解决方案,开发者可以利用它本身提供的功能外,也可以与第三方框架和技术整合,合一自由选择采用哪种技术进行开发。

Spring基础包

Spring-core-3.2.8.RELEASE.jar

Spring-context-3.2.8. RELEASE.jar

Spring-beans-3.2.8. RELEASE.jar

Common-logging.jar

Spring-expression-3.2.8. RELEASE.jar

 

 

  1. public class OracleUserDAO implements UserDAO{
  2.     private JDBCDataSource dataSource;
  3.     /** 创建 OracleUserDAO 对象必须依赖于JDBCDataSource实例 */
  4.     public OracleUserDAO(JDBCDataSource dataSource) {
  5.         this.dataSource = dataSource;
  6.     }
  7.     /** 根据唯一用户名查询系统用户, 如果没有找到用户信息返回null */
  8.     public User findByName(String name) {
  9.         System.out.println("利用JDBC技术查找User信息");
  10. String sql = "select id, name, pwd, phone  from USERS where name=?";
  11. Connection conn = null;
  12. try {
  13. conn = dataSource.getConnection();
  14. PreparedStatement ps = conn.prepareStatement(sql);
  15. ps.setString(1, name);
  16. ResultSet rs = ps.executeQuery();
  17. User user=null;
  18. while(rs.next()){
  19. user = new User();
  20. user.setId(rs.getInt("id"));
  21. user.setName(rs.getString("name"));
  22. user.setPwd(rs.getString("pwd"));
  23. user.setPhone(rs.getString("phone"));
  24. }
  25. rs.close();
  26. ps.close();
  27. return user;
  28. } catch (SQLException e) {
  29. e.printStackTrace();
  30. throw new RuntimeException(e);
  31. }finally{
  32. dataSource.close(conn);
  33. }
  34. }

36.}

1.      <!-- setter注入 -->
2.   
3.      <bean id="dataSource" class="org.tarena.dao.JDBCDataSource">
4.   
5.          <property name="driver" value="oracle.jdbc.OracleDriver"></property>
6.   
7.          <property name="url" value="jdbc:oracle:thin:@localhost:1521:XE"></property>
8.   
9.          <property name="user" value="openlab"></property>
10. 
11.        <property name="pwd" value="open123"></property>
12. 
13.    </bean>
 
17.    <!-- 构造器注入 -->
18. 
19.    <bean id="userDAO" class="org.tarena.dao.OracleUserDAO">
20. 
21.        <!-- 利用构造器参数注入bean的属性 -->
22. 
23.        <constructor-arg name="dataSource" ref="dataSource"/>
24. 
25.    </bean>

 

 

Spring IoC容器可以自动装配(autowire)相互协作bean之间的关联关系,autowire可以针对单个bean进行设置,autowire的方便之处在于减少xml的注入配置。

在xml配置文件中,可以在<bean/>元素中使用autowire属性指定自动装配规则,一共有五种类型值

No : 禁用自动装配,默认值

byName : 根据属性名自动装配。此选项将煎炒容器并根据名字查找与属性完全一致的bean

         并将其与属性自动装配

byType : 如果容器中存在一个与指定属性类型相同的bean ,那么将与该属性自动装配

constructor : 与byType类似,不同之处在于它与构造器参数

autoDelete :

 

 

 

 

步骤八:测试引用方式集合注入

1.为Spring配置文件applicationContext.xml增加如下配置, 采用引用方式注入集合对象, 代码参考如下:

        <!-- 定义集合Bean -->

        <util:list id="oneList">

               <value>Tom</value>

               <value>Andy</value>

        </util:list>

        <util:set id="oneSet">

               <value>James Gosling</value>

               <value>Martin fowler</value>

        </util:set>

        <util:map id="oneMap">

               <entry key="1001" value="Java语言基础"></entry>

               <entry key="1002" value="Java Web基础"></entry>

        </util:map>

        <util:properties id="oneProps">

               <prop key="username">root</prop>

               <prop key="password">1234</prop>

        </util:properties>

        <!-- 引用方式注入集合属性 -->

        <bean id="messagebean2" class="org.tarena.bean.MessageBean">

               <property name="moduleName" value="资费管理"></property>

               <property name="pageSize" value="5"></property>

               <property name="username" value="andy"></property>

               <property name="password" value="123"></property>

               <!-- 引用方式注入集合属性 -->

               <property name="someList" ref="oneList" />

               <property name="someSet" ref="oneSet" />

               <property name="someMap" ref="oneMap" />

               <property name="someProps" ref="oneProps" />

        </bean>

2. 增加Test2类测试如上配置, Test2代码如下:

package org.tarena.test;

 

import org.springframework.context.ApplicationContext;

import org.springframework.context.support.ClassPathXmlApplicationContext;

import org.tarena.bean.MessageBean;

 

/** 引用方式注入集合 */

public class Test2 {

        public static void main(String[] args) throws Exception{

               String conf = "applicationContext.xml";

               ApplicationContext ac = new ClassPathXmlApplicationContext(conf);

               MessageBean bean = ac.getBean("messagebean2",MessageBean.class);

               bean.execute();

        }

}

 

利用Spring表达式注入属性值

在工程的src下 ,创建属性文件db.properties , 文件内容如下

user=scott

password注入的值为null

修改applicationContext.xml文件,注入Spring表达式,代码如下

<util:properties id=”jdbcProperties” location=”classpath:db.properties” />

<bean id=”messagebean” class=”org.tarena.bean.MessageBean>

         <property name=”moduleName” name=”资源管理”></property>

         <property name=”pageSize” value=”5”></property>    

         <property name=”username” value=”#{jdbcProperties.user}”></property>

         <property name=”password” ></property>

</bean>

 

 

测试Spring自动组建扫描

如何使用组件扫描的方式和"注解标记"配合获取容器中的ExampleBean对象

方案:

使用组建扫描,首先需要在XML配置中指定扫描类路径,配置代码如下

<context:component-scan base-package=”com.tarena”/>

上述配置,容器实例化时会自动扫描com.tarena包及其子包下的所有组件类。

指定扫描类路径后,并不是该路径下所有组件类都扫描到Spring容器的,只有在组件类定义前面有以下注解标记时,才会扫描到Spring容器

@Component    通用注解

@Name         通用注解

@Respository  持久化层组件注解

@Service      业务层组件注解

@Controller   控制层组件注解

 

 

 

3.1 问题

使用组件扫描的方式,重构如何控制ExampleBean实例化为单例或非单例模式。

 

3.2 方案

1. 通常受Spring管理的组件,默认的作用域是"singleton"。如果需要其他的作用域可以使用@Scope注解,只要在注解中提供作用域的名称即可

@Scope(“singleton”)

 

2.@PostConstruct 和 @PreDestroy注解分别用于指定初始化和销毁回调方法

 

 

4.2 方案

使用Spring注解方式实现组件的声明, 并且利用注解注入方式解决依赖关系.

Jar包如下

包含Spring必须的5个jar包, 以及数据库驱动程序

Spring-core-3.2.8.RELEASE.jar

Spring-context-3.2.8. RELEASE.jar

Spring-beans-3.2.8. RELEASE.jar

Common-logging.jar

Spring-expression-3.2.8. RELEASE.jar

Javax.inject-1.jar               是srping3.0开始增添的对JSR-330标准的支持,使用@Inject注解标记需要添加此jar包

Mysql-connector-java-5.1.8.bin.jar

Ojdbc5.jar

 

步骤八:使用注解将OracleUserDao声明为Bean, 并且注入到UserService中

1. 新建OracleUserDao实现UserDao接口,在该类中实现findByName方法, findByName方法调用JdbcDataSource的getConnection方法获取数据库连接. 使用注解@Repository将Oracle声明为存储组件, 并且设置组件ID为userDao, 这样便于自动注入到UserService对象中.

 

 

@Repository("userDao") //指定特定的Bean ID 方便setUserDAO注入

public class OracleUserDao implements UserDao, Serializable{

 

 

重构UserService类,在属性设置方法setUserDao()上使用注解@Resource, 这样Spring就会自动的将前一步声明的userDao对象注入到当前UserService对象中. userDao引用变量不再为null

 

 

 配置的方式可以使用Spring表达式的方式#{***.***}下面使用注解的方式

十:使用@Value将db.properties文件中的jdbc参数注入到JdbcDataSource

在src下新建db.properties文件,保存jdbc配置参数完整代码如下

Dirver=oracle.jdbc.OracleDriver

url=jdbc:oracle:thin:@localhost:1521:XE

user=openlab

pwd=open123

更新applicationContext.xml文件,将db.properties读取到Spring中代码片段如图所示

<util:properties id=”jdbcProps” location=”classPath:db.properties”/>

 

2. 重构JdbcDataSource类, 使用@Value和Spring表达式配合将db.properties文件中的JDBC配置信息注入到JdbcDataSource属性中, 其中driver属性一定在setDriver方法上声明, 否则不能正确注册JDBC Driver.

 

/** 组件注解 */

@Component

public class JdbcDataSource implements Serializable{

       

        private String driver;

       

        @Value("#{jdbcProps.url}")

        private String url;

       

        @Value("#{jdbcProps.user}")

        private String user;

       

        @Value("#{jdbcProps.pwd}")

        private String pwd;

       

        public String getDriver() {

               return driver;

        }

        /** 必须使用Bean属性输入, 否则不能进行JDBC Driver注册 */

        @Value("#{jdbcProps.driver}")

        public void setDriver(String driver) {

               try{

                       //注册数据库驱动

                       Class.forName(driver);

                       this.driver = driver;

               }catch(Exception e){

                       throw new RuntimeException(e);

               }

        }

 

 

 

. 添加MysqlUserDao类实现UserDao接口, 在MySQL上实现findByName方法,并且使用@Repository声明为存储组件, 在setDataSource方法上使用@Inject声明dataSource属性注入. 完整代码如下所示:

 

/** 持久层 注解  */

@Repository //指定特定的Bean ID

public class MysqlUserDao implements UserDao, Serializable{

       

        private JdbcDataSource dataSource;

       

        public MysqlUserDao() {

        }

 

        @Inject

        public void setDataSource(

                       @Named("jdbcDataSource")JdbcDataSource dataSource) {

               this.dataSource = dataSource;

        }

        public JdbcDataSource getDataSource() {

               return dataSource;

        }