Spring에서 지원하는 ServletContextAware를 구현(implements)하면 거의 거져 먹여주는 꼴이다.

 

@Controller
public class TestController implements ServletContextAware{
	@Override
	public void setServletContext(ServletContext servletContext) {
		this.servletContext = servletContext;
	}
}

 

'프로그래밍 > Spring' 카테고리의 다른 글

Spring | collection & association  (0) 2020.12.24
Spring | AOP  (0) 2020.12.23
Spring - DI  (0) 2020.12.22

 

위의 emp는 dept의 deptno를 외래키로 참조하는 테이블이다.

내부조인 : select * from dept left outer emp e join on d.deptno = e.deptno;

외부조인 : select * from dept d left outer join emp e on d.deptno = e.deptno;

와 같이 SQL쿼리를 사용하여 조인할 수 있다. 

 

이렇게 값을 얻어서 VO에 넣어서 저장하기가 애매(?)할 수가 있다.

 

Mybatis를 이용하여 조인을 처리하여 VO의 저장할 수 있는 방법이 있다.

 

collection1:多관계에서 쓰이는 방법으로 부모의 레코드를 뽑아내면서 해당 레코드를 참조하는 자식의 레코드들을 뽑아낼 수 있다. -> 어떻게보면 이중포문과 비슷하다고 생각이 들 수 있다.

 

사용하게되는 태그 resultMap과 select면 된다.

resultMap은 select태그의 속성 중 resultMap이라는 속성이 존재한다.

resultMap을 먼저 선언한 뒤, select에서 참조하는 방법이다.

<!-- 조인 시 VO가 두개의 컬럼을 감당할 수 있어야함...  -->
	<!-- 쿼리결과와 객체간 매핑을 자동으로 하는 것이 아니라, 
	개발자가 주도하여 처리를 하고 싶을때는 별도의 매핑을 선언.. -->
	<!-- 매핑의 커스터마이징 -->
	<resultMap type="Dept" id="deptJoinEmp">
	<!-- column=query에서 뽑아진 컬럼명 -->
		<id column="deptno" property="deptno"/><!-- primary key -->
		<result column="dname" property="dname"/><!-- 일반컬럼 -->
		<result column="loc" property="loc"/>
		<!-- 부서정보가져오고 부서정보에 포함되는 외부에 있는 부서원정보가져오기-->
		<!-- Emp(ofType)로 구성된  List(javaType)-->
		<!-- deptno컬럼을 가져오겠다. -->
		<!-- propery는 set메서드를 생각 -->
		<collection column="deptno" javaType="java.util.List" ofType="Emp" select="Emp.select"  property="empList"/>
	</resultMap>
	<!-- 이중포문과 비슷 dept정보를 가져올 때 그 정보를 가지고 emp정보를 가져오고 다음 dept가져오면 그 dept에 대한 emp를 뽑아온다. -->
	<select id="selectAll" resultMap="deptJoinEmp">
		select deptno, dname, loc from dept 
	</select>
	

resultMap은 매핑을 개발자가 커스터마이징하여 내가 만든 VO에 맞게 조인할 수 있다.

resultMap태그의 속성 중 type은 만들 VO객체를 말하고 id는 select에서 참조할 수 있게 이름을 지어주는 것이다.

id는 테이블의 primary key를 매핑하는 것이고, result는 일반 컬럼들을 매핑하는 것이다.

위 태그의 속성 중 column은 쿼리로 뽑아배는 레코드의 컬럼을 말하고, property는 VO객체의 set메서드를 말한다.

collection의 속성 중 javaType은 만들 자료형을 말하고 ofType은 javaType이 List와 같은 제네릭형일 때 자료형을 정해준다. select는 자식의 Mapper에서의 사용할 쿼리id를 말한다.

 

<resultMap id="empJoinDept" type="Emp" >
		<id column="empno" property="empno"/><!-- primary key -->
		<result column="ename" property="ename"/>
		<result column="job" property="job"/>
		<result column="mgr" property="mgr"/>
		<result column="hiredate" property="hiredate"/>
		<result column="sal" property="sal"/>
		<result column="comm" property="comm"/>
		<!-- 자식관점에서는 부모와 1:1 관계로 가져옴 -->
		<association column="deptno" property="dept" javaType="Dept" select="Dept.selectById"/>
	</resultMap>
	
	<!-- 사원테이블 정보 가져오기 -->
	<select id="selectAll" resultMap="empJoinDept">
		select * from emp
	</select>

association1:1관계에서 사용할 수 있는 조인이다. 즉, 자식이 참조하고 있는 컬럼에 대한 부모레코드를 참조할 수 있다.

위 collection 이해할 수 있다면 association을 쉽게 이해할 수 있다.

'프로그래밍 > Spring' 카테고리의 다른 글

Spring - ServletContext 쉽게 가져오기  (0) 2021.01.05
Spring | AOP  (0) 2020.12.23
Spring - DI  (0) 2020.12.22

DI를 사용할 경우 클래스내의 멤버변수에 대한 의존도가 낮아지게 되면서 결합도가 낮아진다.

하지만, 멤버변수의 존재가 아예 사라진다는 경우에 과연 결합도가 없다고 할 수 있을까?

 

이를 해결하기위해 Spring에서는 AOP를 사용하였다.

 

AOP란?

클래스내의 멤버변수와의 의존도를 아예 없게 함으로써 다른 클래스와의 결합도를 낮추는 기법이다.

Spring은 AspectJ의 기술을 채용하여 사용하였다.  

 

쓰는 이유?

예로 쇼핑몰 웹사이트를 제작 시 장바구니, 구매 등등 로그인 상태를 체크를 반드시 필요로 하는 페이지가 존재한다.

이런 경우 AOP와 같은 기술을 사용하지 않게 되면 해당 페이지의 컨트롤러와 같은 클래스나 페이지내에서 의존하게 된다. 이를 AOP와 같은 기술을 사용하여 분리하게 되면 프로그램의 유지보수가 상당히 편할 것이다.

 

사용방법

mvnrepository의 Spring MVC를 가져와서 pom.xml에 추가해준다.

 

Spring에서 사용되는 jar들이 많이 생기는데 여기에서 AOP도 추가된다.

<!-- https://mvnrepository.com/artifact/org.springframework/spring-webmvc -->
		<dependency>
			<groupId>org.springframework</groupId>
			<artifactId>spring-webmvc</artifactId>
			<version>4.3.30.RELEASE</version>
		</dependency>

그리고 aspectJ에서 지원하는 weaber 또한 필요로 한다.

<!-- https://mvnrepository.com/artifact/org.aspectj/aspectjweaver -->
		<dependency>
			<groupId>org.aspectj</groupId>
			<artifactId>aspectjweaver</artifactId>
			<version>1.8.14</version>
			<scope>runtime</scope>
		</dependency>

 

아래의 코드로 예를 들어본다면, Student클래스내에 각 메서드들의 실행 시작과 실행 후에 Bell클래스의 메서드인 startBell(), endBell()실행하도록 만들어봄으로써 AOP를 이해할 수 있다.

package test;

public class Student {
	
	public void study1() { //영어시간
//		System.out.println("♬ 시작 종"); //종이 울리는 것은 학생과 관련된 기능이 아님!!! 그리고 중복된다.
		System.out.println("1교시는 영어시간이에요");
	}
	public void study2() {//국어시간
		System.out.println("2교시는 영어시간이에요");	
	}
	public void study3() {//물리시간
		System.out.println("3교시는 물리시간이에요");	
	}
	public void study4() {//수학시간
		System.out.println("4교시는 수학시간이에요");
	}
}
package test;

public class Bell {
	public void startBell() {
		System.out.println("♬ 시작 종");
	}
	
	public void endBell() {
		System.out.println("♬ 종료 종");
	}
}

 

<!-- 학생과 벨을 엮어보자(weaving) -->
	
	<!-- AOP를 이용하기 위해서는, 공통로직 즉 횡단적 관심사항을 등록한다!! -->
	<bean id="bell" class="test.Bell"/>
	
	<!-- 어떤 시점에, 어떤 객체에게 횡단점 관심사항을 적용할지 xml태그로 서술한다..
		즉 프로그램 코드가 아닌 xml과 같은 설정파일에서 구현하는 방법을 선언적이라한다.. 
	-->
	<aop:config>
		<aop:aspect id="bellAspect" ref="bell">
			<!-- 어떤 시점에 벨이 관여할지를 결정 -->
			<!-- test..*(..) 테스트 패키지 아래의 모든 클래스의 모든 메서드 -->
			<aop:pointcut expression="execution(public * test.Student.*(..))" id="bellpointcut"/>
			<aop:pointcut expression="execution(public * test.Dog.*(..))" id="pointcutToDog"/>
			<!-- 공통기능 동작을 언제 할지, 즉 학생의 동작 이전에 적용, 이후에 동작시킬지.. -->
			<aop:before method="startBell" pointcut-ref="bellpointcut"/>
			<aop:after method="endBell" pointcut-ref="bellpointcut"/>
			<aop:before method="startBell" pointcut-ref="pointcutToDog"/>
			<aop:after method="endBell" pointcut-ref="pointcutToDog"/>
		</aop:aspect>
	</aop:config>
	<bean id="student" class="test.Student"/>
	<bean id="dog" class="test.Dog"/>

Bell클래스의 인스턴스가 Student의 메서드들의 실행을 관찰하고 있다고 생각하면 쉬운 것 같다.

'프로그래밍 > Spring' 카테고리의 다른 글

Spring - ServletContext 쉽게 가져오기  (0) 2021.01.05
Spring | collection & association  (0) 2020.12.24
Spring - DI  (0) 2020.12.22

+ Recent posts