....

Struts ActionForm을 사용할때의 전략.... 본문

JAVA

Struts ActionForm을 사용할때의 전략....

idkook 2009. 4. 17. 17:08
뜬금없이 다른곳에서 개발한 서버의 고도화 프로젝트를 떠안게 됐다...

Spring을 공부하면서 나름 이것저것 손을 많이 대버리는 바람에 어느정도 자신이 있었지만...

유일하게 나중에 공부해야지~ 라고 생각했던 Struts가 두둥~ 하고 내 눈앞에 펼쳐졌다... OTL

소스 분석, 환경 분석을 주구장창 시작하고... 아항.. 아항.. 이렇게 돌아가는 거구나.. 대충 통밥으로 감 잡고..

확실히 스프링을 공부하고 실무에 적용하면서 익히게 되는 많은 지식들이 엄청난 도움이 된다는걸 실감했다.[각주:1]

어찌됐는 기존의 소스코드는 가히 엉망 진창이였다... SQL Injection에 대한 처리도 전혀 안되어 있었으며, 주석또한 거의 전무하고, 그나마 있는 주석들이 다 중국어..(이건 뭐냐......)  아주 간간~~~히 가뭄에 콩나듯이 한글로 된 주석을 발견할 수 있었다..

어느 중국인이 짜놓은 사이트 구조를 그대로 수정해서 사이트를 구축해놓은 것으로 유추된다.

그나마 Struts를 썼으면... 그 장점이라도 살려야 하건만.. 로직만 잔뜩 꼬여있고... DAO와 Controller(여기선 Struts)의 계층 구분도 전혀 안되어 있었으며, 심할땐 ActionForm에서 직접 쿼리를 생성해서 그 쿼리를 DAO에 던지는 당황스런 코드도 볼수 있었다...

이해가 안되면 할려고 노력이라도 하지... 남의 소스 엎어와서는 자기가 새로 작업해야 하는 부분만 어거지로 돌아가게 짜놓은 흔적이 아주 역력했다... 원판 소스도 상당히 질이 안좋은데 거기에 더 질 안좋은 소스를 섞어놓은 기분...

Model 1.5냐 ?????
차라리 그렇게 짜려면 다 그렇게 짜서 분석이라도 쉽게 해주지.. 어떤건 여기서 어떤건 저기서... 처리하는데 무슨 페이지 하나 로직 분석할려면 처음부터 꼼꼼히 뜯어봐야 하는 난감한 상황이 되버렸다.. ㅠㅠ;

가뜩이나 첨보는 Struts로 머리가 지끈지끈한데.. 그것조차 일관되지 않게 짜놓은 소스들을 보면서 내 머리는 점점 지진난 기분이 되가고 있으니...

어쨋든 일은 맡았고.. 진행은 해야 하고... 여기 있던 소스와 똑같은 방식으로 작업하기에는 내 자존심이 허락하지 않는다... 기존에 누락된 정보 수정페이지를 신규로 만들면서 딜레마에 빠져버렸다...

도메인 계층의 Bean을 끌어써야 하는데 기존 ActionForm을 너무 많이 뜯어고치기는 싫고... 스프링 MVC에서 잘 써먹었던 Command 객체에 도메인 빈을 직접 넣어서 Form과 연계시켰던 방식으로 작업하려고 했더니..[각주:2] DataType이 String이 아닌 int, date등 마구마구 짬뽕이 되어 있어서 BeanUtils에서 에러가 마구 난사가 된다.

Struts에 대한 지식도 얼마 없는 상태에서 도매인빈과 Form을 어떻게 연결해서 넘길지 전략을 결정해야 하는 난감한 상황.... 과연 어떤 방식으로 최대한 코드를 안고치고 (시간이 없으니까.. ㅠㅠ) 작업량을 줄이고 코드 중복을 줄여나가면서 매핑 시킬 수 있을까 하면서 구글링을 하다가 아래 글을 찾았다...

음.. 우리의 전략이라고 했지만... 따라해야 겠다... 내가 생각해도 아래 내용들이 조목조목 잘 맞고..

단점이라면.. 기존의 ActionForm에 도매인 객체의 프로퍼티를 일일히 똑같이 넣어줘야 한다는 점.. (코드 중복이라 상당히 싫지만... 직관적인 수정은 진짜 용이하겠다... )

그런데... DAO단에 던질때.. ActionForm을 던져버릴까... 도매인빈에 일일히 매핑을 해서 도매인 빈을 던져버릴까... 이런이런... 또 갈등이 생기는군... 갈등의 연속이다.. ㅠㅠ;

아래는 퍼온 글이다. 원문제작자님께 감사의 말씀을~!

아래 내용은 http://www.oracleclub.com/article/11380 에서 퍼온 내용이다.

1. ActinoForm 사용전략의 종류
① 도메인 객체 Bean과 1:1 매치되는 ActionForm 생성
② 통합적으로 사용가능한 하나의 ActinoForm 생성
③ 도메인 객체 Bean을 자신의 property로 가지는 ActionForm 생성
④ 내부에 Map 객체를 가지는 ActionForm 생성
⑤ 별도의 클래스 파일 없이 struts-config.xml에서 정의해서 사용하는 DynaActionForm 생성

2. 각각의 특징과 장*단점
①번의 장점
-. 도메인 객체 Bean과 1:1 매치되는 방식이므로 데이터 이동이 명확하며 전체 애플리케이션 구조 이해가 수월하다.
-. BeanUtils.copyProperties 메써드 사용으로 Action 단에서의 처리로직이 거의 필요없다.
①번의 단점
-. 도메인 객체 Bean의 개수에 따라 ActionForm 클래스를 만들어줘야 하므로 큰 애플리케이션일수록 작업량이 많아지게 된다.
-. 도메인 객체 Bean의 설계에 종속적이므로 도메인 객체의 변경에 따라 계속적인 유지보수가 발생하게 된다(매치되는 도메인 객체 Bean과 property 이름이 같아야 하므로).

②번의 장점
-. 하나의 ActionForm 클래스로 여러가지 Action에서 사용하게 되므로 재사용성이 높으며, 유지보수할 클래스 개수가 현저하게 줄어든다.
②번의 단점
-. 하나의 ActionForm에서 여러 도메인 객체 Bean property와 매치시켜야 하므로 도메인 객체 Bean 설계시 비슷한 property 이름을 통일시켜주는 작업(예를 들어 각 도메인 객체 Bean의 pk 속성의 이름은 id로 통일한다는 등)을 해주거나(Layer간 의존도가 높아짐), 해당 Action에서 불필요한 데이터까지도 담게 됨으로써 통신시 부하가 상대적으로 높아질 것이다. 그리고 상당히 머리가 아프며 이것저것 동시다발적으로 생각해야 되기 때문에 고도의 집중력이 요구되어진다.


③번의 장점
-. 도메인 Bean을 ActionForm 내에서 직접 property로 가지고 있게 됨으로써 데이터 copy와 같은 단계가 필요없으며, 도메인 객체 Bean 내부의 변경이 ActionForm 자체에 영향을 주지 않음으로써 Layer간 의존도를 낮출 수 있다.
-. Bean에서의 프라퍼티를 일일이 ActionForm 에서 매치되게 구현해주지 않아도 됨으로써 클래스 구조를 간단하게 만들며 유지보수를 쉽게 해준다.
③번의 단점
-. 내부의 도메인 객체 Bean에서 String, Boolean 이 아닌 다른 타입(숫자형 타입 Long, Integer 혹은 날짜형 타입 Date, Timestamp 등)을 가지고 있게 될 경우, 사용자 입력 오류 등의 경우에, ClassCastException이 발생할 가능성이 높으며, 이에 대한 에러 처리에 어려움을 가진다.
-. ActionForm 의 내부 propery인 Bean이 가지고 있는 property에 대한 Validation 체크를 위한 xDoclet 사용이 안됨으로 인해 개발자 공통의 xml 생성 및 관리에 불편함을 초래한다.

④번의 장점
-. ③번의 경우와 비슷하게 도메인 객체 Bean의 property의 변화와 관계없이 ActionForm 내부의 Map property에 set/getMethod()를 사용해주면 되기 때문에 단순한 형태의 ActionForm 생성이 가능하며 유지보수 대상 클래스가 줄어든다.
-. org.apache.struts.scaffold.BaseMapForm 을 상속받기만 하면 Map ActionForm 구현은 간단하게 끝난다.
④번의 단점
-. 역시 ③번과 마찬가지로 Validation 생성을 위한 xDoclet 사용이 불가능하며, 명확한 property가 명시되어 있지 않음으로 인해 클래스 전체 구조가 이해하기 힘들게 된다(특히 유집보수를 다른 사람이 하게 될 경우). 이 부분도 만만치 않게 머리가 아프다.

⑤번의 장점
-. 각각의 클래스로 생성되어야 할 ActionForm 들을 struts-config.xml에서 태그만 정의해주면 되기 때문에 사용이 간편하며, ActionForm 관리가 용이해진다.
-. ActionForm 클래스를 하나도 사용하지 않아도 됨으로 인해 ActionForm 클래스 유지보수와 관련한 비용이 절감된다.
⑤번의 단점
-. 역시 Validation 생성을 위한 xDoclet 사용이 안되며, struts-config.xml 관리가 어려워진다(config 파일의 거대화 혹은 merge 파일로 빼냈을 경우 관리의 복잡성).

3. 각각의 특징에서 본 우리의 ActionForm 사용전략
-. 일단은 case by case 의 입장을 견지한다(각각의 사용전략은 그에 맞는 경우에 따라 최고의 효과를 가질 수 있으므로, 선험적인 제외는 올바르지 않다).
-. 기본적으로는 도메인 객체 Bean과 1:1 매치관계를 가지는 ActionForm 을 작성한다.(어플리케이션의 구조가 직관적이며 Action단의 불필요한 로직발생을 최소화)
-. write, update 등과 상관없이 List 화면만 보여줄 경우 공통된 타입(List)으로 데이터를 받아오기 때문에 공통적인 하나의 ActionForm 작성으로 대체하는 것이 효율성 및 유지보수의 편리함을 극대화할 수 있다.
-. 위의 ListActionForm의 경우 검색조건이 있다면, 검색조건은 Map으로 관리하는 것이 편리하다(검색조건은 화면에 따라 다를 수 있으며, 도메인 객체 Bean과 매치되는 property 속성이 아니므로 해당 검색 param을 key로, 넘겨진 값을 value로 가지는 Map으로 관리하는 것이 유리하다).

  1. 엄밀히 말하면 스프링을 공부해서 익히는게 아니라.. 스프링을 잘 쓰기 위해서 다른 Side Framework를 공부하게 되고 디자인패턴을 공부하게 되면서 익히는 지식들이 정말 많은 도움이 된다... [본문으로]
  2. 이 경우 중첩 객체로 들어가기 때문에 Form의 이름이 command.BeanProperty 와 같은 식으로 들어간다.. 때문에 Javascript로 컨트롤 할때는 getElementById를 남발해야 한다... ㅎㅎ 물론 이 방식이 DOM표준이라고 얼핏 들은것 같지만.... [본문으로]
Comments