随笔-124  评论-49  文章-56  trackbacks-0
IOC控制反转:应用本身不负责依赖对象的创建及维护,依赖对象的创建及维护是由外部容器负责的。
依赖注入:在运行期,由外部容器动态地将依赖对象注入到组件中。
-----------------------------------------------------------------------------
第一个项目
1    spring的依赖库
     * SPRING_HOME/dist/spring.jar
     * SPRING_HOME/lib/jakarta-commons/commons-logging.jar
     * SPRING_HOME/lib/log4j/log4j-1.2.14.jar
     如果使用了切面编程(AOP),还需要下列jar文件
     * SPRING_HOME/lib/aspectj/aspectjweaver.jar和aspectjrt.jar
     * SPRING_HOME/lib/cglib/cglib-nodep-2.1_3.jar
     如果使用了JSR-250的注解,如@Resource/@postConstruct/@preDestroy,还需要下列jar文件
     * SPRING_HOME/lib/j2ee/common-annotations.jar
2    拷贝spring配置文件到src下
3    拷贝log4j配置文件到src下
4(1) 在UserManager中提供构造函数,spring将实例化好的UserDao实现注入给我们
public class UserManagerImpl implements UserManager {
                
private UserDao userDao;
                
public UserManagerImpl(UserDao userDao){
                    
this.userDao=userDao;
                }

                
public void save(String username, String password) {
                    
this.userDao.save(username, password);
                }

          }
4(2) 在UserManager中提供set方法,spring将实例化好的UserDao实现注入给我们
public class UserManagerImpl implements UserManager {
                
private UserDao userDao;
                
public UserDao getUserDao() {
                    
return userDao;
                }

                
public void setUserDao(UserDao userDao) {
                    
this.userDao = userDao;
                }

                
public void save(String username, String password) {
                    
this.userDao.save(username, password);
                }

         }
5    让spring管理我们的对象创建和依赖,必须在spring配置文件中(applicationContext.xml)进行定义
     * 构造函数
<bean id="userDao4MySqlImpl" class="com.my.spring.dao.UserDao4MySqlImpl"/>
       
<bean id="userDao4OracleImpl" class="com.my.spring.dao.UserDao4OracleImpl"/>
       
<bean id="userManagerImpl" class="com.my.spring.manager.UserManagerImpl">
            
<constructor-arg ref="userDao4MySqlImpl"/>
            //
<constructor-arg index="0" type="com.my.spring.dao.UserDao4OracleImpl" ref="userDao4MySqlImpl"/>
       
</bean>
       * set方法
       方法一:
       
<bean id="userDao4MySqlImpl" class="com.my.spring.dao.UserDao4MySqlImpl"/>
       
<bean id="userDao4OracleImpl" class="com.my.spring.dao.UserDao4OracleImpl"/>
       
<bean id="userManagerImpl" class="com.my.spring.manager.UserManagerImpl">
            
<property name="userDao" ref="userDao4OracleImpl"/>
       
</bean>
       方法二(使用内部bean)
       
<bean id="userManagerImpl" class="com.my.spring.manager.UserManagerImpl">
            
<property name="userDao">
                 
<bean class="com.my.spring.manager.UserManagerImpl">
            
</property>
       
</bean>
* 注解方式
      1 头文件中必须加入
xmlns:context="http://www.springframework.org/schema/context"
          http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-2.5.xsd
          
<context:annotation-config/>//开启注解
2 在java代码中使用@Autowired或@Resource注解方式进行装配,它们区别是:
         * @Autowired默认按类型装配,默认情况下要求依赖对象必须存在,如果允许null值,可以设置它required为false,
         如果想使用按名称装配,可以结合@Qualifier注解一起使用,如下:
            @Autowired @Qualifier("userBean")
            private User user;
         * @Resource默认按名称装配,找不到匹配的bean才会按类型装配。它和@Autowired一样可以标注在字段或属性的setter方法上。
         可以通过name属性指定名称,如果没有指定name属性,当注解标注在字段上,即默认取字段的名称为name属性名称,当注注解
         标注在属性的setter方法上,即默认取属性名作为bean名称寻找依赖对象。
         注意:一旦指定了name属性,就只能按名称装配了。
            @Resource(name="userBean")
            private User user;
6    实例化spring容器并调用相关方法
     //ApplicationContext ctx=new ClassPathXmlApplicationContext(new String[]{"applicationContext.xml"});
     BeanFactory factory =new ClassPathXmlApplicationContext("applicationContext.xml");
7    获取bean
UserManager userManager=(UserManager)ctx.getBean("userManagerImpl");
       UserManager userManager
=(UserManager)factory.getBean("userManagerImpl");

8    调用业务码
    userManager.save("张三", "123");
spring IoC容器的关键点:
     * 必须将被管理的对象定义到spring配置文件中
     * 必须定义构造函数或setter方法,让spring将对象注入过来
手动添加schema文件,方法如下:
windows->preferences->myeclipse->files and editors->xml->xmlcatalog

-------------------------------------------------------------------------------------------------------------------
普通属性的注入
  *多个配置文件可以放入String[]数组中,调用factory=new ClassPathXmlApplicationContext(String[] array);
  *多个配置文件可以使用*通配符,(测试未成功)factory=new ClassPathXmlApplicationContext("applicationContext-*.xml");
  *可以将一个类分成多个配置文件进行配置,但id不能相同
示例:

Beans:
private String strValue;
    
private int intValue;
    
private List listValue;
    
private Set setValue;
    
private String[] arrayValue;
    
private Map mapValue;
    
private Properties properties;
applicationContext-beans.xml
<bean id="beans" class="com.my.spring.Beans">
        
<property name="strValue" value="Hello"/>
        
<property name="intValue">
            
<value>123</value>
        
</property>
        
<property name="listValue">
            
<list>
                
<value>list1</value>
                
<value>list2</value>
            
</list>
        
</property>
        
<property name="setValue">
            
<set>
                
<value>set1</value>
                
<value>set2</value>
            
</set>
        
</property>
        
<property name="arrayValue">
            
<list>
                
<value>array1</value>
                
<value>array2</value>
            
</list>
        
</property>
        
<property name="mapValue">
            
<map>
                
<entry key="k1" value="v1"/>
                
<entry key="k2" value="v2"/>
            
</map>
        
</property>
        
<property name="date">
            
<value>2008-08-15</value>
        
</property>
        
<property name="properties">
            
<props>
                
<prop key="key1">value1</prop>
                
<prop key="key2">value2</prop>
                
<prop key="key3">value3</prop>
            
</props>
        
</property>
    
</bean>
调用:
private BeanFactory factory=new ClassPathXmlApplicationContext("applicationContext-beans.xml");
        Beans b
=(Beans)factory.getBean("beans");
        System.out.println(b.getIntValue());
        System.out.println(b.getStrValue());
        System.out.println(b.getArrayValue());
        System.out.println(b.getListValue());
        System.out.println(b.getMapValue());
        System.out.println(b.getDate());

---------------------------------------------------------------------------------------------
自定义属性编辑器
*作用:将spring配置文件中的字符串转换成相应的对象进行注入
       spring已经有内置的属性编辑器,我们可以根据需求自己定义属性编辑器
*定义方法:
       1 继承PropertyEditorSupport类,复写setAsText()方法
       2 将属性编辑注册到spring中
1 编写自定义处理类
public class UtilDatePropertyEditor extends PropertyEditorSupport {
    
private String format="yyyy-MM-dd";
    @Override
    
public void setAsText(String text) throws IllegalArgumentException {
        SimpleDateFormat sdf
=new SimpleDateFormat(format);
        
try {
            Date d
=sdf.parse(text);
            
this.setValue(d);
        }
 catch (ParseException e) {
            
// TODO Auto-generated catch block
            e.printStackTrace();
        }

    }

    
public String getFormat() {
        
return format;
    }

    
public void setFormat(String format) {
        
this.format = format;
    }

}
2 配置apllicationContext-edition.xml
<bean id="customEditorConfigurer" class="org.springframework.beans.factory.config.CustomEditorConfigurer">
        
<property name="customEditors">
            
<map>
                
<entry key="java.util.Date">
                    
<bean class="com.my.spring.UtilDatePropertyEditor"/>
                
</entry>
            
</map>
        
</property>
</bean>
3 调用
String[] contexts=new String[]{"applicationContext-beans.xml","applicationContext-edition.xml"};
        factory
=new ClassPathXmlApplicationContext(contexts);

-----------------------------------------------------------------------------------------------------
公共属性的注入
依赖对象的注入方法,可以采用:
 * ref属性
 * <ref>标签
 * 内部<bean>来定义
<bean id="beans2" class="com.my.spring.Beans2">
        
<property name="beans3">
            
<ref bean="beans3"/>
        
</property>
        
<property name="beans4" ref="beans4"/>
        
<property name="beans5" ref="beans5"/>
</bean>
如何将公共的注入定义描述出来?
 * 通过<bean>标签定义的属性,指定abstract="true"
 * 具有相同属性的类在<bean>标签中指定其parent属性
<bean id="beanAbstract" abstract="true">
        
<property name="id" value="1000"/>
        
<property name="name" value="jack"/>
</bean>
    
<bean id="beans3" class="com.my.spring.Beans3" parent="beanAbstract">
        
<property name="password" value="8888"/>
</bean>

<bean id="beans4" class="com.my.spring.Beans4" parent="beanAbstract"/>

<bean id="beans2" class="com.my.spring.Beans2">
        
<property name="beans3">
            
<ref bean="beans3"/>
        
</property>
        
<property name="beans4" ref="beans4"/>
        
<property name="beans5" ref="beans5"/>
</bean>

<bean id="beans5" class="com.my.spring.Beans5">
        
<property name="age" value="123"/>
</bean>

--------------------------------------------------------------------------------------------------

Bean的作用域

scope可以取值:
  * singleton:每次调用getBean时返回相同的实例
  * prototype:每次调用getBean时返回不同的实例
 
<bean id="beans" class="com.my.spring.Beans" scope="singletion">
<bean id="beans" class="com.my.spring.Beans" scope="prototype">
--------------------------------------------------------------------------------------------------
自动装配
1 根据名称
  设置<beans>标签中default-autowire="byName"

<bean id="beanAbstract" abstract="true">
                
<property name="id" value="1000"/>
                
<property name="name" value="jack"/>
        
</bean>
        
<bean id="beans3" class="com.my.spring.Beans3" parent="beanAbstract">
                
<property name="password" value="8888"/>
        
</bean>
        
<bean id="beans4" class="com.my.spring.Beans4" parent="beanAbstract"/>
        
        
<bean id="beans2" class="com.my.spring.Beans2">
    
<!-- 可以省略,会按名称自动装配
                <property name="beans3">
                    <ref bean="beans3"/>
                </property>
                <property name="beans4" ref="beans4"/>
                <property name="beans5" ref="beans5"/>
    
-->
        
</bean>
        
        
<bean id="beans5" class="com.my.spring.Beans5">
                
<property name="age" value="123"/>
        
</bean>
2 根据类型
 设置<beans>标签中default-autowire="byType"
<bean id="beanAbstract" abstract="true">
                
<property name="id" value="1000"/>
                
<property name="name" value="jack"/>
        
</bean>
        
<bean id="beans33" class="com.my.spring.Beans3" parent="beanAbstract">
                
<property name="password" value="8888"/>
        
</bean>
        
<bean id="beans433" class="com.my.spring.Beans4" parent="beanAbstract"/>
        
        
<bean id="beans2" class="com.my.spring.Beans2">
    
<!-- 可以省略,会按类型自动装配
                <property name="beans3">
                    <ref bean="beans3"/>
                </property>
                <property name="beans4" ref="beans4"/>
                <property name="beans5" ref="beans5"/>
    
-->
        
</bean>
        
        
<bean id="beans523" class="com.my.spring.Beans5">
                
<property name="age" value="123"/>
        
</bean>

------------------------------------------------------------------------------------------

<Bean>属性
1 id为bean的名称,是唯一的
2 name也是为bean取名的,作用相同,区别是id中不能有"/"符号,name中可以有,如:
    * name="/login"
3 class是bean类的全名
4 init-method:bean的初始化方法
5 destroy-method:bean消灭时调用的方法

自动装配依赖对象,不建意使用[byType/byName]
<bean id="..." class="..." autowire="byType"/>

------------------------------------------------------------------------------------------------
注解方式

1 spring的依赖库
     * SPRING_HOME/dist/spring.jar
     * SPRING_HOME/lib/jakarta-commons/commons-logging.jar
     * SPRING_HOME/lib/log4j/log4j-1.2.14.jar
     如果使用了切面编程(AOP),还需要下列jar文件
     * SPRING_HOME/lib/aspectj/aspectjweaver.jar和aspectjrt.jar
     * SPRING_HOME/lib/cglib/cglib-nodep-2.1_3.jar
     如果使用了JSR-250的注解,如@Resource/@postConstruct/@preDestroy,还需要下列jar文件
     * SPRING_HOME/lib/j2ee/common-annotations.jar

手动添加schema文件,方法如下:
windows->preferences->myeclipse->files and editors->xml->xmlcatalog
文件在dist/resources目录下的spring-beans-2.5.xsd

2 applicationContext.xml

<?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-2.5.xsd
           http://www.springframework.org/schema/context
           http://www.springframework.org/schema/context/spring-context-2.5.xsd"
>
    
<context:annotation-config />//开启配置项

    
<bean id="personDao" class="org.spring.dao.impl.PersonDaoImpl"/>
</beans>
3 在java代码中使用@Autowired或@Resource注解方式进行装配,它们区别是:
  @Autowired默认按类型装配,@Resource默认按名称装配,当找不到与名称匹配的bean才会按类型装配
 
  # 用于字段上
  @Autowired
  private PersonDao personDao;
  # 用于属性的setter方法上
  @Autowired
  public void setPersonDao(PersonDao personDao){...}
         * @Autowired默认按类型装配,默认情况下要求依赖对象必须存在,如果允许null值,可以设置它required为false,
         如果想使用按名称装配,可以结合@Qualifier注解一起使用,如下:
            @Autowired @Qualifier("personDaoBean")
            private PersonDao personDao;
         * @Resource默认按名称装配,找不到匹配的bean才会按类型装配。它和@Autowired一样可以标注在字段或属性的setter方法上。
         可以通过name属性指定名称,如果没有指定name属性,当注解标注在字段上,即默认取字段的名称为name属性名称,当注注解
         标注在属性的setter方法上,即默认取属性名作为bean名称寻找依赖对象。
         注意:一旦指定了name属性,就只能按名称装配了。
            @Resource(name="personDao")
            private PersonDao personDao;
  例(继上):
public class PersonBizImpl implements IPersonBiz {
    @Resource[或@Resource(name
="personDao")]//指定bean的名称,和applicationContext.xml文件中bean名称相同
    private IPersonDao personDao;//可以不用写setter方法
    
    
//或者在属性的setter方法上
    
//@Resource
    
//public void setPersonDao(IPersonDao personDao) {
    
//    this.personDao = personDao;
    
//}

    
public void say(){
        personDao.say();
    }

  }

posted on 2009-11-30 08:58 junly 阅读(344) 评论(0)  编辑  收藏 所属分类: spring

只有注册用户登录后才能发表评论。


网站导航: