캠핑과 개발

JSTL 요약

DEVELOPMENT/Java2014. 8. 5. 12:51
설정

web.xml

 

<taglib>
    <taglib-uri>jstl-c</taglib-uri>
    <taglib-location>/WEB-INF/tlds/jstl/c.tld</taglib-location>
</taglib>
<taglib>
    <taglib-uri>jstl-fmt</taglib-uri>
    <taglib-location>/WEB-INF/tlds/jstl/fmt.tld</taglib-location>
</taglib>
<taglib>
    <taglib-uri>jstl-fn</taglib-uri>
    <taglib-location>/WEB-INF/tlds/jstl/fn.tld</taglib-location>
</taglib>


 

jsp 에서

 

<%@ taglib uri="jstl-c" prefix="c" %>

<%@ taglib uri="jstl-fmt" prefix="fmt" %>

<%@ taglib uri="jstl-fn" prefix="fn" %>


EL#

  1. 생존범위 속성 맵

    1. pageScope
    2. requestScope
    3. sessionScope
    4. applicationScope
  2. 요청 파라미터 맵

    1. param
    2. paramValues
  3. 요청 헤더 맵

    1. header
    2. headerValues
  4. 쿠키 맵

    1. cookie
  5. 컨텍스트 초기화 파라미터 맵(서블릿 초기화 파라미터 아님)

    1. initParam
  6. 실제 pageContext 객체에 대한 참조. 이것은 빈임

    1. pageContext

      1. pageContext 접근자

        1. getErrorData()
        2. getPage()
        3. getRequest()
        4. getResponse()
        5. getServletConfig)()
        6. getServletContext()
        7. getSession()
      2. JspContext로 부터 상속받은 접근자

        1. getAttribute()
        2. getAttributeNamesInScope()
        3. getAttributesScope()
        4. getExpression!Eval!uator()
        5. getOut()
        6. getVariableResolver()



스크립팅

  1. <$= request.getHeader("host") %>

EL 내장 객체

  1. ${header["host"]}
  2. ${header.host}
  3. ${headerValues.host[]}


스크립팅

  1. <%= request.getMethod() %>

EL 내장 객체

  1.  ${pageContext.request.method}

 

core

 

<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>

  • 일반적인 것

    • <c:out>
    • <c:set>
    • <c:remove>
    • <c:catch>
  • 조건

    • <c:if>
    • <c:choose>
    • <c:when>
    • <c:otherwise>
  • URL 관련

    • <c:import!>
    • <c:url>
    • <c:redirect>
    • <c:param>
  • 반복

    • <c:forEach>
    • <c:forEachToken>


① set


     - JSP의 setAttribute()와 같은 역활
     - 기본형
       <c:set   var="변수명"
                    value="변수명에 할당된 값"
                    target="자바빈 객체명이나 Map 객체명"
                    property="자바빈 객체나 Map 객체의 값을 설정할 프로퍼티 명"
                    scope="변수의 공유 범위(유효기간)으로 page|request|session|application" />
     - 예제
          <c:set var="country" value="${'Korea'}" />
          <c:set var="intArray" value="<%=new int[] {1,2,3,4,5}%>" />
          <c:set var="sum" value="${sum+i}" />
 
② out


     - JSP의 표현식을 대체하는 것으로 많이 사용됨
     - 기본형
          <c:out var="변수명"
                    default="기본값"
                    escapeXML="true|false" />
 
     * escapeXML
     > 생략시 기본값은 true
     > true일 경우 값 중에 포함된 <>&'" 문자들을 각각 <, >, &, ', "로 출력

     - 예제
          <c:out value="${sum}" />
          <c:out value="${val}" />
 
③ remove


     - JSP의 removeAttribute()와 같은 역활
     - 기본형
          <c:remove var="변수명"
                              scope="변수의 공유 범위로 page(생략 시 기본)|request|session|application" />
     - 예제
          <c:remove var="browser" />
 
④ catch


     - body 위치에서 실행되는 코드의 예외를 잡아내는 역할
     - 기본형
          <c:catch var="에러가 발생할 때 에러 메세지가 포함될 변수명" />
     - 예제
          <c:catch var="errmsg">
               line 1~
               <%=1/0%>
               line 2~
          </c:catch>
          <c:out value="${errmsg}" />
 
⑤ if


     - 조건문에 사용
     - 기본형
          <c:if   test="조건 판별식"
                    var="변수명"
                    scope="변수의 공유범위 page|request|session|application"
     - 예제
          <c:if test="${country != null}">
               국가명 : <c:out value="${country}" />
          </c:if>
 
⑥ choose


     - 자바의 switch문과 동일
     - 조건에서 문자열 비교가 가능
     - 하나 이상의 <when>과 하나의 <otherwise> 서브 태그를 가짐
 
⑦ when


     - choose 태그의 서브태그
     - choose 태그내에서 여러번 사용될 수 있다.
     - 기본형
          <c:when test="조건 판별식" />
 
⑧ otherwise


     - choose 태그의 서브태그
     - choose 태그내에서 한번만 사용될 수 있다.
     - 예제 :
          <c:choose>
               <c:when test="${country == 'Korea'}">
               나라 : <c:out value="${country}" />
          </c:when>
 
          <c:when test="${country == 'Canada'}">
               나라 : <c:out value="${country}" />
          </c:when>
   
          <c:otherwise>
               선택된 나라가 없습니다.
          </c:otherwise>
     </c:choose>
 
⑨ forEach


     - 객체 전체에 걸쳐 반복 실행할 때 사용
     - 기본형
          <c:forEach   items="반복할 객체명"
                              begin="시작값"
                              end="종료값"
                              step="증가값"
                              var="변수명"
                              varStatus="별도의 변수" />

⑩ forTokens


     - 문자열을 주어진 구분자(delimiter)로 분할
     - 기본형
          <c:forTokens items="반복할 객체명"
                              delims="구분자"
                              begin="반복할 시작값"
                              end="반목 마지막값"
                              step="증가값"
                              var="변수명"
                              varStatus="별도의 변수"
     - 예제
          <c:forTokens var="color" items="빨강색,주황색.노란색.초록색,파랑색,남색.보라색" delims=",.">
               color : <c:out value="${color}" /><br>
          </c:forTokens>
 
⑪ import!


 - 웹 어플리케이션 내부의 자원 및 http, ftp와 같은 외부에 있는 자원에 대해 접근
 - 기본형
  <c:import! url="읽어올 URL"
     var="읽어올 데이터를 저장할 변수명"
     scope="변수의 공유 범위"
     varReader="리소스의 내용을 Reader 객체로 읽어올 때 사용"
     charEncoding="읽어온 데이터의 캐릭터셋 지정" />
 
⑫ redirect


     - response.sendRedirect()를 대체하는 태그로 지정한 다른 페이지로 이동
     - 기본형
          <c:redirect url="이동할 URL" />
 
⑬ url


     - 쿼리 파라미터로 부터 URL 생성
     - 기본형
          <c:url var="생성한 URL이 저장될 변수명"
                    value="생성할 URL"
                    scope="변수의 공유 범위" />
 
⑭ param


     - 기본형
          <c:param name="파라미터 명"
                         value="파라미터 값" />
               <c:url var="registrationURL" value="/customers/register">
               <c:param name="name" value="${param.name}" />
               <c:param name="country" value="${param.country}" />
          </c:url>


<c:set var="temp" value="Hello! World" />
<c:out value="${ temp }" default="value is null"/><br>
<c:out value="${ temp }" default="value is null" escapeXml="false" /><br>
<c:out value="${ temp2 }" default="value is null" /><br>

<c:remove var="timezone" scope="session"/>
<c:set var="timezone" scope="session">CST</c:set>

<c:out value="${cookie['tzPref'].value}" default=="CST"/>

 

function
<%@ taglib prefix="fn" uri="http://java.sun.com/jsp/jstl/functions" %>

${fn:substring(name, 1, 10)}


fn:contains(string, substring)  
string이 substring을 포함하면 true 리턴. 

fn:containsIgnoreCase(string,substring)
대소문자에 관계없이, string이 substring을 포함하면 true 리턴. 

fn:endsWith(string, suffix)   
string이 suffix로 끝나면 true 리턴. 

fn:escapeXml(string)    
string에 XML과 HTML에서 특별한 의미를 가진 문자들이 있으면, XML 엔티티 코드로 바꿔준 뒤 문자열 리턴. 

fn:indexOf(string,substring)  
string에서 substring이 처음으로 나타나는 인덱스 리턴. 

fn:join(array, separator)
  
array(배열) 요소들을 separator를 구분자로 하여 연결해서 리턴 

fn:length(item)
      
item 이 배열이나 컬렉션이면 요소의 갯수를, 문자열이면 문자의 갯수를 리턴. 

fn:replace(string, before, after)
 
string 내에 있는 before 문자열을 after 문자열로 모두 바꿔서 리턴. 

fn:split(string, separator)
   
string 내의 문자열을 separator에 따라 나누어서 배열로 구성해 리턴. 

fn:startsWith(string, prefix)
  
string이 prefix로 시작하면 true 리턴. 

fn:substring(string, begin, end)
 
tring에서 begin 인덱스에서 시작해서 end 인덱스에 끝나는 부분
(end 인덱스에 있는문자 포함)의 문자열을 리턴.

fn:substringAfter(string, substring)

string에서 substring이 나타나는 이후의 부분에 있는 문자열을 리턴. 

fn:substringBefore(string, substring)

string에서 substring이 나타나기 이전의 부분에 있는 문자열을 리턴. 

fn:toLowerCase(string)
    
string을 모두 소문자로 바꿔 리턴. 

fn:toUpperCase(string)
    
string을 모두 대문자로 바꿔 리턴. 

fn:trim(string)
      
string 앞뒤의 공백(whitespace)을 모두 제거하여 리턴.


fmt

 

<%@ taglib prefix="fmt" uri="http://java.sun.com/jsp/jstl/fmt" %>

  • 국제화

    • <fmt:message>
    • <fmt:setLocale>
    • <fmt:setTimeZone>
    • <fmt:bundle>
    • <fmt:setBundle>
    • <fmt:param>
    • <fmt:requestEncoding>
  • 포맷팅

    • <fmt:timeZone>
    • <fmt:setTimeZone>
    • <fmt:formatNumber>
    • <fmt:formatDate>
    • <fmt:parseNumber>
    • <fmt:parseData>
    • <fmt:parseNumber>



jstl fmt로 날짜보여줄때, pattern attribute에 의한 날짜 표현 방식들

pattern="yyyy-MM-dd aa h:mm:ss"    
2007-12-13 오전 9:36:48

pattern="yyyy-MM-dd aa hh:mm:ss"  
2007-12-13 오전 09:36:48

pattern="yyyy-MM-dd H:mm:ss"      
2007-12-13 9:36:48

pattern="yyyy-MM-dd HH:mm:ss"    
2007-12-13 09:36:48


<fmt:setLocale value="fr_CA" scope="session"/>
<fmt:setTimeZone value="Australia/Brisbane" scope="session"/>

<fmt:formatDate value="${blogEntry.created}" dateStyle="full"/>
<c:out value="${blogEntry.title}" escapeXml="false"/>
<fmt:formatDate value="${blogEntry.created}" pattern="h:mm a zz"/>
<fmt:formatNumber value="0.02" type="currency" currencySymbol="원"/>

<fmt:formatNumber value="9876543.61" type="number"/>

[type="{number|currency|percent}"]


<fmt:parseDate value="${usDateString}" parseLocale="en_US" type="both" dateStyle="short" timeStyle="short" var="usDate"/>

 

sql
<%@ taglib uri="http://java.sun.com/jsp/jstl/sql" prefix="sql" %>
  • 데이터베이스 접근

    • <sql:query>
    • <sql:update>
    • <sql:setDataSource>
    • <sql:param>
    • <sql:dataParam>



xml

<%@ taglib uri="http://java.sun.com/jsp/jstl/xml" prefix="x" %>

  • 코어 xml 액션

    • <x:parse>
    • <x:out>
    • <x:set>
  • xml 흐름 제어

    • <x:if>
    • <x:choose>
    • <x:when>
    • <x:otherwise>
    • <x:forEach>
  • 변환 액션

    • <x:transform>
    • <x:param>

http://blog.daum.net/sowebpro/7163216 --> 이곳에서 퍼왓습니다. 감사합니다.

보통 java application을 실행할 때 java.exe를 이용해서 실행한다.


하지만, java.exe 는 console window command 이므로 java.exe 를 이용해서 application을 실행한 후 cmd 창을 닫게되면 해당 application이 같이 종료되게 된다.


Background로 실행하기 위해서 Unix에서는 & 명령어를 이용해서 쉽게 실행가능 하지만, Window에서는 어떻게 해야 할지에 대해서 한참을 구글링해야만 했다. 


알고나면 쉬운 것을 알기 전까지는 왜 이렇게 어려운 것일까?...ㅠㅠ


console window를 종료하더라도 실행한 application이 종료되지 않게 background 로 실행시키려면 javaw.exe를 이용하면 된다.

e.g: javaw.exe MyJavaApp


하지만, background로 실행된다고 하더라도 windows 의 경우 보통 .bat 파일을 이용해서 java application을 실행하게 되므로 위와 같은 명령어로 작성된 bat 파일은 open된 console window가 닫히지 않고 열린채 그대로 있게 된다.


그럴때에는 javaw.exe 명령어 앞에, start /B 를 추가해서 실행해 주면 java application 실행 후 자동으로 cmd 창이 닫혀지게 된다.

e.g: start /B javaw.exe MyJavaApp


e.g: RunJavaAppOnCMD.bat - console window mode java application execution.

java MyJavaApp


e.g: RunJavaAppInBackgroundAndNotCloseCMD.bat - background mode java application execution.

javaw MyJavaApp

 


 

e.g: RunJavaAppInBackgroundAndCloseCMD.bat - background mode java application execution and close console automatically.

start /B javaw MyJavaApp

 

 



참조: 

"javaw.exe" belongs to Java from Sun Microsystems, Inc..http://www.neuber.com/taskmanager/process/javaw.exe.html 

The javaw.exe command is identical to java.exe, except that with javaw.exe there is no associated console window. This implies you can't get it to display the version with -version, since there is no console to display it on. Use javaw.exe when you don't want a command prompt window to appear. The javaw.exe launcher will, however, display a dialog box with error information if a launch fails for some reason.

 

[출처]http://blog.daum.net/oiztlomo/4609505

'DEVELOPMENT > Java' 카테고리의 다른 글

클래스 동적 로딩하기  (0) 2015.06.01
JSTL 요약  (0) 2014.08.05
java 화면캡쳐 샘플  (0) 2013.12.04
Java Process Kill Script  (0) 2013.09.04
jdom을 이요한 XML 쓰기와 읽기  (0) 2013.08.23

  1. import java.awt.AWTException;
  2. import java.awt.Dimension;
  3. import java.awt.Rectangle;
  4. import java.awt.Robot;
  5. import java.awt.Toolkit;
  6. import java.awt.image.BufferedImage;
  7. import javax.imageio.ImageIO;
  8. import java.io.File;
  9. import java.io.IOException;
  10. import javax.imageio.ImageIO;
  11.  
  12. public class Test {
  13.     public static void main(String[] args){
  14.         captureScreen("c:\\captureImage.png");
  15.     }
  16.    
  17.     public static void captureScreen(String fileName) {
  18.         Dimension screenSize = Toolkit.getDefaultToolkit().getScreenSize();
  19.         Rectangle screenRectangle = new Rectangle(screenSize);
  20.         Robot robot = null;
  21.         try {
  22.             robot = new Robot();
  23.             BufferedImage image = robot.createScreenCapture(screenRectangle);
  24.             ImageIO.write(image, "png"new File(fileName));
  25.         } catch (AWTException e) {
  26.             e.printStackTrace();
  27.         } catch (IOException e) {
  28.             e.printStackTrace();
  29.         }
  30.     }
  31. }



'DEVELOPMENT > Java' 카테고리의 다른 글

JSTL 요약  (0) 2014.08.05
windows에서 java application을 background에서 실행  (0) 2014.03.19
Java Process Kill Script  (0) 2013.09.04
jdom을 이요한 XML 쓰기와 읽기  (0) 2013.08.23
eclipse SWT/JFace 라이브러리 추가  (0) 2013.06.12

자바프로세스를 찾아 없애도록 한다.

ps -ef | grep java | grep -v grep | awk '{print "kill " $2}' | sh -v

 

[출처] http://www.imnuz.net/entry/Java-Process-Kill-Script?category=40

'DEVELOPMENT > Java' 카테고리의 다른 글

windows에서 java application을 background에서 실행  (0) 2014.03.19
java 화면캡쳐 샘플  (0) 2013.12.04
jdom을 이요한 XML 쓰기와 읽기  (0) 2013.08.23
eclipse SWT/JFace 라이브러리 추가  (0) 2013.06.12
java openGL  (0) 2012.08.23


필요라이브러리 dom4j-1.6.1.jar


XML 쓰기

import org.jdom.Document;

import org.jdom.Element;

import org.jdom.input.SAXBuilder;

import org.jdom.output.XMLOutputter;


public class XMLWriterExample{

public static void main(String[] args) {

Element element = null;

Document document = null;

try{

SAXBuilder builder = new SAXBuilder();

element = new Element("root"); //rootElement 생성

 //하위 엘레먼트 생성후 속성 추가 및 text 추가

Element sub = new Element("sub").setAttribute("test1", "aaaa").setText("안녕하세요");

element.addContent(sub); //root Element에 sub Element 추가

document = new Document(element);

      

      //파일 생성

XMLOutputter out = new XMLOutputter();

out.output(document, new FileOutputStream(new File("d://test.xml")));

}catch(Exception e){

//TODO Exception 처리

}

}

}



XML 읽기

package url;


import java.io.FileOutputStream;

import java.net.URL;

import java.util.List;

import org.jdom.Document;

import org.jdom.Element;

import org.jdom.input.SAXBuilder;

import org.jdom.output.XMLOutputter;



public class Ex2 {

    public static void main(String[] args) throws Exception {

        URL url = new URL("http://openapi.naver.com/search?key=7d78ca29b1966e2cafee0327b181429d&target=movie&query=java&display=50&start=1&sort=sim");


        //xml이기 때문에 그냥 String을 이용하는 것이 아니라 JDOM으로 파싱하여 편하게 사용하고 싶습니다 (DOM구조)


        Document doc = new SAXBuilder().build(url);


        //root엘리먼트인 rss요소를 뽑아오기

        Element rss = doc.getRootElement();


        //rss의 자식인 channel요소를 얻고

        Element channel = rss.getChild("channel");

        //channel의 자식인 item요소들을 얻습니다.

        List<Element> itemList = channel.getChildren("item");


        //item 이라는게 책이다

        //책이름과 저자, 가격을 출력해 봅시다


        for(Element book : itemList){

            System.out.print("영화제목 : "+ book.getChildText("title") + " \t");

            //book.getChild("title").getText();

            System.out.print("감독 : " + book.getChildText("director") + "\t");

            System.out.println("배우 : " + book.getChildText("actor"));

        }

        //실제파일로 저장해 봅시다.

        XMLOutputter xout = new XMLOutputter();


        //파일로 저장

        xout.output(doc, new FileOutputStream("c:/movie.xml"));

        //콘솔창 출력

        xout.output(doc, System.out);

    }


'DEVELOPMENT > Java' 카테고리의 다른 글

java 화면캡쳐 샘플  (0) 2013.12.04
Java Process Kill Script  (0) 2013.09.04
eclipse SWT/JFace 라이브러리 추가  (0) 2013.06.12
java openGL  (0) 2012.08.23
자바 정규표현식  (0) 2012.05.17

eclipse에서 SWT/JFace를 개발하기 위해서 swt, JFace 관련 라이브러리를 추가해야 한다.

관련 라이브러리는 eclipse에 기본적으로 있으니 그걸 사용해서 추가해주면 된다.

 

관련 프로젝트에 속성에서 java Build Path 메뉴에 Libraries 탭에서 에서 설정을 한다.

Libraries 탭에서 Add Variable 버튼을 선택하고 뜨는 팝업창에서 Configure Variables... 버튼을 누른다.

또 하나의 팝업창이 뜨는데 여기에서 Classpath Variables 메뉴에서 New 버튼을 통하여 아래 내용을 등록하면 된다.

이클립스 버전에 따라서 해당 jar 파일이 다를 수 있으니 유념해서 넣어준다.

 

 

Name : SWT_LIB
Path : workspace폴더/wt-3.3-win32-win32-x86/swt.jar

Name : JFACE_LIB
Path : eclipse폴더/plugins/org.eclipse.jface_xxxxx.jar

Name : BOOT_LIB
Path : eclipse폴더/plugins/org.eclipse.core.boot_xxxxx.jar //eclipse juno에서는 없더라...

Name : RUNTIME_LIB
Path : eclipse폴더/plugins/org.eclipse.core.runtime_xxxxx.jar

Name : JFACETEXT_LIB
Path : eclipse폴더/plugins/org.eclipse.jface.text_xxxxx.jar

Name : TEXT_LIB
Path : eclipse폴더/plugins/org.eclipse.text_xxxxx.jar

Name : OSGI_LIB
Path : eclipse폴더/plugins/org.eclipse.osgi_xxxxx.jar

Name : EQUINOX_LIB
Path : eclipse폴더/plugins/org.eclipse.equinox.common_xxxxx.jar

Name : COMMANDS_LIB
Path : eclipse폴더/plugins/org.eclipse.core.commands_xxxxx.jar

'DEVELOPMENT > Java' 카테고리의 다른 글

Java Process Kill Script  (0) 2013.09.04
jdom을 이요한 XML 쓰기와 읽기  (0) 2013.08.23
java openGL  (0) 2012.08.23
자바 정규표현식  (0) 2012.05.17
대용량 데이터 처리를 위한 JAVA Tunning(튜닝)  (0) 2012.05.17

java openGL

DEVELOPMENT/Java2012. 8. 23. 23:37

/* JOGL(Java OpenGL) 관련 링크 */

 

//Jogl HOME -> sample, source, download...
https://jogl.dev.java.net/

 

//JSR 231: Java bindings to the OpenGL native 3D graphics library
http://jcp.org/en/jsr/detail?id=231

 

//Java Games - Forums -> jogl - Java Bindings for OpenGL
//Jogle 개발관련 정보를 자세히 알 수 있는 포럼
http://www.javagaming.org/forums/index.php

 

//Jogle 관련 wiki (초기진행중)
http://wiki.java.net/bin/view/Games/JOGL

 

//JOGL: A Beginner's Guide and Tutorial By Kevin Conroy
http://www.cs.umd.edu/~meesh/kmconroy/JOGLTutorial/

 

//이구철 블로그 : Java + Eclipse + Jogl 철치 및 예제
http://blog.naver.com/dcknsk/50000002701

 

//Jogl 설치 관련...
http://www.mobilefish.com/developer/jogl/jogl.html

 

//Juggling JOGL : Jogl 2d 예제

http://today.java.net/pub/a/today/2004/03/18/jogl-2d-animation.html

 

//Learning Java Bindings for OpenGL (JOGL)

// -> Book : 3 개의 Sample Chapter 제공 

http://www.genedavissoftware.com/books/jogl/

 

 

/* NeHe(OpenGL Tutorials) + Jogl 관련 링크 */

 

//NeHe OpenGL Tutorials
http://nehe.gamedev.net/

 

//NeHe 예제를 Jogl(JSR 231 적용)로 구현한 예제 파일들... 
//예전의 Jogl을 이용한 것은 NeHe 홈에서 구할 수 있음.
http://pepijn.fab4.be/?page_id=34

 

//NeHe OpenGL Tutorial 한글 번역(중)
http://www.galexandria.com/doc/index.php/%EB%B6%84%EB%A5%98:NeHe

 

 

/* OpenGL */

 

//OpenGL Programming Guide or 'The Red Book'

http://www.rush3d.com/reference/opengl-redbook-1.1/

 

 

/* 기타 : 게임, 멀티미디어 관련 자바 정보... */

 

//Book : Killer Game Programming in Java
http://fivedots.coe.psu.ac.th/~ad/jg/

 

//QuickTime for Java
http://developer.apple.com/quicktime/qtjava/

 

//Sun 의 간략한 AWT 강의

http://java.sun.com/developer/onlineTraining/awt/contents.html

 

//프리맨의 자바잡이 -> 자바 기초 강의

http://www.impunity.co.kr/~rfm98/ver3/chobo/chobo.html

자바의 정규표현식은 J2SE 1.4 부터 지원되지 시작했습니다. 관련된 주요 클래스들는 java.util.regex 팩키지에 있습니다.

Pattern 클래스

Pattern 객체는 Perl 문법과 비슷한 형태로 정의된 정규표현식을 나타냅니다. 문자열로 정의한 정규표현식은 사용되기 전에 반드시 Pattern 클래스의 인스턴스로 컴파일되어야 합니다. 컴파일된 패턴은 Matcher 객체를 만드는 데 사용되며, Matcher 객체는 임의의 입력 문자열이 패턴에 부합되는 지 여부를 판가름하는 기능을 담당하합니다. 또한 Pattern 객체들은 비상태유지 객체들이기 때문에 여러 개의 Matcher 객체들이 공유할 수 있습니다.

Matcher 클래스

Matcher 객체는 특정한 문자열이 주어진 패턴과 일치하는가를 알아보는데 이용됩니다. Matcher 클래스의 입력값으로는 CharSequence라는 새로운 인터페이스가 사용되는데 이를 통해 다양한 형태의 입력 데이터로부터 문자 단위의 매칭 기능을 지원 받을 수 있습니다. 기본적으로 제공되는 CharSequence 객체들은 CharBuffer, String, StringBuffer 클래스가 있습니다.

Matcher 객체는 Pattern 객체의 matcher 메소드를 통해 얻어진다. Matcher 객체가 일단 만들어지면 주로 세 가지 목적으로 사용됩다.

  • 주어진 문자열 전체가 특정 패턴과 일치하는 가를 판단(matches).
  • 주어진 문자열이 특정 패턴으로 시작하는가를 판단(lookingAt).
  • 주어진 문자열에서 특정 패턴을 찾아낸다(find).

이들 메소드는 성공 시 true를 실패 시 false 를 반환합니다.

또한 특정 문자열을 찾아 새로운 문자열로 교체하는 기능도 제공됩니다. appendRepalcement 메소드는 일치하는 패턴이 나타날 때까지의 모든 문자들을 버퍼로 옮기고 찾아진 문자열 대신 교체 문자열로 채워 넣습니다. 또한 appendTail 메소드는 캐릭터 시퀀스의 현재 위치 이후의 문자들을 버퍼에 복사해 넣습니다. 다음 절에 나오는 예제 코드를 참고하도록 합시다.

CharSequence 인터페이스

CharSequence 인터페이스는 다양한 형태의 캐릭터 시퀀스에 대해 일관적인 접근 방법을 제공하기 위해 새로 생겨났으며, java.lang 패키지에 존재합니다. 기본적으로 String, StringBuffer, CharBuffer 클래스가 이를 구현하고 있으므로 적절한 것을 골라 사용하면 되며, 인터페이스가 간단하므로 필요하면 직접 이를 구현해 새로 하나 만들어도 됩니다.



자바 정규표현식 사용 예제

기본 사용 예제

소스

import java.util.regex.Matcher;
import java.util.regex.Pattern;

/**
 * 정규표현식 기본 사용 예제 
 * 
 * @author   Sehwan Noh <sehnoh at java2go.net>
 * @version  1.0 - 2006. 08. 22
 * @since    JDK 1.4
 */
public class RegExTest01 {

    public static void main(String[] args) {

        Pattern p = Pattern.compile("a*b");
        Matcher m = p.matcher("aaaaab");
        boolean b = m.matches();
        
        if (b) {
            System.out.println("match");
        } else {
            System.out.println("not match");
        }
    }
}

결과

match

문자열 치환하기

소스

import java.util.regex.Matcher;
import java.util.regex.Pattern;

/**
 * 문자열 치환 예제
 * 
 * @author   Sehwan Noh <sehnoh at java2go.net>
 * @version  1.0 - 2006. 08. 22
 * @since    JDK 1.4
 */
public class RegExTest02 {

    public static void main(String[] args) {

        Pattern p = Pattern.compile("cat");
        Matcher m = p.matcher("one cat two cats in the yard");
        
        StringBuffer sb = new StringBuffer();
        while (m.find()) {
            m.appendReplacement(sb, "dog");
        }
        m.appendTail(sb);
        System.out.println(sb.toString());
        
        // or
        //String str = m.replaceAll("dog");
        //System.out.println(str);
    }
}

결과

one dog two dogs in the yard

이메일주소 유효검사

소스

import java.util.regex.Matcher;
import java.util.regex.Pattern;

/**
 * 이메일주소 유효검사
 * 
 * @author   Sehwan Noh <sehnoh at java2go.net>
 * @version  1.0 - 2006. 08. 22
 * @since    JDK 1.4
 */
public class RegExTest03 {
    
    public static boolean isValidEmail(String email) {
        Pattern p = Pattern.compile("^(?:\\w+\\.?)*\\w+@(?:\\w+\\.)+\\w+$");
        Matcher m = p.matcher(email);
        return m.matches();
    }

    public static void main(String[] args) {
        
        String[] emails = { "test@abc.com", "a@.com", "abc@mydomain" };
        
        for (int i = 0; i < emails.length; i ++) {
            if (isValidEmail(emails[i])) {
                System.out.println(emails[i]);
            }
        }
    }
}

결과

test@abc.com

HTML 태그 제거

소스

import java.util.regex.Matcher;
import java.util.regex.Pattern;

/**
 * HTML 태그 제거
 * 
 * @author   Sehwan Noh <sehnoh at java2go.net>
 * @version  1.0 - 2006. 08. 22
 * @since    JDK 1.4
 */
public class RegExTest04 {

    public static String stripHTML(String htmlStr) {
        Pattern p = Pattern.compile("<(?:.|\\s)*?>");
        Matcher m = p.matcher(htmlStr);
        return m.replaceAll("");
    }
    
    public static void main(String[] args) {
        String htmlStr = "<html><body><h1>Java2go.net</h1>"
            + " <p>Sehwan@Noh's Personal Workspace...</p></body></html>";
        System.out.println(stripHTML(htmlStr));        
    }
}

결과

Java2go.net Sehwan@Noh's Personal Workspace...

HTML 링크 만들기

소스

import java.util.regex.Matcher;
import java.util.regex.Pattern;

/**
 * HTML 링크 만들기
 * 
 * @author   Sehwan Noh <sehnoh at java2go.net>
 * @version  1.0 - 2006. 08. 22
 * @since    JDK 1.4
 */
public class RegExTest05 {

    public static String linkedText(String sText) {
        Pattern p = Pattern.compile("(http|https|ftp)://[^\\s^\\.]+(\\.[^\\s^\\.]+)*");
        Matcher m = p.matcher(sText);

        StringBuffer sb = new StringBuffer();
        while (m.find()) {
            m.appendReplacement(sb, "<a href='" + m.group()+"'>" + m.group() + "</a>");
        }
        m.appendTail(sb);

        return sb.toString();
    }    
        
    public static void main(String[] args) {        
        String strText = "My homepage URL is http://www.java2go.net/home/index.html.";
        System.out.println(linkedText(strText));
    }
}

결과

My homepage URL is <a href='http://www.java2go.net/index.html'>http://www.java2go.net/index.html</a>.

금지어 필터링하기

소스

import java.util.regex.Matcher;
import java.util.regex.Pattern;

/**
 * 금지어 필터링하기
 * 
 * @author   Sehwan Noh <sehnoh at java2go.net>
 * @version  1.0 - 2006. 08. 22
 * @since    JDK 1.4
 */
public class RegExTest06 {
    
    public static String filterText(String sText) {
        Pattern p = Pattern.compile("fuck|shit|개새끼", Pattern.CASE_INSENSITIVE);
        Matcher m = p.matcher(sText);

        StringBuffer sb = new StringBuffer();
        while (m.find()) {
            //System.out.println(m.group());
            m.appendReplacement(sb, maskWord(m.group()));
        }
        m.appendTail(sb);
        
        //System.out.println(sb.toString());
        return sb.toString();
    }
    
    public static String maskWord(String word) {
        StringBuffer buff = new StringBuffer();
        char[] ch = word.toCharArray();
        for (int i = 0; i < ch.length; i++) {
            if (i < 1) {
                buff.append(ch[i]);
            } else {
                buff.append("*");
            }
        }
        return buff.toString();
    }
    
    public static void main(String[] args) {
        String sText = "Shit! Read the fucking manual. 개새끼야.";        
        System.out.println(filterText(sText));
    }
}

결과

S***! Read the f***ing manual. 개**야.


Java Regex References

A regular expression, specified as a string, must first be compiled into an instance of this class. The resulting pattern can then be used to create a Matcher object that can match arbitrary character sequences against the regular expression. All of the state involved in performing a match resides in the matcher, so many matchers can share the same pattern.

A typical invocation sequence is thus

 Pattern p = Pattern.compile("a*b");
 Matcher m = p.matcher("aaaaab");
 boolean b = m.matches();

A matches method is defined by this class as a convenience for when a regular expression is used just once. This method compiles an expression and matches an input sequence against it in a single invocation. The statement

 boolean b = Pattern.matches("a*b", "aaaaab");
is equivalent to the three statements above, though for repeated matches it is less efficient since it does not allow the compiled pattern to be reused.

Instances of this class are immutable and are safe for use by multiple concurrent threads. Instances of the Matcher class are not safe for such use.

Summary of regular-expression constructs

ConstructMatches
 
Characters
xThe character x
\\The backslash character
\0nThe character with octal value 0n (0 <= n <= 7)
\0nnThe character with octal value 0nn (0 <= n <= 7)
\0mnnThe character with octal value 0mnn (0 <= m <= 3, 0 <= n <= 7)
\xhhThe character with hexadecimal value 0xhh
\uhhhhThe character with hexadecimal value 0xhhhh
\tThe tab character ('\u0009')
\nThe newline (line feed) character ('\u000A')
\rThe carriage-return character ('\u000D')
\fThe form-feed character ('\u000C')
\aThe alert (bell) character ('\u0007')
\eThe escape character ('\u001B')
\cxThe control character corresponding to x
 
Character classes
[abc]a, b, or c (simple class)
[^abc]Any character except a, b, or c (negation)
[a-zA-Z]a through z or A through Z, inclusive (range)
[a-d[m-p]]a through d, or m through p: [a-dm-p] (union)
[a-z&&[def]]d, e, or f (intersection)
[a-z&&[^bc]]a through z, except for b and c: [ad-z] (subtraction)
[a-z&&[^m-p]]a through z, and not m through p: [a-lq-z](subtraction)
 
Predefined character classes
.Any character (may or may not match line terminators)
\dA digit: [0-9]
\DA non-digit: [^0-9]
\sA whitespace character: [ \t\n\x0B\f\r]
\SA non-whitespace character: [^\s]
\wA word character: [a-zA-Z_0-9]
\WA non-word character: [^\w]
 
POSIX character classes (US-ASCII only)
\p{Lower}A lower-case alphabetic character: [a-z]
\p{Upper}An upper-case alphabetic character:[A-Z]
\p{ASCII}All ASCII:[\x00-\x7F]
\p{Alpha}An alphabetic character:[\p{Lower}\p{Upper}]
\p{Digit}A decimal digit: [0-9]
\p{Alnum}An alphanumeric character:[\p{Alpha}\p{Digit}]
\p{Punct}Punctuation: One of !"#$%&'()*+,-./:;<=>?@[\]^_`{|}~
\p{Graph}A visible character: [\p{Alnum}\p{Punct}]
\p{Print}A printable character: [\p{Graph}\x20]
\p{Blank}A space or a tab: [ \t]
\p{Cntrl}A control character: [\x00-\x1F\x7F]
\p{XDigit}A hexadecimal digit: [0-9a-fA-F]
\p{Space}A whitespace character: [ \t\n\x0B\f\r]
 
java.lang.Character classes (simple java character type)
\p{javaLowerCase}Equivalent to java.lang.Character.isLowerCase()
\p{javaUpperCase}Equivalent to java.lang.Character.isUpperCase()
\p{javaWhitespace}Equivalent to java.lang.Character.isWhitespace()
\p{javaMirrored}Equivalent to java.lang.Character.isMirrored()
 
Classes for Unicode blocks and categories
\p{InGreek}A character in the Greek block (simple block)
\p{Lu}An uppercase letter (simple category)
\p{Sc}A currency symbol
\P{InGreek}Any character except one in the Greek block (negation)
[\p{L}&&[^\p{Lu}]] Any letter except an uppercase letter (subtraction)
 
Boundary matchers
^The beginning of a line
$The end of a line
\bA word boundary
\BA non-word boundary
\AThe beginning of the input
\GThe end of the previous match
\ZThe end of the input but for the final terminator, if any
\zThe end of the input
 
Greedy quantifiers
X?X, once or not at all
X*X, zero or more times
X+X, one or more times
X{n}X, exactly n times
X{n,}X, at least n times
X{n,m}X, at least n but not more than m times
 
Reluctant quantifiers
X??X, once or not at all
X*?X, zero or more times
X+?X, one or more times
X{n}?X, exactly n times
X{n,}?X, at least n times
X{n,m}?X, at least n but not more than m times
 
Possessive quantifiers
X?+X, once or not at all
X*+X, zero or more times
X++X, one or more times
X{n}+X, exactly n times
X{n,}+X, at least n times
X{n,m}+X, at least n but not more than m times
 
Logical operators
XYX followed by Y
X|YEither X or Y
(X)X, as a capturing group
 
Back references
\nWhatever the nth capturing group matched
 
Quotation
\Nothing, but quotes the following character
\QNothing, but quotes all characters until \E
\ENothing, but ends quoting started by \Q
 
Special constructs (non-capturing)
(?:X)X, as a non-capturing group
(?idmsux-idmsux) Nothing, but turns match flags on - off
(?idmsux-idmsux:X)  X, as a non-capturing group with the given flags on - off
(?=X)X, via zero-width positive lookahead
(?!X)X, via zero-width negative lookahead
(?<=X)X, via zero-width positive lookbehind
(?<!X)X, via zero-width negative lookbehind
(?>X)X, as an independent, non-capturing group

Backslashes, escapes, and quoting

The backslash character ('\') serves to introduce escaped constructs, as defined in the table above, as well as to quote characters that otherwise would be interpreted as unescaped constructs. Thus the expression \\ matches a single backslash and \{ matches a left brace.

It is an error to use a backslash prior to any alphabetic character that does not denote an escaped construct; these are reserved for future extensions to the regular-expression language. A backslash may be used prior to a non-alphabetic character regardless of whether that character is part of an unescaped construct.

Backslashes within string literals in Java source code are interpreted as required by the Java Language Specification as either Unicode escapes or other character escapes. It is therefore necessary to double backslashes in string literals that represent regular expressions to protect them from interpretation by the Java bytecode compiler. The string literal "\b", for example, matches a single backspace character when interpreted as a regular expression, while "\\b" matches a word boundary. The string literal "\(hello\)" is illegal and leads to a compile-time error; in order to match the string (hello) the string literal "\\(hello\\)" must be used.

Character Classes

Character classes may appear within other character classes, and may be composed by the union operator (implicit) and the intersection operator (&&). The union operator denotes a class that contains every character that is in at least one of its operand classes. The intersection operator denotes a class that contains every character that is in both of its operand classes.

The precedence of character-class operators is as follows, from highest to lowest:

1    Literal escape    \x
2    Grouping[...]
3    Rangea-z
4    Union[a-e][i-u]
5    Intersection[a-z&&[aeiou]]

Note that a different set of metacharacters are in effect inside a character class than outside a character class. For instance, the regular expression . loses its special meaning inside a character class, while the expression - becomes a range forming metacharacter.

Line terminators

line terminator is a one- or two-character sequence that marks the end of a line of the input character sequence. The following are recognized as line terminators:

  • A newline (line feed) character ('\n'),
  • A carriage-return character followed immediately by a newline character ("\r\n"),
  • A standalone carriage-return character ('\r'),
  • A next-line character ('\u0085'),
  • A line-separator character ('\u2028'), or
  • A paragraph-separator character ('\u2029).

If UNIX_LINES mode is activated, then the only line terminators recognized are newline characters.

The regular expression . matches any character except a line terminator unless the DOTALL flag is specified.

By default, the regular expressions ^ and $ ignore line terminators and only match at the beginning and the end, respectively, of the entire input sequence. If MULTILINE mode is activated then ^ matches at the beginning of input and after any line terminator except at the end of input. When in MULTILINE mode $ matches just before a line terminator or the end of the input sequence.

Groups and capturing

Capturing groups are numbered by counting their opening parentheses from left to right. In the expression ((A)(B(C))), for example, there are four such groups:

1    ((A)(B(C)))
2    (A)
3    (B(C))
4    (C)

Group zero always stands for the entire expression.

Capturing groups are so named because, during a match, each subsequence of the input sequence that matches such a group is saved. The captured subsequence may be used later in the expression, via a back reference, and may also be retrieved from the matcher once the match operation is complete.

The captured input associated with a group is always the subsequence that the group most recently matched. If a group is evaluated a second time because of quantification then its previously-captured value, if any, will be retained if the second evaluation fails. Matching the string "aba" against the expression (a(b)?)+, for example, leaves group two set to "b". All captured input is discarded at the beginning of each match.

Groups beginning with (? are pure, non-capturing groups that do not capture text and do not count towards the group total.

Unicode support

This class is in conformance with Level 1 of Unicode Technical Standard #18: Unicode Regular Expression Guidelines, plus RL2.1 Canonical Equivalents.

Unicode escape sequences such as \u2014 in Java source code are processed as described in ?.3 of the Java Language Specification. Such escape sequences are also implemented directly by the regular-expression parser so that Unicode escapes can be used in expressions that are read from files or from the keyboard. Thus the strings "\u2014" and "\\u2014", while not equal, compile into the same pattern, which matches the character with hexadecimal value 0x2014.

Unicode blocks and categories are written with the \p and \P constructs as in Perl. \p{prop} matches if the input has the property prop, while \P{prop} does not match if the input has that property. Blocks are specified with the prefix In, as in InMongolian. Categories may be specified with the optional prefix Is: Both \p{L} and \p{IsL} denote the category of Unicode letters. Blocks and categories can be used both inside and outside of a character class.

The supported categories are those of The Unicode Standard in the version specified by the Character class. The category names are those defined in the Standard, both normative and informative. The block names supported by Pattern are the valid block names accepted and defined by UnicodeBlock.forName.

Categories that behave like the java.lang.Character boolean ismethodname methods (except for the deprecated ones) are available through the same \p{prop} syntax where the specified property has the name javamethodname.

Comparison to Perl 5

The Pattern engine performs traditional NFA-based matching with ordered alternation as occurs in Perl 5.

Perl constructs not supported by this class:

  • The conditional constructs (?{X}) and (?(condition)X|Y),

  • The embedded code constructs (?{code}) and (??{code}),

  • The embedded comment syntax (?#comment), and

  • The preprocessing operations \l \u, \L, and \U.

Constructs supported by this class but not by Perl:

  • Possessive quantifiers, which greedily match as much as they can and do not back off, even when doing so would allow the overall match to succeed.

  • Character-class union and intersection as described above.

Notable differences from Perl:

  • In Perl, \1 through \9 are always interpreted as back references; a backslash-escaped number greater than 9 is treated as a back reference if at least that many subexpressions exist, otherwise it is interpreted, if possible, as an octal escape. In this class octal escapes must always begin with a zero. In this class, \1 through \9 are always interpreted as back references, and a larger number is accepted as a back reference if at least that many subexpressions exist at that point in the regular expression, otherwise the parser will drop digits until the number is smaller or equal to the existing number of groups or it is one digit.

  • Perl uses the g flag to request a match that resumes where the last match left off. This functionality is provided implicitly by the Matcher class: Repeated invocations of the find method will resume where the last match left off, unless the matcher is reset.

  • In Perl, embedded flags at the top level of an expression affect the whole expression. In this class, embedded flags always take effect at the point at which they appear, whether they are at the top level or within a group; in the latter case, flags are restored at the end of the group just as in Perl.

  • Perl is forgiving about malformed matching constructs, as in the expression *a, as well as dangling brackets, as in the expression abc], and treats them as literals. This class also accepts dangling brackets but is strict about dangling metacharacters like +, ? and *, and will throw a PatternSyntaxException if it encounters them.



    2010/09/30 - [개발 이야기/JAVA] - JAVA를 이용한 정규식 간단 사용법


    [출처]http://www.java2go.net/java/java_regex.html


'DEVELOPMENT > Java' 카테고리의 다른 글

eclipse SWT/JFace 라이브러리 추가  (0) 2013.06.12
java openGL  (0) 2012.08.23
대용량 데이터 처리를 위한 JAVA Tunning(튜닝)  (0) 2012.05.17
Apache Daemon 사용하기  (0) 2012.05.17
Quartz 문서  (0) 2011.07.13

대용량 데이타를 처리할 때는 1초 아니 0.001초도 아껴야 한다.
아래의 팁을 활용하여 수행 속도를 줄여 보자.

- 64bit OS 를 사용하고, 아끼지 말고 RAM을 추가해라.
CPU만 지원한다면, 무조건 64bit 운영체제를 설치해서 사용하라. RAM이 4GB 이하라도 설치해라.
CPU의 처리 단위 증가 뿐만 아니라, 메모리를 최대한 사용할 수 있기 때문에 GC의 회수가 감소하여 속도가 더 높아진다.

내 경우, Windows XP 32bit 에서 최대메모리가 약 1.5G 이상 불가능 했는데, 
Windows7 64bit 에서는 OS가 사용하는 메모리를 제외하고 모두 JVM이 사용할 수 있었다. 
1GB 파일을 생성하는데, 대략 5~10배 정도의 실행 시간 차이가 있었다.

- xms, xmx 옵션을 최대한 크게, 그리고 같게 잡는다.
다르게 잡아 줄 경우, 실행 도중에 메모리 할당이 이루어져서 실행 시간이 증가한다.

(1) Windows7 64bit (물리적 메모리가 4g인 경우)
java -jar -xms4g -xmx4g xxx.jar  
재미있는 것은 Windows7 64bit 에서는 이 두 값을 물리적 메모리 보다 크게 잡아도 실행이 된다. 이유는 모르겠다.

(2) Windows XP 32bit (물리적 메모리가 4g인 경우)
java -jar -xms1.5g -xmx1.5g xxx.jar  
아마  1~1.5 사이까지 가능할 것이다. 넘어 가면 실행 자체가 안 되는데 실행가능한 최대값을 찾아 사용하자.

- String 대신 StringBuilder를 사용하라. (단, 스레드를 사용할 경우에는 StringBuffer를 사용하라.)
문자열에 여러 가지 조작을 가할 경우이다. 변하지 않는 문자열의 경우, String을 사용하면 된다.
String을 사용하여도 컴파일러가 적당히 변환해 준다고는 하지만, 컴파일러는 항상 개발자보다 무식하다.

참고로 실행 속도는 StringBuilder > StringBuffer >> String 이며,  
메모리사용량은 StringBuilder = StringBuffer << String 이다.
자세한 비교는 http://hongsgo.egloos.com/2033998 를 참고하라.

- String.split() 대신 StringTokenizer.nextToken()을 사용하라.
StringTokenizer.nextToken()는 사용이 불편하지만 빠르며, String.split()는 사용하기 편하지만 느리다.
token이 빈 문자열일 경우, String.split() 은 ""를 해당 배열 원소에 저장해 주지만, StringTokenizer.nextToken() 는 null을 리턴한다.
단 정규식을 구분자로 사용할 경우는 어쩔 수 없이  String.split() 을 사용해야 한다.
성능비교는  http://ir.bagesoft.com/622 를 참고하라.
 
- Buffered~계열 클래스 (BufferedReader, BufferedWriter 등) 를 사용하라.
이건 너무 쉬운 내용이라. 자세한 것은 검색을 통해 찾아 봐라.

'DEVELOPMENT > Java' 카테고리의 다른 글

java openGL  (0) 2012.08.23
자바 정규표현식  (0) 2012.05.17
Apache Daemon 사용하기  (0) 2012.05.17
Quartz 문서  (0) 2011.07.13
[JAVA] 동적 캐스팅  (0) 2011.06.10

1. 데몬(daemon) 이란?
 주기적인 서비스 요청을 처리하기 위해서 커널상에 백그라운드 모드로 실행되는 프로세스로, 메모리 관리 방법에 따라 단독 데몬과 xinetd로 분리된다.

단독데몬
 항상 백그라운드 모드로 실행되고 메모리를 상대적으로 많이 소비한다. 그러나 서비스(응답속도)가 빠르다. httpd와 같은 웹서비스 데몬이 대표적.
xinetd(슈퍼데몬)
 요청이 있을때마다 xinetd가 서비스를 싱행시켜주므로 메모리 소비가 적다. 그러나 단독데몬에 비해 상대적으로 서비스 속도가 느리다.


 2. 간단한 자바 데몬 만들기
 nohup을 이용해서 java를 실행시킨다.

 터미널이 종료될 때(쉘이 종료될 때) 프로세스가 죽는 이유는 해당 프로세스가 쉘의 자식 프로세스 이기 때문이다. 따라서, 부모 프로세스가 죽을대 던지는 SIGHUP을 자식 프로세스가 받게 된다.

 nohup은 부모 프로세스가 죽을때 자식 프로세스에게 SIGHUP을 던지지 않는 프로세스를 말한다.
$ nohup java 클래스명 &

  
 사용하기 편한 장점은 있으나, 문제는 중지를 시킬수 없다. 즉, 해당 프로세스 ID를 찾아내 kill하는 수 밖에 없다. 물론 파일 체크 기법, 소켓을 이용한 제어 방법등을 사용할 수 있지만 스스로 구현해야 하는 번거로움이 있다.


 3. apache commons daemon 이용하기
 Java는 UNIX의 시그널 처리를 할수 없기때문에, 중지 신호(TERM signal)를 처리하기 위해서는 따로 구현을 해야한다. 이런 번거로움을 해결하기 위해 자카르타의 하위 프로젝트중의 commons daemon을 이용한다. commons daemon은 중지 신호를 받으면 미리 지정된 메소드를 실행한다.

 ** 다운로드: http://commons.apache.org/daemon/

 UNIX용 Jsvc와 윈도우용 Procrun 있다.
 여기서는 Jsvc를 이용해보도록 하겠다.

 

 commons daemon을 다운로드해 압축을 해제하면 위 그림과 같다.
 commons-daemon.jar 파일은 Java프로젝트 lib폴더에 복사해둔다.

 


 bin폴더의 압축파일을 해제하면 jsvc-src라는 폴더가 나온다.
 폴더의 내용은 위와 같다.
 commons daemon을 사용하기 위해서는 바로 여기서 jsvc를 빌드해줘야 한다.
 빌드환경은 다음과 같다.(리눅스에서 빌드해야한다.)

GNU AutoConf(at least 2.53)
ANSI-C compliant compiler(GCC is good)
GNU Make
A Java Platform 2 compliant SDK

 여기서부터는 ubuntu 8.10 환경에서 진행하도록 한다.

 먼저 JDK가 설치되어 있지 않다면 JDK를 설치한다.
 $ sudo apt-get install sun-java6-jdk


 JDK가 설치되는 경로는 /usr/lib/jvm/java-6-sun 이다.

 gcc 및 make 가 설치되있지 않다면 아래 명령를 이용해 한방에 설치한다.
 $ sudo apt-get install build-essential


 AutoConf가 설치되있지 않다면 AutoConf를 설치한다.
 $ sudo apt-get install autoconf


 Jsvc를 빌드하는 방법은 다음과 같다.

support/buildconf.sh
./configure --with-java=/usr/lib/jvm/java-6-sun
make


참고 방법

mkdir /root/commons-daemon

cd /root/commons-daemon

wget http://www.apache.org/dist/commons/daemon/binaries/1.0.5/commons-daemon-1.0.5.jar
wget http://mirror.apache-kr.org//commons/daemon/source/commons-daemon-1.0.5-src.tar.gz
tar zxvf commons-daemon-1.0.5-src.tar.gz
cd commons-daemon-1.0.5-src/src/native/unix/
support/buildconf.sh
./configure --with-java=/opt/jdk1.6.0_24/
make
mv jsvc /root/commons-daemon

 

 빌드가 성공적으로 이루어졌다면 위 그림과 같이 jsvc가 만들어진것을 확인할 수 있다. 이후 이 파일을 가지고 Java 데몬을 실행한다.

 Java 데몬을 만들려면 org.apache.commons.daemon.Daemon 인터페이스의 init, start, stop, destory 메소드를 구현해야 한다.


샘플

package com.bagesoft.test.daemon;
 
import org.apache.commons.daemon.Daemon;
import org.apache.commons.daemon.DaemonContext;
import org.apache.commons.daemon.DaemonInitException;
 
public class TestDaemon implements Daemon, Runnable {
    private String status = "";
    private int no = 0;
    private Thread thread = null;
 
    @Override
    public void init(DaemonContext context) throws DaemonInitException,
            Exception {
        System.out.println("init...");
        String[] args = context.getArguments();
        if (args != null) {
            for (String arg : args) {
                System.out.println(arg);
            }
        }
        status = "INITED";
        this.thread = new Thread(this);
        System.out.println("init OK.");
        System.out.println();
    }
 
    @Override
    public void start() {
        System.out.println("status: " + status);
        System.out.println("start...");
        status = "STARTED";
        this.thread.start();
        System.out.println("start OK.");
        System.out.println();
    }
 
    @Override
    public void stop() throws Exception {
        System.out.println("status: " + status);
        System.out.println("stop...");
        status = "STOPED";
        this.thread.join(10);
        System.out.println("stop OK.");
        System.out.println();
    }
 
    @Override
    public void destroy() {
        System.out.println("status: " + status);
        System.out.println("destroy...");
        status = "DESTROIED";
        System.out.println("destroy OK.");
        System.out.println();
    }
 
    @Override
    public void run() {
        while (true) {
            System.out.println(no);
            try {
                Thread.sleep(1000);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
            if (no > 1000) {
                break;
            }
            no++;
        }
    }
}


init에서 초기화, start에서 처리할 작업을 별도의 쓰레드로 생성해서 실행한다. start 메소드 호출후 반드시 return 되어야 데몬이 시그널 처리를 제대로 할 수 있다.
 stop, destroy 는 중지 신호가 오면 차례되로 호출된다.


 이제 실행/중지 스크립트를 작성한다.
 Jsvc를 싱행하는데 필요한것은 실행하는 계정(user), JAVA_HOME(-home), 프로세스ID 파일(-pidfile), 출력지정(-outfile, -errfile), 클래스파일(-cp) 등이 있다.


JAVA_HOME=/opt/jdk1.6.0_24
JSVC=/root/commons-daemon/jsvc
USER=root
 
DAEMON_HOME=/root/commons-daemon
PID_FILE=$DAEMON_HOME/daemon.pid
OUT_FILE=$DAEMON_HOME/daemon.out
#ERR_FILE=$DAEMON_HOME/daemon.err
 
CLASSPATH=\
$DAEMON_HOME/commons-daemon-1.0.5.jar:\
$DAEMON_HOME/BageSoft.jar
 
MAIN_CLASS=com.bagesoft.test.daemon.TestDaemon
case "$1" in
  start)
    #
    # Start Daemon
    #
    rm -f $OUT_FILE
    $JSVC \
    -user $USER \
    -java-home $JAVA_HOME \
    -pidfile $PID_FILE \
    -outfile $OUT_FILE \
    -errfile $OUT_FILE \
    -cp $CLASSPATH \
    $MAIN_CLASS
    #
    # To get a verbose JVM
    #-verbose \
    # To get a debug of jsvc.
    #-debug \
    exit $?
    ;;
 
  stop)
    #
    # Stop Daemon
    #
    $JSVC \
    -stop \
    -nodetach \
    -java-home $JAVA_HOME \
    -pidfile $PID_FILE \
    -outfile $OUT_FILE \
    -errfile $OUT_FILE \
    -cp $CLASSPATH \
    $MAIN_CLASS
    exit $?
    ;;
 
  *)
    echo "[Usage] TestDaemon.sh start | stop"
    exit 1;;

esac 

 

이제 Java 데몬을 실행하기 위한 모든 준비를 마쳤다.

위에서 작성한 스크립트 파일을 이용해 Java 데몬을 실핸한다.
 정상적으로 데몬이 시작된다면 PID_FILE에 지정한 파일이 생성된것을 확인할 수 있다.

 

 

데몬을 중지하려면 start 대신 stop을 입력으로 스크립트를 실행하면 된다.


[출처] http://ultteky.egloos.com/10877963

'DEVELOPMENT > Java' 카테고리의 다른 글

자바 정규표현식  (0) 2012.05.17
대용량 데이터 처리를 위한 JAVA Tunning(튜닝)  (0) 2012.05.17
Quartz 문서  (0) 2011.07.13
[JAVA] 동적 캐스팅  (0) 2011.06.10
log4jdbc를 활용하여 쿼리 로그 남기기  (0) 2011.06.01