처음 Struts 2 Framework 을 설치하고 환경설정하는 내용입니다. Struts 2 Framework 으로 웹 어플리케이션을 작성하기 위해서는 기본 선수 지식이 필요합니다. 아래의 기술들을 어느정도 알고 있어야 Struts 2 Framework 으로 웹 어플리케이션 작성이 쉽습니다.
- Java
- Filters, JSP, and Tag Libraries
- JavaBeans
- HTML and HTTP
- Servlet Containers(Tomcat 등)
- XML
국내 자바 개발자들이 Struts 2 Framework 를 익히고, 개발하는데 서로의 노하우를 공유할 수 있도록 게시판을 만들어 질답 및 팁을 여러사람이 볼 수 있도록 하였습니다.
Apache Struts 2 Framework 를 다운로드 받기 위해서는 Apache Struts Download 싸이트로 가서 최신 버전을 다운로드 받습니다.
Struts 2 Framework 웹 어플리케이션을 작성하기 위한 설정을 살펴본다.
Struts 2 Framework 어플리케이션을 개발하기 위해서는 최소한 필요한 파일을 복사합니다. 그 목록은 아래에 나와 있습니다.
- struts2-core.jar : Framework Library 파일입니다.
- xwork.jar : XWork 2 라이브러리로써 Struts 2 에서 사용되어 집니다.
- ognl.jar : OGNL(Object Graph Navigation Library) 를 지칭하며 Framework 에서 사용되는 Expression Language 입니다.
- freemarker.jar : Freemarker 로 쓰여진 UI Tag template 에서 사용합니다.
- common-logging.jar : 로그 처리를 위한 라이브러리입니다.
- web.xml : Struts 2 Framework 을 연동하는 웹 어플리케이션 환경설정 파일
- struts.xml : Struts 2 Framework 의 환경설정 내용을 포함하고 있으며, Action, Result, interceptor 등의 내용을 포함하고 있습니다.
web.xml 파일에 Struts 2 Framework 을 연동하는 내용을 기술합니다. 아래의 내용과 같이 web.xml 을 구성합니다.
web.xml 에 FilterDispatcher 를 등록하여 request 가 발행하면 Struts 2 Framework 가 그 request 를 받도록 설정합니다.
<?xml version="1.0"?>
<!DOCTYPE web-app PUBLIC "-//Sun Microsystems, Inc.//DTD Web Application 2.3//EN"
"http://java.sun.com/dtd/web-app_2_3.dtd"><web-app>
<display-name>My Application</display-name>
<filter>
<filter-name>struts2</filter-name>
<filter-class>org.apache.struts2.dispatcher.FilterDispatcher</filter-class>
</filter>
<filter-mapping>
<filter-name>struts2</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
</web-app>
Struts 에서 작성한 어플리케이션이 정상적인 동작을 하기 위해서 필요한 환경설정 내용을 포함하고 있습니다.
<!DOCTYPE struts PUBLIC
"-//Apache Software Foundation//DTD Struts Configuration 2.0//EN"
"http://struts.apache.org/dtds/struts-2.0.dtd"><struts><!-- Configuration for the default package. -->
<package name="default" extends="struts-default">
...
</package>
</struts>
2. Hello World
Struts 2 Framework 를 사용한 Hello World 웹 어플리케이션을 작성해봅니다. 웹페이지에서 Request 를 발생시키고, 서버에서 해당 Request 를 받은 다음, Hello World 문자열을 다시 보내서, 브라우저에서 Hello World 문자열을 나타냅니다.
원문에서는 간단한 소스와 환경설정하는 방법이 나와 있지만, 한글화를 하면서 Eclipse 를 사용하여, 각 단계별로 이미지를 포함하였습니다.
최신 Eclipse 버전인 Eclipse Europa JEE 버전을 사용하여 HelloWorld Web Application 을 작성합니다.
우선 Workspace 를 생성합니다.
File -> New -> Project 메뉴를 선택하고, Web -> Dynamic Web Project 를 선택합니다.
Project Name : Hello World 로 입력합니다.
Dynamic Web Project 를 생성한 후에 실행할 서버(runtime) 을 지정해야 합니다. 현재는 처음으로 프로젝트를 생성하였기에, 설정된 Target Runtime 이 없습니다.
Hello World 어플리케이션은 웹 어플리케이션이기 때문에, 가장 많이 사용되는 Tomcat 를 지정하여 실행을 하도록 합니다.
따라서 Tomcat 을 설치하고 난 후, 톰캣을 Target Runtime 으로 지정합니다.
New 버튼을 클릭하고, Apache -> Apache Tomcat 5.5 를 선택합니다.
그리고 Tomcat 이 설치된 디렉토리를 지정합니다.
Finish 버튼을 클릭하면 Target Runtime 이 위에서 설정한 Tomcat 으로 지정된 것을 확인할 수 있습니다.
Struts 2 Framework 을 사용하기 위해서는 위에서 설명한 필수 라이브러리를 포함시켜야 합니다.
Eclipse 에서 User Library 에 Struts 2 Framework 에서 사용되는 라이브러리를 추가합니다.
Struts 2 Framework 을 연동하여, Request 가 발생되면 Struts 2 로 처리가 되도록 web.xml 을 아래와 같이 수정합니다.
Request 가 발생되고, 그 결과를 화면에 보여질 JSP 파일을 추가합니다.
File -> New -> JSP 를 선택하고, HelloWorld.jsp 로 입력합니다.
그리고 아래와 같이 소스 코드를 입력합니다.
그리고 HelloWorld 클래스를 생성하고 아래와 같이 구현합니다.
File -> New -> Class 메뉴를 선택하고, Package : com.javamodeling.struts2, Name : HelloWorld 를 입력합니다.
Request 가 발생되고, 어느 Action 클래스가 Request 를 처리하고, 그에 따른 처리 결과에 따라서 JSP 파일로 Forwording 을 해야 합니다.
이러한 sturts 2 의 전체 환경설정을 struts.xml 에 정의를 합니다.
src -> new -> Other -> XML -> XML 을 선택하고, struts.xml 파일을 생성하고 아래와 같이 입력합니다.
배포하기 위해서는 Servers 탭에서 Add and Remove Projects 메뉴를 선택하고, HelloWorld 프로젝트를 추가합니다.
Server 를 실행하고, 주소창에 다음과 같이 입력하면 http://localhost:8080/HelloWorld/HelloWorld.action 아래와 같은 결과를 확인할 수 있습니다.
간단하게 Struts2 Framework 을 사용하여 HelloWorld 어플리케이션을 작성해 보았습니다.
Request 가 발생해서, 최종 Response 가 Browser 까지 전달되는 과정이 어떻게 되는지 살펴보겠습니다.
- Servlet Container(Tomcat)는 Browser 로부터 Request 를 받습니다. 이 Request 에는 HelloWorld.action 이 포함되어 있습니다.
- web.xml 에서 모든 request 는 struts2 로 전달되도록 URL Mapping 에 의해서 설정되어 있습니다. 따라서 org.apache.struts2.dispatcher.FilterDispatcher 를 경유하게 되어 있습니다.
- .action 이 있기에 Struts2 Framework 에서는 Struts 2 Framework 에서 Request 를 처리하도록 합니다.
- Sturts2 는 struts.xml 에서 요청한 HelloWorld.action 과 같은 이름의 HelloWorld(.action 은 빼고) 가 있는지 찾습니다. 같은 이름이 존재하면, struts.xml 에서 지정한 클래스의 객체를 execute() 메소드를 실행합니다.
- HelloAction.execute() 메소드가 실행되고, 필요한 비즈니스 로직이 실행됩니다. return 하는 값이 SUCCESS 이면 정상적인 정상으로 판단하고, struts.xml 에서 지정한 Result 에 기술된 HelloWorld.jsp 로 Forwarding 합니다.
- HelloWorld.jsp 에서는 <s:property value="message"> 태그를 인식하여 HelloWorld.getMessage() 메소드를 호출하여, HTML 을 구성합니다.
- 마지막으로 HTML 코드를 Browser 로 response 합니다.
3. Using Tags
지금부터는 위에서 작성한 Hello World 어플리케이션에 추가로 기능을 덧붙이도록 하겠습니다. Hello World 는 실행하기 위해서 간단하게 설정만 하였지만, 지금 부터는 몇몇 기능을 추가하여 기본적인 어플리케이션을 만들어보겠습니다.
우선 웹 어플리케이션에서는 다른 페이지나 Request 를 발생할 수 있고, HyperLink 를 추가할 수 도 있습니다.
페이지에 동적으로 HTML 코드를 처리하기 위해서 많이 사용되고 있는 것이 Tag 이며, Struts 2 Framework 에서 사용되고 있는 몇 개의 Tag 를 살펴보겠습니다.
많이 사용되고 있는 기능중에 하나가 다른 페이지로 연결하는 Link 입니다. Welcome.jsp 파일을 추가하고, 아래와 같이 코딩합니다.
결과 페이지를 각 언어별로 볼 수 있도록 페이지 링크를 추가한 화면입니다. 각 언어별로 Resource Bundle 에서 값을 읽어서 결과를 처리하기 위함입니다.
위와 같이 처리하기 위해서 HelloWorld.jsp 파일을 아래와 같이 추가합니다.
위 Welcome.jsp 와 HelloWorld.jsp 에서 두가지의 Link 하는 방법을 나타내고 있습니다. HellWorld.jsp 에서 사용된 %{url} 은 <s:url> 태그에서 사용된 url 값을 그대로 사용하는 방법입니다.
<s:url> 이 사용된 방법은 위 예제에서 아래의 세가지 경우입니다.
- Resource links : <link href= "<s:url value=" /css/tutorial.css "/>" rel= "stylesheet" type= "text/css" />
Resource Link 는 header 에서 필요한 리소스(파일, 페이지)를 Link 하는 역할을 합니다.
- Direct links : <li><a href= "<s:url action=" Register "/>" >Register</a></li>
Direct Link 는 해당 Action 을 직접 호출합니다. Action 의 확장자를 지정하지 않아도, Tag 가 rendering 하면서 자동을 확장자를 붙여줍니다.
- Links with parameters : <s:url id= "url" action= "Welcome" > <s:param name= "request_locale" >en</s:param> </s:url> <s:a href= "%{url}" >English</s:a>
이 param 태그는 request 가 전송될때, ?request_locale=en 으로 변환하여 Welcome Action 에 전송됩니다. 그리고 %{url} 에 파라미터가 포함된 경로가 포함되어 집니다.
만약 Welcom Action 이 실행된 후, 그 결과를 특정 페이지로 Forwarding 해야 합니다. Welcome Action 을 처리하기 위해서 struts.xml 에 아래 내용을 추가합니다.
<actjon> 태그에서 class 속성을 부여하지 않으면 Action 클래스를 수행하지 않고 직접 페이지로 Forwarding 합니다.
이렇게 Action 이름과 Forwarding 할 페이지 이름이 동일할 경우, 아래과 같이 wildcard mapping 을 사용하여 처리를 하면 훨씬 편리합니다.
아래와 같이 코딩해도 결과는 마찬가지로 나타납니다.
입력폼을 처리해야 하는 경우에, Struts 2 의 태그에서도 입력 폼을 위한 태그를 사용할 수 있습니다. 아래와 같이 간단하게 태그를 추가해보겠습니다.
Logon.jsp 파일을 생성하고, 아래와 같이 코딩합니다. Struts 2 태크가 HTML Form 형식에 맞게 rendering 을 해줍니다.
4. Coding Action
위에서 Tag 부분을 설명하면서 Login Form 을 완성하였습니다. 이번에는 Login Action 을 구현해 보겠습니다. Login Action 에서 비즈니스 로직이 수행되고 난후에 그 결과에 따라서 리턴하는 값이 달라지게 됩니다.
그리고 아래 URL 로 로그인 기능이 수행됩니다.
http: //localhost:8080/HelloWorld/Logon.action
Login.action 이 호출되면, User Name 과 Password 값을 받아서 로그인 처리를 하기 위한 Logon 클래스를 생성합니다.
아래와 같이 Logon 클래스를 추가하고, 코딩합니다.
package com.javamodeling.struts2; import com.opensymphony.xwork2.ActionSupport; public class Logon extends ActionSupport { public String execute() throws Exception { if (isInvalid(getUsername())) return INPUT; if (isInvalid(getPassword())) return INPUT; return SUCCESS; } private boolean isInvalid(String value) { return (value == null || value.length() == 0); } private String username; public String getUsername() { return username; } public void setUsername(String username) { this.username = username; } private String password; public String getPassword() { return password; } public void setPassword(String password) { this.password = password; } }
위 Logon class 에서 비즈니스 로직이 수행되는 것은 execute() 메소드입니다. Logon.action 이 호출되면 execute() 메소드가 실행되고 비즈니스 로직이 수행되고, HTML Form 값은 자동으로 Action 클래스의 getter/setter 로 지정된 property 에 저장이 됩니다.
위의 Logon 클래스에서 setUserName() 과 setPassword() 메소드가 HTML Form 의 값을 저장하여 Logon 클래스에 해당 값이 저장됩니다.
5. Selecting Results
Request 에 대한 Action 이 수행된 후, Response 를 처리하기 위해서 Result 가 선택되어집니다. Result 는 간단한 HTML 페이지, JSP 페이지, Freemaker 나 Velocity 같은 Template 엔진, 혹은 PDF 같은 문서나 복잡한 리포트로 Forward 될 수 있습니다. 또한 Action mapping 통하여 여러개의 Result 도 가능합니다. 특정 하나의 Result 로 선택되기 위해서는, Action 클래스에서 Result 에 맞는 결과 값을 리턴해야 합니다.
아래와 같이 struts.xml 에 코드를 추가합니다.
Logon.jsp 에서 username 과 password 를 입력하면 Logon Action 에서 success 값을 리턴합니다. succuess 값은 디폴트 result 값으로써, Menu action 으로 전송됩니다.
만약에 두 값이 입력되지 않으면, Logon Action 은 input 값을 리턴하게 되고, 다시 Logon.jsp 로 Forwarding 됩니다.
일반적으로 Result 의 Type 은 Dispatcher forward 입니다. 이는 특정 JSP 페이지로 forwarding 을 하며, 위에서 설정된 redirect-action 은 client browser 에서 다시 rediect 를 생성하게 하여 Action 을 호출합니다.
Logon Action 이 정상적으로 수행하고 난 후, 다음으로 Forwarding 할 페이지를 아직 결정하지 않았습니다. 그래서 Logon Action 이 정상적으로 수행되고 난 후에 Forwarding 할 Menu.jsp 파일을 아래와 같이 생성하고 코딩합니다.
Menu Action 이 호출되면, Menu.jsp 으로 Forwarding 됩니다. 이렇게 되는 것은 위에서 struts.xml 파일에 * 라는 wildcard 를 설정해 놓았고, Action Name 과 동일한 JSP 파일로 Forwarding 하게 되어 있습니다. 따라서 Logon Action 에서 Menu Action 을 호출하게 되면, Menu.jsp 로 Forwarding 됩니다.
하나의 JSP 페이지로 화면에 보이는 모든 내용을 포함하지는 않습니다. 여러개의 JSP 파일로 나누어서 한 화면을 구성하는게 일반적입니다. 따라서 Struts 2 태그를 사용하여 다른 JSP 파일을 포함하는 것은 아래와 같은 태그를 사용할 수 있습니다.
<%@ taglib prefix="s" uri="/struts-tags" %>
<s:include value="Missing.jsp" />
6. Validating Input
앞서서 Logon Action 에서는 User Name 과 Password 에서 Validation 을 수행하였습니다. 이렇게 간단한 어플리케이션에서는 코드상에서 Validation 을 체크할 수도 있지만, 큰 어플리케이션이나 대용량 어플리케이션을 개발할 경우에는 코드상에서 Validation 을 체크하는 것은 매우 힘듭니다. 또한 유지보수하는데 매우 어려움이 많습니다.
Struts 2 Framework 에서는 Validation Framework 을 제공하여 Input 값에 대한 Validation 을 체크할 수 있습니다.
Validation 은 XML 파일로 Validation 에 대한 내용을 정의할 수 있고, Annotation 으로 Validation 을 정의할 수 있습니다.
XML 파일은 Action Name 과 동일한 이름으로 시작하고, 파일명 뒷 부분에 "-validation.xml" 이라고 파일명을 정하면 됩니다. 이 문서에서 작성하고 있는 Logon Action 에 Validation 을 설정하려면 Logon-validation.xml 로 파일을 생성하면 됩니다.
LOgon Action 클래스가 있는 같은 패키지에 Logon-validation.xml 파일을 생성하고 아래와 같이 코딩합니다.
위와 같이 Validation 을 추가하면, 첫 페이지를 호출할때 Validation 을 수행하게 됩니다. 하지만 첫 페이지는 그냥 입력화면을 처리하고 Validation 을 수행하지 말아야 합니다.
따라서 첫 페이지를 호출할때, Validation 을 수행하지 않게 하기 위해서 Welcome.jsp 와 struts.xml 파일을 아래와 같이 수정합니다.
Logon 화면이 보일때 까지 과정
- Welcome.jsp 에서 Logon_input.action 이 호출되기에, struts2 에서 이에 맞는 actioin mapping 을 찾습니다. struts.xml 에 Logon_* 가 있기에 이 action mapping 을 찾습니다.
- method={1} 가 설정되어 있기에, method=input 으로 인식합니다.
- struts2 에서 Logon.input() 메소드를 호출합니다.
- input() method 는 vadidation 을 처리하지 않는 특별한 메소드로 지정되어 있기에, Validation 을 수행하지 않고 그냥 실행합니다.
- 디폴트 input() method 는 input 값을 리턴합니다.
- struts2 는 Validation 메시지 없이 그냥 Logon.jsp 로 Forwarding 합니다.
Logon 페이지에서 Submit 버튼을 클릭할 경우
- struts2 에서는 Submit 버튼이 클릭하게 되면, Logon Action 에 맞는 Validation 을 수행합니다.
- Logon-validation.xml 파일을 찾고, XML 내용에 맞게 Validation 객체를 생성합니다. Validation 객체는 각 Validator 객체들로 구성되어 있습니다.
- Validator 는 각 입력 속성에 대해서 체크를 합니다.
- 만약 Validator 가 실패할 경우(Validation 체크에서 에러가 난 경우), 해당 메시지가 Queue 에 저장됩니다.
- 모든 Validator 가 수행되고 난 후에, struts2 에는 발생된 에러가 있는지 확인합니다. 만약에 에러가 있다면, input Result 를 찾고, Action 클래스는 실행되지 않습니다.
- 에러가 없다면 Action 클래스가 수행되고, input 속성에 대한 validation 이 끝났기에, success Result 를 리턴합니다.
7. Localizing Output
Validation 체크할 경우, 메시지를 화면에 보여줬습니다. 같은 메시지를 여러 곳에 처리하거나, 각자 다른 언어를 사용할 경우, 해당 언어에 맞는 메시지를 화면에 보여줘야 할 경우가 많이 있습니다.
이럴때 메시지를 리소스 번들(Resource Bundle)에 저장해서 사용하면 매우 편리합니다.
페이지에서 나타내는 메시지와 Validation 에서 처리하는 메시지를 저장하기 위한 Resouce Bundle 을 생성해 보겠습니다.
Struts 2 에서 Resource Bundle 은 Action Name 과 동일하게 주고, 파일 확장자를 .properties 로 주면 됩니다. 따라서Logon Action 에 대한 Resource Bundle 파일명은 Logon.properties 가 됩니다.
파일이 저장되는 위치는 Validation 과 마찬가지로, Action 클래스의 패키지 경로와 동일합니다.
그리고 해당 패키지에서 공통적으로 사용되는 Resource Bundle 을 정의하고 싶으면, package.properties 파일을 만들면 이 package.properties 가 있는 패키지 경로의 모든 클래스에서 사용할 수 있습니다.
우선 Logon Action 과 같은 패키지 경로에 package.properties 파일을 생성하고 아래와 같이 입력합니다.
그리고 위에서 정의한 Resource Bundle 을 사용하도록, Logon.jsp 파일과 Logon-validation.xml 파일을 수정합니다.
한글 메시지를 보이게 하는 것을 살펴보겠습니다. Resource Bundle 을 사용하는데 있어서 한글 메시지를 처리하기 위해서는 한글이 유니코드로 저장이 되어야 합니다.
Logon Action 클래스가 위치한 곳에 Logon.properties 파일을 생성하고 아래와 같이 입력합니다.
//requiredstring = $\{getText(fieldName)} 는 필수입력입니다. requiredstring = $\{getText(fieldName)} \ub294\u0020\ud544\uc218\uc785\ub825\uc785\ub2c8\ub2e4. //password = 암호 password = \uc554\ud638 //username = 사용자명 username = \uc0ac\uc6a9\uc790\uba85
정리
Struts 2 Framework 을 사용하여 간단한 어플리케이션을 작성하였습니다. Eclipse 로 쉽게 따라할 수 있도록 이미지를 많이 추가하였으며, 혹시 궁금한 점이 있으시면 아래 게시판에 글을 남겨주시기 바랍니다.