Upload
sungchul-park
View
2.815
Download
8
Embed Size (px)
DESCRIPTION
사내에서 진행 된 스프링 웹 애플리케이션 개발 과정 중 스프링 코어 부분의 두번째 발표 자료입니다.
Citation preview
스프링 프레임워크 코어Java 구성을 활용한 스프링 코어 사용
박성철
목차
기본 빈(Bean) 정의
오토 와이어 / 컴포넌트 자동 탐색
AOP 설정
기본 빈(Bean) 정의
빈 정의 방법
XML 구성가장 오래된 빈 설정 방법메타 정보의 완벽한 분리
자바 구성어노테이션 방식과 의미론적 일관성언어 지원 타입 안전성 IDE
그루비 빈 구성아직 초기 단계자바 구성보다 가독성 개선(그루비
“우리의 선택”
@Configuration
@Configuration����������� ������������������
public����������� ������������������ class����������� ������������������ AppConfig����������� ������������������ {����������� ������������������
����������� ������������������ ����������� ������������������ ����������� ������������������ …⋯����������� ������������������
}
“이 클래스는
빈을 정의하는 객체도 스프링 빈
빈 생성: @Bean
@Configuration����������� ������������������
public����������� ������������������ class����������� ������������������ AppConfig����������� ������������������ {����������� ������������������
����������� ������������������ ����������� ������������������ ����������� ������������������ @Bean����������� ������������������
����������� ������������������ ����������� ������������������ ����������� ������������������ public����������� ������������������ AcmeBean����������� ������������������ acmeBean()����������� ������������������ {����������� ������������������
����������� ������������������ ����������� ������������������ ����������� ������������������ ����������� ������������������ ����������� ������������������ ����������� ������������������ return����������� ������������������ new����������� ������������������ AcmeBean();����������� ������������������
����������� ������������������ ����������� ������������������ ����������� ������������������ }����������� ������������������
}
“이 메서드는
@Bean(name=“acmeBean”)����������� ������������������
@Bean(name={“acmeBean”,����������� ������������������ “superBean”})
명시적인 빈 이름 지정빈 별명 지정
스프링 IoC 컨테이너
BeanFactory: 기본 빈 컨테이너
ApplicationContext
하부 타입
AOP, 국제화, 이벤트 발생기업용 애플리케이션에 필요한 기능 추가
ApplicationContext 종류
AnnotationConfigApplicationContextAnnotationConfigWebApplicationContextClassPathXmlApplicationContextFileSystemXmlApplicationContextGenericApplicationContextGenericGroovyApplicationContextGenericWebApplicationContextGenericXmlApplicationContextResourceAdapterApplicationContextXmlPortletApplicationContextXmlWebApplicationContext
우리가 사용할컨테이너 구현체
ApplicationContext 시작
ctx����������� ������������������ =����������� ������������������ new����������� ������������������ AnnotationConfigApplicationContext(AppConfig
!또는
!ctx����������� ������������������ =����������� ������������������ new����������� ������������������ AnnotationConfigApplicationContext(
ctx.register(AppConfig.class,����������� ������������������ AnotherAppConfig.class);
ctx.register(YetAnotherAppConfig
의존 관계 주입매개변수 전달
@Bean����������� ������������������
public����������� ������������������ Teller����������� ������������������ teller(ContentProvider����������� ������������������ provider
����������� ������������������ return����������� ������������������ new����������� ������������������ StdOutTeller(provider
}����������� ������������������
!@Bean����������� ������������������
public����������� ������������������ ContentProvider����������� ������������������ contentProvider()����������� ������������������ {����������� ������������������
����������� ������������������ return����������� ������������������ new����������� ������������������ HelloWorldProvider();����������� ������������������
}
의존 관계 주입메서드 호출
@Bean����������� ������������������
public����������� ������������������ Teller����������� ������������������ teller()����������� ������������������ {����������� ������������������
����������� ������������������ return����������� ������������������ new����������� ������������������ StdOutTeller(contentProvider()
}����������� ������������������
!@Bean����������� ������������������
public����������� ������������������ ContentProvider����������� ������������������ contentProvider()����������� ������������������ {����������� ������������������
����������� ������������������ return����������� ������������������ new����������� ������������������ HelloWorldProvider();����������� ������������������
}
구성 결합: @Import
@Configuration����������� ������������������
@Import(SubAppConfig.class)����������� ������������������
public����������� ������������������ class����������� ������������������ MainAppConfig����������� ������������������ {����������� ������������������
����������� ������������������ ����������� ������������������ ����������� ������������������ …⋯����������� ������������������
}����������� ������������������
!@Configuration����������� ������������������
public����������� ������������������ class����������� ������������������ SubAppConfig����������� ������������������ {����������� ������������������
����������� ������������������ ����������� ������������������ ����������� ������������������ …⋯����������� ������������������
}
빈 범위: @Scope
ConfigurableBeanFactory
SCOPE_SINGLETON “singleton”
SCOPE_PROTOTYPE “prototype”
WebApplicationContext
SCOPE_REQUEST “request”
SCOPE_SESSION “session”
SCOPE_GLOBAL_SESSION “globalSession”
SCOPE_APPLICATION “application"
@Bean
@Scope(“prototype”)
public����������� ������������������ ContentProvider����������� ������������������ contentProvider()����������� ������������������ {����������� ������������������
����������� ������������������ return����������� ������������������ new����������� ������������������ HelloWorldProvider();����������� ������������������
}
빈 범위의 종류A
pplic
atio
n C
ont
ext
singleton prototype request session
getBean()
항상 동일한 빈 반환
매번 새로운 빈 반환
웹 요청 안에 동일한 빈 반환
웹 세션 안에 동일한 빈 반환
표준 범위 웹 확장 범위
@Bean(iniMethod=“init”,����������� ������������������ destoryMethod=“dispose”)����������� ������������������
public����������� ������������������ AcmeBean����������� ������������������ acmeBean()����������� ������������������ {����������� ������������������
����������� ������������������ ����������� ������������������ ����������� ������������������ ����������� ������������������ ����������� ������������������ ����������� ������������������ return����������� ������������������ new����������� ������������������ AcmeBean();����������� ������������������
}
@Bean!
initMethoddestoryMethod
빈을 생성한 후에 init() 메서드를 호출하고 소멸 전에 dispose()
빈 초기화/정리@Bean의 속성 사용
빈 초기화/정리JSR-250 사용
@PostConstruct����������� ������������������
public����������� ������������������ void����������� ������������������ init()����������� ������������������ {����������� ������������������
����������� ������������������ ����������� ������������������ ����������� ������������������ …⋯����������� ������������������
}����������� ������������������
!@PreDestory����������� ������������������
public����������� ������������������ void����������� ������������������ dispose()����������� ������������������ {����������� ������������������
����������� ������������������ ����������� ������������������ ����������� ������������������ …⋯����������� ������������������
}
빈의 초기화와 정리 메서드에 직접 !
@PostConstruct@PreDestory
빈을 생성한 후에 init() 메서드를 호출하고
소멸 전에 dispose()
자동 구성
자동 와이어링
스프링 고유
@Autowired:����������� ������������������
@Qualifier:����������� ������������������
JSR-330 Dependency Injection for Java
@Inject:����������� ������������������
@Named:����������� ������������������
@Qualifier:����������� ������������������
JSR
@Resource:����������� ������������������
JSR-330
<dependency>����������� ������������������
����������� ������������������ ����������� ������������������ ����������� ������������������ ����������� ������������������ <groupId>javax.inject</groupId>����������� ������������������
����������� ������������������ ����������� ������������������ ����������� ������������������ ����������� ������������������ <artifactId>javax.inject</artifactId>����������� ������������������
����������� ������������������ ����������� ������������������ ����������� ������������������ ����������� ������������������ <version>1</version>����������� ������������������
</dependency>
@Autowired vs @Inject
spring JSR-330 비고@Autowired @Inject @Inject에는 required 속성이 없음@Component @Named
@Scope @Singleton JSR-330 표준에선 prototype이 기본이지만 스프링에서는 singleton을 기본으로 적용
@Qualifier @Named 빈 이름 지정@Qualifier @Qualifier 자작 한정 어노테이션 제작
@Value N/A@Required N/A
@Lazy N/A
자동 와이어링
public����������� ������������������ class����������� ������������������ Foo����������� ������������������ {����������� ������������������
����������� ������������������ ����������� ������������������ @Inject����������� ������������������
����������� ������������������ ����������� ������������������ private����������� ������������������ Bar����������� ������������������ bar;����������� ������������������
����������� ������������������ ����������� ������������������ …⋯����������� ������������������
}
@Bean����������� ������������������
public����������� ������������������ Foo����������� ������������������ foo()����������� ������������������ {����������� ������������������
����������� ������������������ return����������� ������������������ new����������� ������������������ Foo();����������� ������������������
}����������� ������������������
!@Bean����������� ������������������
public����������� ������������������ Bar����������� ������������������ bar()����������� ������������������ {����������� ������������������
����������� ������������������ return����������� ������������������ new����������� ������������������ Bar();����������� ������������������
}
빈 생성/등록
스프링 IoC 컨테이너
주입
빈 생성
자동 와이어링 이름 지정
public����������� ������������������ class����������� ������������������ Foo����������� ������������������ {����������� ������������������
����������� ������������������ ����������� ������������������ @Inject����������� ������������������
����������� ������������������ ����������� ������������������ @Named(“baar”)����������� ������������������
����������� ������������������ ����������� ������������������ private����������� ������������������ Bar����������� ������������������ bar;����������� ������������������
����������� ������������������ }
public����������� ������������������ class����������� ������������������ Bar{����������� ������������������
����������� ������������������ ����������� ������������������ ����������� ������������������ …⋯����������� ������������������
}
public����������� ������������������ class����������� ������������������ Baar����������� ������������������ extends����������� ������������������ Bar{����������� ������������������
����������� ������������������ ����������� ������������������ ����������� ������������������ …⋯����������� ������������������
}
public����������� ������������������ class����������� ������������������ Barr����������� ������������������ extends����������� ������������������ Bar{����������� ������������������
����������� ������������������ ����������� ������������������ ����������� ������������������ …⋯����������� ������������������
}
자동 빈 탐색@ComponentScan
@Configuration����������� ������������������
@ComponentScan(basePackages=“com.fupfin.acmebomb.domain”)����������� ������������������
public����������� ������������������ class����������� ������������������ AppConfig����������� ������������������ {����������� ������������������
����������� ������������������ ����������� ������������������ ����������� ������������������ …⋯����������� ������������������
}
지정한 패키지 밑의 모든 빈을 자동으로 찾아서 애플리케이션 컨텍스트에 등록
자동?
빈 지정@Component, @Named
@Component����������� ������������������
public����������� ������������������ class����������� ������������������ ThisIsBean����������� ������������������ {����������� ������������������
����������� ������������������ ����������� ������������������ ����������� ������������������ …⋯����������� ������������������
}
“이 객체는 스프링 빈입니다.”
@Component
JSR-330
빈 표시 어노테이션
@Component
@Service
@Controller
@Repository
비즈니스 로직을 처리하는 컴포넌트애플리케이션 아키텍처 참
데이터를 읽고 쓰는 컴포넌트
DataAccessException 애플리케이션 아키텍처 참
MVC
상속
상속
상속
@Configuration
@ComponentScan 속성
• basePackageClasses����������� ������������������ • basePackages����������� ������������������ =����������� ������������������ value����������� ������������������ • includeFilters,����������� ������������������ excludeFilters����������� ������������������
• FilterType• nameGenerator����������� ������������������ • resourcePattern����������� ������������������ • useDefaultFilters
@ComponentScan(basePackageClasses����������� ������������������ =����������� ������������������ BeansPackageMarker.class,����������� ������������������ ����������� ������������������ ����������� ������������������ ����������� ������������������ ����������� ������������������ ����������� ������������������ ����������� ������������������ ����������� ������������������
지연 생성: @Lazy의존 빈 지정: @DependsOn
@Service����������� ������������������
@Lazy����������� ������������������
@DependsOn({“AnotherService”,����������� ������������������ “YetAnotherService”})����������� ������������������
public����������� ������������������ class����������� ������������������ MyServiceImpl����������� ������������������ implements����������� ������������������ MyService����������� ������������������ {����������� ������������������
����������� ������������������ ����������� ������������������ ����������� ������������������ …⋯����������� ������������������
}
“정말 필요할 때까지는 빈을 생성하지 않아요.”
“이 빈들을 먼저 생성해야 해요.”
관점 중심 프로그래밍(AOP)
AOP
OOP
횡단 관심사의 모듈화
DI
스프링은 동적 프록시 기반의
JDK
@AspectJ
AspectJ 방식 AOP 활성화@EnableAspectJAutoProxy
@Configuration����������� ������������������ @ComponentScan(basePackages="com.fupfin.aop")����������� ������������������ @EnableAspectJAutoProxy����������� ������������������ public����������� ������������������ class����������� ������������������ AppConfig����������� ������������������ {����������� ������������������ ����������� ������������������ ����������� ������������������ ����������� ������������������ …⋯����������� ������������������ }
<dependency>����������� ������������������ ����������� ������������������ ����������� ������������������ <groupId>org.aspectj</groupId>����������� ������������������ ����������� ������������������ ����������� ������������������ <artifactId>aspectjweaver</artifactId>����������� ������������������ ����������� ������������������ ����������� ������������������ <version>1.5.4</version>����������� ������������������ </dependency>
AOP 모듈 정의: @Aspect
해당 클래스가
일반 자바 코드를
@Aspect����������� ������������������
@Component
public����������� ������������������ class����������� ������������������ AcmeAspect����������� ������������������ {����������� ������������������
����������� ������������������ ����������� ������������������ ����������� ������������������ …⋯����������� ������������������
}
자동 등록되도록 하려고
추가함
어드바이스 정의: @Advice
대상
@Aspect����������� ������������������
public����������� ������������������ class����������� ������������������ AcmeAspect����������� ������������������ {
����������� ������������������ ����������� ������������������ ����������� ������������������ @
����������� ������������������ ����������� ������������������ ����������� ������������������ public����������� ������������������ void����������� ������������������ doSomeBefore()����������� ������������������ {����������� ������������������
����������� ������������������ ����������� ������������������ ����������� ������������������ ����������� ������������������ ����������� ������������������ ����������� ������������������ System.out.println(System.currentTimeMillis
����������� ������������������ ����������� ������������������ ����������� ������������������ }����������� ������������������
}
적용 시점기능
대상(포인트컷)
@Advice 시점 종류
@Before
@After
@AfterReturning
@AfterThrowing
@Around
@Before & @After조인 포인트 속성 외에 특별한 속성 없음
메서드 매개변수에 JoinPoint 조인포인트 정보 전달
@Before(“execution(*����������� ������������������ set*(..))
public����������� ������������������ void����������� ������������������ doSomeBefore()����������� ������������������ {����������� ������������������
����������� ������������������ ����������� ������������������ ����������� ������������������ …⋯����������� ������������������
}����������� ������������������
!@After(“execution(*����������� ������������������ set*(..))
public����������� ������������������ void����������� ������������������ doSomeAfter
����������� ������������������ ����������� ������������������ ����������� ������������������ …⋯����������� ������������������
}
조인포인트 정보
@AfterReturning@AfterThrowing
@AfterReturning의 returning 속성에 반환값을 받는 매개변수 지정 가능
@AfterThrowing의 throwing 가능
@AfterReturning(pointcut=“execution(*����������� ������������������ set*(..))
public����������� ������������������ void����������� ������������������ doSomeAfter(Object����������� ������������������ retVal)����������� ������������������ {����������� ������������������
����������� ������������������ ����������� ������������������ ����������� ������������������ …⋯����������� ������������������
}����������� ������������������
!@AfterThrowing(pointcut=“execution(*����������� ������������������ set*(..))
public����������� ������������������ void����������� ������������������ doSomeAfter(Exception����������� ������������������ ex)����������� ������������������ {����������� ������������������
����������� ������������������ ����������� ������������������ ����������� ������������������ …⋯����������� ������������������
}
반환 값
예외
@Around
ProceedingJoinPoint 타입의 매개변수에 ProceedingJoinPoint실행할 수 있도록 함
@Around(pointcut=“execution(*����������� ������������������ set*(..))
public����������� ������������������ Object����������� ������������������ doSomethingAround(ProceedingJoinPoint����������� ������������������ thisJoinPoint)
����������� ������������������ ����������� ������������������ ����������� ������������������ //����������� ������������������ do����������� ������������������ something����������� ������������������ before����������� ������������������ call����������� ������������������ target����������� ������������������ method����������� ������������������
����������� ������������������ ����������� ������������������ ����������� ������������������ Object����������� ������������������ retval����������� ������������������ =����������� ������������������ thisJoinPoint.proceed();����������� ������������������
����������� ������������������ ����������� ������������������ ����������� ������������������ //����������� ������������������ do����������� ������������������ something����������� ������������������ after����������� ������������������ calling����������� ������������������ target����������� ������������������ method����������� ������������������
����������� ������������������ ����������� ������������������ ����������� ������������������ …⋯����������� ������������������
����������� ������������������ ����������� ������������������ ����������� ������������������ return����������� ������������������ retval;����������� ������������������
}
대상 메서드를 실행하고반환 값을 받음
반환 값 반환
대상 메서드 지정 분리: @Pointcut
@Pointcut(“execution(*����������� ������������������ *(..))”)����������� ������������������
public����������� ������������������ void����������� ������������������ ifService()����������� ������������������ {}����������� ������������������
!@Before(pointcut=“ifService()”)����������� ������������������
public����������� ������������������ void����������� ������������������ doSomeBefore()����������� ������������������ {����������� ������������������
����������� ������������������ ����������� ������������������ ����������� ������������������ …⋯����������� ������������������
}
포인트컷 표현execution
within
this
target
args
@target
@args
@within
@annotation
execution
execution([throws����������� ������������������
public, private
반환값
패키지와 클래스 이름
매서드 이름
매개변수
예외
execution(public����������� ������������������ *����������� ������������������ *(..))execution(*����������� ������������������ set*(..))execution(*����������� ������������������ com.xyz.service..*
기타
@Enable*
@EnableTransactionManagement
@EnableCaching
@EnableWebMvc
@EnableScheduling
@EnableAsync
@EnableAspectJAutoProxy
@EnableLoadTimeWeaving
@EnableSpringConfigured
@PropertySource
@Configuration����������� ������������������
@PropertySource(value����������� ������������������ =����������� ������������������ "classpath:META-INF/config.xml")����������� ������������������
public����������� ������������������ class����������� ������������������ PropertySourcesConfiguration����������� ������������������ {����������� ������������������
}����������� ������������������
!!@Configuration����������� ������������������
@PropertySource(value����������� ������������������ =����������� ������������������ "classpath:META-INF/config.properties")����������� ������������������
public����������� ������������������ class����������� ������������������ PropertySourcesConfiguration����������� ������������������ {����������� ������������������
}
“XML 파일로
“Properties 파일로
@Profile
@Configuration
class����������� ������������������ DataAccessConfig����������� ������������������ {����������� ������������������
!����������� ������������������ ����������� ������������������ @Configuration����������� ������������������
����������� ������������������ ����������� ������������������ @Profile({"JPA"})����������� ������������������
����������� ������������������ ����������� ������������������ public����������� ������������������ static����������� ������������������ class����������� ������������������ JPAConfig����������� ������������������ {����������� ������������������ …⋯����������� ������������������ }����������� ������������������
!����������� ������������������ ����������� ������������������ @Bean����������� ������������������
����������� ������������������ ����������� ������������������ @Profile("TEST
����������� ������������������ ����������� ������������������ public����������� ������������������ DataSource����������� ������������������ embeddedDatabase
!}
“JPA
@Profile
AnnotationConfigApplicationContext����������� ������������������ applicationContext����������� ������������������ =����������� ������������������ new����������� ������������������ A…⋯Context();����������� ������������������
applicationContext.register(DataAccessConfig.class);����������� ������������������
!ConfigurableEnvironment����������� ������������������ environment����������� ������������������ =����������� ������������������ applicationContext.getEnvironment();����������� ������������������
environment.setActiveProfiles(Profiles.JPA,����������� ������������������ Profiles.TEST
“JPA, TEST