Spring实战-读书笔记(章节一、二)-Spring框架的目的以及装配Bean

Spring框架的目的

spring框架的目的和意义:让java开发变得简单。

spring提供四种核心策略实现这个目的:
1、不侵入POJO
2、使用依赖注入(DI)来实现对象之间保持松散耦合
3、使用面向切面(AOP)来确保POJO的简单性(不侵入POJO)
4、使用模板代码来消除样板代码(类如JdbcTemplet类,将JDBC API封装简化数据库的放问,将业务代码和JDBC代码分离)

装配Bean

Spring中装配Bean有三种方式:隐士的发现和装配Bean(自动装配)、javaConfig显式配置、XML配置文件显式配置,Spring容器的Bean都来自此三种方式。

自动装配

使用自动装配功能可分为三个步骤

  1. 开启自动扫描组件功能,配置一个或多个包名
  2. 扫描指定包下类标记@Component注解,Spring会将此类作为容器中的Bean
  3. 在依赖的字段、方法或构造方法上使用@Autowired注解标记

涉及的注解

对应第一个步骤:
@ComponentScan:表示启用组件扫描,默认会扫描配置类所在的包以及子包下的类,可以通过basePackPages指定多个包明。
@Configuraction:标记一个类为spring配置类。

对应第二个步骤:
@Component:标记的类作为组件类,spring会为此类创建一个bean,不指定bean名称spring会默认将类的首字母小写作为bean名称。
@Named:是java规范中的依赖注入注解,作用同Component,也可以被Spring识别。

对应第三个步骤:
@Autowired:标记在构造函数、set方法、字段上告诉spring自动装配策略注入依赖bean。
@Inject:是java规范中的依赖注入注解,作用同Component,也可以被Spring识别。
自动装配规则(仅供参考)
//spring自动装配策略规则:
//1,首先,检测到依赖类型仅仅有一个实现Bean,使用这个Bean注入
//2,其次,将字段名称、方法和构造函数上的形参名称作为bean id去匹配对应的Bean,使用这个Bean注入

代码事例

package com.zhangxy.chapter_2.autoconfig.main;

public interface CDPlayer {
	void paly();
}
package com.zhangxy.chapter_2.autoconfig.main;

public interface CompactDisc {
	void paly();
}
package com.zhangxy.chapter_2.autoconfig.main;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

@Component
public class MediaPlayer implements CDPlayer {

	private CompactDisc compactDisc;

	@Autowired
	public MediaPlayer(CompactDisc compactDisc) {
		this.compactDisc = compactDisc;
	}

	@Override
	public void paly() {
		System.out.println("MediaPlayer start paly");
	}
}
package com.zhangxy.chapter_2.autoconfig.main;

import org.springframework.stereotype.Component;

@Component
public class SgtPeppers implements CompactDisc {

	@Override
	public void paly() {
		System.out.println("SgtPeppers start paly");
	}
}
package com.zhangxy.chapter_2.autoconfig.main;

import org.springframework.context.annotation.ComponentScan;
import org.springframework.context.annotation.Configuration;

@Configuration
@ComponentScan(basePackages= {"com.zhangxy.chapter_2.autoconfig.main"})
public class CDPlayerConfig {
}
~~~~测试类~~~~:
package com.zhangxy.chapter_2.autoconfig.test;

import static org.junit.Assert.*;

import org.junit.Rule;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;

import com.zhangxy.chapter_2.autoconfig.main.CDPlayer;
import com.zhangxy.chapter_2.autoconfig.main.CDPlayerConfig;

import org.junit.contrib.java.lang.system.StandardOutputStreamLog;

@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(classes= {CDPlayerConfig.class})
public class CDPlayerTest {
	@Rule
	public final StandardOutputStreamLog log = new StandardOutputStreamLog();

	@Autowired
	private CDPlayer cdPlayer;
	
	@Test
	public void test() {
		cdPlayer.paly();
		assertEquals("MediaPlayer start paly\r\n" + 
				"", log.getLog());
	}
}

javaConfig显式配置

javaConfig显式配置通过java代码来配置Bean。此方式的配置主要是通过代码去理解。
涉及注解
@Bean:标记在一个方法告诉spring方法的返回对象将最为spring上下文中的bean,可以通过name属性可以指定Bean的名称,默认的已方法名作为bean名称。

代码事例

package com.zhangxy.chapter_2.javaconfig.main;

public interface CDPlayer {
	void paly();
}
package com.zhangxy.chapter_2.javaconfig.main;

public interface CompactDisc {
	void paly();
}
package com.zhangxy.chapter_2.javaconfig.main;

public class MediaPlayer implements CDPlayer {

	private CompactDisc compactDisc;

	public MediaPlayer(CompactDisc compactDisc) {
		this.compactDisc = compactDisc;
	}

	@Override
	public void paly() {
		System.out.println("MediaPlayer start paly");
	}
}
package com.zhangxy.chapter_2.javaconfig.main;

public class SgtPeppers implements CompactDisc {
	@Override
	public void paly() {
		System.out.println("SgtPeppers start paly");
	}
}
~~~~测试~~~~
package com.zhangxy.chapter_2.javaconfig.test;

import static org.junit.Assert.*;

import org.junit.Rule;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;

import com.zhangxy.chapter_2.javaconfig.main.CDPlayer;
import com.zhangxy.chapter_2.javaconfig.main.CDPlayerConfig;

import org.junit.contrib.java.lang.system.StandardOutputStreamLog;

@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(classes= {CDPlayerConfig.class})
public class CDPlayerTest {
	@Rule
	public final StandardOutputStreamLog log = new StandardOutputStreamLog();

	@Autowired
	private CDPlayer cdPlayer;
	
	@Test
	public void test() {
		cdPlayer.paly();
		assertEquals("MediaPlayer start paly\r\n" + 
				"", log.getLog());
	}
}
注意:MediaPlayer和SgtPeppers没有标记@Component注解,CDPlayerConfig类也没有使用@ComponentScan注解开启自动扫描组件。

XML配置文件显示配置

XML配置文件显示配置是通过XML来配置Bean。此方式主要是通过XML配置去理解。以上两种方式都是通过在字段、set方法和构造函数上使用注解@AutoWired来注入依赖的Bean。在XML中如何注入依赖的Bean呢???

通过构造函数来注入依赖的bean

a,构造函数引用类型注入
<constructor-arg ref="bean id"/>
<c:形参名称-ref="bean id"/>
<c:_0-ref="bean id"/>
b,构造函数字面量注入
<constructor-arg value="ABC">
<c:形参名称="ABC"/>
<c:_0="ABC"/>
c,构造函数集合类型注入
c.1,String类型集合
<constructor-arg>
<list>
<value>ABC</value>
<value>ABC</value>
</list>
</constructor-arg>
c.2,引用类型集合
<constructor-arg>
<list>
<ref bean="bean id"/>
<ref bean="bean id"/>
</list>
</constructor-arg>
以上元素都是<bean>元素的子元素。

属性注入

a,属性引用类型注入
<property name="属性名称" ref="bean id"/>
<p:属性名称-ref="bean id"/>
b,属性字面量注入
<property name="属性名称" ref="ABC"/>
<p:属性名称="ABC"/>
事例代码
参照下一个章节事例代码。

javaConfig、XML配置文件互相引用

我们可以通过javaConfig方式配置一部分Bean,在通过XML配置方法配置一部分Bean,那我们如何在javaConfig配置中引用XML配置的Bean???如果在XML配置中引用javaConfig的Bean???开启组件扫描产生的Bean我们在javaConfig和XML配置可以直接通过Bean id引用。

javaConfig配置中引用XML配置的Bean

涉及注解
@ImportResource:引用XML配置文件,作用在javaConfig类上。
@Import:应用其它javaConfig类,作用在javaConfig类上。
事例代码
package com.zhangxy.chapter_2.mixedconfig.importXmlConfig.main;

public interface CompactDisc {
  void play();
}
package com.zhangxy.chapter_2.mixedconfig.importXmlConfig.main;

public interface MediaPlayer {
  void play();
}
package com.zhangxy.chapter_2.mixedconfig.importXmlConfig.main;
import org.springframework.beans.factory.annotation.Autowired;

public class CDPlayer implements MediaPlayer {
  private CompactDisc cd;

  @Autowired
  public CDPlayer(CompactDisc cd) {
    this.cd = cd;
  }

  public void play() {
    cd.play();
  }

}

package com.zhangxy.chapter_2.mixedconfig.importXmlConfig.main;

import java.util.List;

public class BlankDisc implements CompactDisc {

  private String title;
  private String artist;
  private List<String> tracks;

  public BlankDisc(String title, String artist, List<String> tracks) {
    this.title = title;
    this.artist = artist;
    this.tracks = tracks;
  }

  public void play() {
    System.out.println("Playing " + title + " by " + artist);
    for (String track : tracks) {
      System.out.println("-Track: " + track);
    }
  }

}
package com.zhangxy.chapter_2.mixedconfig.importXmlConfig.main;

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

@Configuration
public class CDPlayerConfig {
	
	@Bean
	public MediaPlayer cdPlayer(CompactDisc blankDisc) {
		return new CDPlayer(blankDisc);
	}
}
package com.zhangxy.chapter_2.mixedconfig.importXmlConfig.main;

import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Import;
import org.springframework.context.annotation.ImportResource;

@Configuration
@Import(CDPlayerConfig.class)
@ImportResource("classpath:com\\zhangxy\\chapter_2\\mixedconfig\\importXmlConfig\\main\\blankDisc-config.xml")
public class SystemConfig {
	
}
<?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:p="http://www.springframework.org/schema/p"
  xmlns:util="http://www.springframework.org/schema/util"
  xsi:schemaLocation="http://www.springframework.org/schema/beans 
    http://www.springframework.org/schema/beans/spring-beans.xsd
    http://www.springframework.org/schema/util 
    http://www.springframework.org/schema/util/spring-util.xsd">
    
	<bean id="blankDisc"
		class="com.zhangxy.chapter_2.mixedconfig.importXmlConfig.main.BlankDisc">
		<constructor-arg value="如果这都不算爱" />
		<constructor-arg value="张学友"></constructor-arg>
		<constructor-arg ref="tracks"></constructor-arg>
	</bean>

	<util:list id="tracks">
		<value>A</value>
		<value>B</value>
	</util:list>

</beans>
~~~~测试类~~~~
package com.zhangxy.chapter_2.mixedconfig.importXmlConfig.test;

import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;

import com.zhangxy.chapter_2.mixedconfig.importXmlConfig.main.MediaPlayer;
import com.zhangxy.chapter_2.mixedconfig.importXmlConfig.main.SystemConfig;

@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(classes = { SystemConfig.class })
public class ImportXMLConfigTest {

	@Autowired
	private MediaPlayer mediaPlayer;

	@Test
	public void test() {
		mediaPlayer.play();
	}

}
在XML配置中引用javaConfig的Bean
将javaConfig类在XML配置文件中配置成一个Bean即可。
事例代码
package com.zhangxy.chapter_2.mixedconfig.importJavaConfig.main;

public interface CompactDisc {
  void play();
}
package com.zhangxy.chapter_2.mixedconfig.importJavaConfig.main;

public interface MediaPlayer {
  void play();
}
package com.zhangxy.chapter_2.mixedconfig.importJavaConfig.main;

import java.util.List;

public class BlankDisc implements CompactDisc {

  private String title;
  private String artist;
  private List<String> tracks;

  public BlankDisc(String title, String artist, List<String> tracks) {
    this.title = title;
    this.artist = artist;
    this.tracks = tracks;
  }

  public void play() {
    System.out.println("Playing " + title + " by " + artist);
    for (String track : tracks) {
      System.out.println("-Track: " + track);
    }
  }

}
package com.zhangxy.chapter_2.mixedconfig.importJavaConfig.main;

public class CDPlayer implements MediaPlayer {
  private CompactDisc cd;

  public CDPlayer(CompactDisc cd) {
    this.cd = cd;
  }

  public void play() {
    cd.play();
  }

}
package com.zhangxy.chapter_2.mixedconfig.importJavaConfig.main;

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

@Configuration
public class CDPlayerConfig {
	
	@Bean
	public MediaPlayer cdPlayer(CompactDisc blankDisc) {
		return new CDPlayer(blankDisc);
	}
}
package com.zhangxy.chapter_2.mixedconfig.importJavaConfig.main;

import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Import;

@Configuration
@Import(CDPlayerConfig.class)
public class SystemConfig {
	
}
<?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:p="http://www.springframework.org/schema/p"
  xmlns:util="http://www.springframework.org/schema/util"
  xsi:schemaLocation="http://www.springframework.org/schema/beans 
    http://www.springframework.org/schema/beans/spring-beans.xsd
    http://www.springframework.org/schema/util 
    http://www.springframework.org/schema/util/spring-util.xsd">
    
    
	<bean id="blankDisc"
		class="com.zhangxy.chapter_2.mixedconfig.importJavaConfig.main.BlankDisc">
		<constructor-arg value="如果这都不算爱" />
		<constructor-arg value="张学友"></constructor-arg>
		<constructor-arg ref="tracks"></constructor-arg>
	</bean>

	<util:list id="tracks">
		<value>A</value>
		<value>B</value>
	</util:list>

    <bean class="com.zhangxy.chapter_2.mixedconfig.importJavaConfig.main.SystemConfig"></bean>
</beans>

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值