[Spring Roo] (3) Roo 아키텍처

프레임웍로그/Spring 2011. 3. 3. 23:45

 


1. 아키텍처 개요

스프링 Roo는 자바로 작성된, 기업용 애플리케이션 개발에 초점을 두고 있다. 현재 버전에서는 전형적으로 

관계형 데이터베이스 백단에 대한 퍼시턴스 접근을 위해 Java Persistence API,  스프링 프레임웍 의존성 주입과 

트랜잭션 관리, JUnit 테스트, Maven 빌드구성를 사용하며,  뷰기술로는 JSP를 사용하는 스프링 MVC  프론트엔드를 

가지고 있다.  이런 형태는 가장 현대적인 자바기반 기업 애플리케이션 형태이다. 

하지만 루를 사용하여, 개발할 수 있는 자바 애플리케이션의 제약이 없다는 것이 중요하다. 

루 1.0.0를 사용해서도 , 어떤 종류의 애플리케이션든지  개발할 수 있다.  현재 버전의 루를 사용하여 쉽게 해결할 수 

있는 몇 가지 요구사항 타입의 예들은 다음과 같다. 


1)  JMS큐에서 메시지를 수신받고, JMS 또는 SMTP로 응답을 전송하는 경우

2) 서비스 레이어를 작성하거나 (Spring의 @Service 스테레오 타입 어노테이션 사용),  리모팅 프로토콜을 사용하여                                 서비스 레이어를 rich client에 공개 (스프링의 remoting services) 하는 경우

3) 스프링의 새로운 @Scheduled 또는 @Aync 어노테이션을 사용하여 데이터베이스에 일련에 사전 정의된 액션을                                   실행하는 경우 

4) 최소한의 시간투자로 최신의 스프링,  AspectJ의 특징을 사용하려는 경우 



2. Roo 와 기존 애플리케이션과의 차이점

루와 전통적인 핸드라이팅 애플리케이션의 주요한 차이점 중 하나는 루가 불필요한 추상화 계층을 추가하지 않았다는 

것이다.  전통적인 자바 엔터프라이즈 애플리케이션은 DAO, 서비스, 도메인, 컨트롤러 계층으로 구성된다. 

루 애플리케이션에서는 entity(도메인 레이어와 유사) 와 web layer만을 사용한다. 서비스 레이어는 애플리케이션이 

필요할 때 추가할 수 있으며, DAO 레이어는 루 애플리케이션에서는 추가되는 경우가 거의 없다. 

루 차기 버전에서는 클라우드 지원과  RIA 프레임웍에 대한 지원이 확장될 예정이다. 현재도 Cloud Foundry, Amazon Web

Services,  Google App Engine 과 같은 클라우드에 배치하는 루 애플리케이션을 작성할 수 있지만, 미래에 비관계형 데이터

베이스와 함께 더 쉽고 편이하게 사용할 수 있는 많은 애드온들이 추가될 것이다.  

RIA 관점에서, Google Web Toolkit 프론트 엔드를 작성할 수 있는 서비스도 추가될 예정이다.

 (GWT와 Roo 모두 엔지니어링 퍼모먼스와 first-class 자바 중심 개발방법에 초점을 두고 있음)   

Apache Maven 의 대안으로 Apache Ivy 지원에 대한 요구사항도 있다.



3. 핵심기술

 

3.1 AspectJ

AspcectJ는 정의된 포인트컷에 advice를 적용하는 AOP 로 가장 잘 알려져있지만,  루 프로젝트들은 AspectJ의 강력한 

inter-type declaration(ITD) 특성을 사용한다. 이것이 루가 사용하는 마술이다. 일반 java 파일로부터 다른 컴파일 

단위로 메서드와 필드들을 클래스 파일에 생성해 넣는다.  생성된 코드는 독립된 파일이기 때문에 그 파일들의 생명주기와 

컨텐츠는 java 파일에 무엇을 하고 있는지와는 완전히 독립적으로 관리할 수 있다.  


 ITD 가 어떻게 동작하는지 알아보자. 아래와 같이 새로운 프로젝트를 만들고 엔티티를 추가하자.


Hello.java  파일 외에도, 일련의 Hello_Roo_*.aj 파일들이 생성되었다.  *_Roo_*.aj 형태를 갖는 파일들이 Aspect ITD 

파일들이며, Roo에 의해 관리된다. 이 파일들을 직접 편집해서는 안된다. 

 

 

Hello.java 파일은 다음과 같은 단순한 형태를 갖는다.


몇몇 어노테이션들이 추가되었는데, 이런 Roo 어노테이션들은 소스 수준에서 유지되며, .class 파일로 컴파일되지 않는다.

Roo 어노테이션들은 항상 @Roo*로 시작하며, 코드 어시스트 기능을 사용할 수 있다.  

 

IDT파일들 중의 Hello_ROO_ToString.aj 을 보자 


ITD는 자바코드와 매우 유사하다. 큰 차이점은 priviledged aspect 로 선언되어있으며, 각 멤버들은 특정한 타겟타입을 

식별한다.  Hello.toString은  Hello 타입에 toString 메서드를 추가하라는 의미이다. 

 


javap 명령을 사용해 생성된 클래스 파일을 확인한 결과이다.



Roo가 AspectJ ITP를 통해 java 파일에 위 그림과 같은 멤버들을 추가하였다. toString 메소드 뿐만아니라, 

스프링의 ConfigurableObject 인터페이스를 구현하고 있으며,  JPA EntityManager에 대한 접근자, 몇몇 퍼시스턴스 메소드, 

getter, setter 들이 추가 되었다.  이런 유용한 특징들이 round-trip 방식으로  자동적으로 관리된다. 

java 파일에  toString 메소드를 정의하거나, 프로그래머가 직접 toString 메소드를 정의하면, 더 높은 우선순위를 갖게되어

자동으로 Hello_Roo_ToString.aj 파일이 삭제된다. 

 

또한 루 애플리케이션은 AspectJ의 뛰어난 AOP 특징을 사용하여, 싱글턴 객체를 사용하여 의존성을 주입하고, 

메소드 호출의 일부로 트랜잭션 서비스가 사용된다. 

 

 

3.2 Spring

루의 디폴트 애플리케이션은 스프링 프레임웍만을 포함하고 있으며, Spring Security, Spring Web Flow와 같은 

다른 프레임웍을 

점진적으로 추가할 수 있는  명령들을 제공하고 있다. 모든 루 애플리케이션들은 Spring Aspect를 사용하며, 

스프링 프레임웍의  

Configurable 의존성 주입과 트랜잭션 어드바이스를 사용한다.  또한 디폴트로 스프링에 어노테이션 기반 

컴포넌트 스캐닝과 

데이베이스 커넥션 풀,  JPA 프로바이더와 같은 객체 생성 및 의존성 주입을 위해 스프링 프레임웍에 의존

한다. 


 

3.3 Entity Layer

Roo 프로젝트에서 entity와 field는 문제 domain을 표현하는 첫번째 진입점이 된다.  entity는 데이터베이스에 저장되는 

특별한 형태의 domain object로,  일반적으로 하나의 entity는 하나의 table을  field 는 하나의 column을 표현하지만, 루쉘을

통해 쉽게 커스터마이징 할 수 있어서, 해당하는 어노테이션을 알 필요도 없다. 

@RooEntity 어노테이션를 사용하면 Persistent  Entity객체를 얻어오는 정적메서드와 JPA  Facada 메소드들,  식별자와 버전을 

위한 getter, setter를 추가하는 .aj 파일을 생성한다. (Hello_Roo_Entity.aj ).  @RooEntity 어노테이션을 제거하고,  JPA를  직접 

구현 할 수도 있다. ( 식별자와 버전은 삭제되지 않는다.)

@RooJavaBean 어노테이션은 클래스 내 모든 필드에 대한 getter, setter 를 추가하는 Hello_Roo_JavaBean.aj 파일을 

생성시키며, 이 메소드를 직접구현하면 자동으로 해당하는 메소드가 ITD에서 제거된다. 

@RooToString 어노테이션은 public void toString 메소드를 추가하는데, 이 메소드는 자동생성된 web controller에서 연관된

엔티티를 보여주기 위해 사용된다. 이 메소드 내부에서는 Caleander 객체를 사용하며, 컬렉션을 포함하는 양방향 관계에서

흔히 나타나는 원형참조를 피할수 있도록 관리해준다. 

반드시 Roo쉘에서 엔티티 클래스를 생성할 필요는 없다. 어떤 편집기나 IDE를 사용하여  엔티티 클래스를 작성하고, 

@RooToString, @RooJavaBean 어노테이션을 사용할 수 있는데, 이러한 방법은 저장될 필요가 없는(엔티티가 아닌)

많은 도메인 객체를 가지고 있을 때 특히 유용하다 

 


 

3.4 Web Layer

Roo 1.0.0은 선택적으로 자동생성된 웹 컨트롤러 레이어를 사용할 수 있도록 제공한다. 이 레이어는 요청이 REST 관례를 

따르도록 보장하는 많은 URL rewriting 규칙을 포함하고 있다.  또한 Apache Tiles, Spring JavaScript 외에도 단일 명령으로 

쉽게 Spring Security를 설정할 수 있게 해준다.  이 컨트롤러들은 항상 요청을 @RooEntitiy 클래스에서 제공하는 메소드로 

직접적으로 위임하는데, 호환성을 위해서  @RooEntity 구현에 의해 제공되는 디폴트 식별자와 버전 관례를 준수하는게 좋다. 

대부분의 Roo 애플리케이션들은 비지니스 로직을 엔티티와 웹 컨트롤러 사이에 놓으며, 가끔은 서비스레이어에 놓기도 한다. 





3.5 Optional Services Layer

웹 애플리케이션은 대부분의 로직을 웹컨트롤러 핸들 메소드에, 나머지를 엔티티 메소드에 작성하기 때문에 거의 서비스 

레이어를 필요로 하지않는다.  하지만 비지니스 로직을 필요로 하는 다음과 같은 경우도 있다. 

   * 로직이 특정 엔티티에만 속하지 않고 여러 엔티티로 확장되야 하는 경우

   * 웹요청의 범위를 넘어 비지니스 로직이 적용되야 하는 경우 

   * 원격 클라이언트 접근이 필요할 때 (remoting protocol을 통해 메소드들을 노출하는게 더 편리하기 때문)

   * 아키텍처 정책이 서비스 레이어를 요구할 때 

   * HTTP  관련 관리와  비지니스 로직에 대한 책임 분할을 통해, 더 높은 수준의 응집도를 필요로 할때 

   * 서비스 레이어에 보안 인증 메타데이터와 트랜잭션 경계를 놓는게 더 선호되는 경우 




3.5 Goodbye DAOs

대부분 작성하는 일반적인 웹 애플리케이션에 반드시 필요 하지는 않기 때문에, 서비스 레이어와 함에 DAO 레이어가 

제거되었다.  DAO 레이어가 필요한 주요한 동기를 생각해보면 루 애플리케이션에서 필요하지 않는 이유를 더 잘 알 수 

있을 것이다. 

    * Testing

    * Separation of concern

       DAO 레이어를 사용하는 이유 중 하나는 객체지향 설계에서 추구하는 높은 응집도를 구현하기 위해서이다. 

       높은 응집도는 관심의 분리와 동일하다고 할 수 있다.  AspectJ의 ITD를 통해, 퍼시스턴스 메소드를 프로그래머가 

       아닌 Roo 처리하도록 하여 관심의 분리를 달성하고 있다. 

    * Pluggable implementaions

       DAO의 다른 장점 중 하나로 하나의 퍼시스턴스 라이브러리에서 다른 것으로의 변경이 용이하다는 것이다. 

      현재 애플리케이션은 API 수준의 추상화를 JPA를 통해 제공하는데, 루는 자동생성된 메서드에서 JPA를 사용하며, 

       DAO 레이어 없이도, 대체 구현을 플러그 할 수 있는 능력을 지원한다.

    * Non-JPA persistence

       몇몇 엔티티들을 JPA Provider를 사용하지 않고, 저장하고 싶을 경우가 있을 것이다. 소규모의 클래스들만이 

       이러한 요구사항이 필요하다면, 나머지 대다수의 엔티티들을 Roo를 사용하여 관리할 수 있다. 대규모의 클래스들이 

       이러한 요구사항을 필요로 한다면 사용자가 직접 (Roo가 JPA Provider에 대해 했던 것처럼) 자동으로 ITD들을 

       관리해주는루 애드온을 작성할 수 있다. 

    * Security authorisation

 

 


'프레임웍로그 > Spring' 카테고리의 다른 글

[Spring Roo] (4) Roo 설치하기  (0) 2011.03.03
[Spring Roo] (3) Roo 아키텍처  (0) 2011.03.03
[Spring Roo] (2) Roo를 사용하는 이유  (0) 2011.03.03
[Spring Roo] (1) Spring Roo란?  (4) 2011.03.03