* ȸ¿ø°¡ÀÔ * ¾ÆÀ̵ð/ºñ¹Ð¹øÈ£ ã±â   ID PW
Last Modified : 2007.05.25

°èÃþÇü °Ô½ÃÆÇ

1. °èÃþÇü °Ô½ÃÆÇ ¼Ò°³

°èÃþÇü °Ô½ÃÆÇÀ̶õ ¿ø±ÛÀÌ ÀÖ°í ±×¿¡ ´ëÇÑ ´äº¯±ÛÀÌ °èÃþÀ¸·Î º¸ÀÌ´Â ´ÙÀ½°ú °°Àº °Ô½ÃÆÇÀ» ¸»ÇÕ´Ï´Ù.

¹øÈ£ Á¦¸ñ ÀÛ¼ºÀÚ ÀÛ¼ºÀÏ
29 Áú¹®4 ±èÅÂÈñ 2007/12/09
27 Áú¹®3 ±èÅÂÈñ 2007/11/27
32   ¤¤ Áú¹®3ÀÇ ´äº¯ ¼ÛÀ±¾Æ 2007/12/22
26 Áú¹®2 ÀÌ¿µ¾Ö 2007/11/25
30   ¤¤ Áú¹®2ÀÇ ´äº¯(µÎ¹øÂ°) ¼ÛÀ±¾Æ 2007/12/20
31     ¤¤ ´äº¯¿¡ ´ëÇÑ Áú¹® ÀÌ¿µ¾Ö 2007/12/21
33       ¤¤ ´äº¯ ¼ÛÀ±¾Æ 2007/12/23
28   ¤¤ Áú¹®2ÀÇ ´äº¯(ù¹øÂ°) ¼ÛÀ±¾Æ 2007/12/01
25 Áú¹®1 ÀüÁöÇö 2007/11/20

(¿©±â¼­ ¹øÈ£´Â °Ô½Ã±ÛÀÇ °íÀ¯¹øÈ£(num)¸¦ ÀǹÌÇÕ´Ï´Ù.)
°èÃþÇü °Ô½ÃÆÇÀÇ ¸ñ·Ïº¸±â´Â ¿ø±Û°ú ´äº¯±ÛÀ» ±×·ìÀ¸·Î ¹­°í, ±×·ì³»¿¡¼­ Á¤·ÄÇÏ¿© º¸¿©ÁÖ¾î¾ß ÇÕ´Ï´Ù.
(¿©±â¼­ ¿ø±ÛÀ̶õ »õ±Û¾²±â¸¦ ÅëÇØ¼­ ÀÛ¼ºµÈ ±ÛÀ» ÀǹÌÇϸç, ´äº¯±ÛÀº ´äº¯¾²±â¸¦ ÅëÇØ¼­ ÀÛ¼ºµÈ ±ÛÀ» ÀǹÌÇÕ´Ï´Ù.)
±×·ì³»¿¡ Á¤·ÄÀ» À§ÇÑ Á¤º¸´Â ´äº¯±ÛÀÌ ¿ø±Û¿¡ ´ëÇØ¼­ ¾ó¸¶³ª ¾Æ·¡¿¡ Àִ°¡¿Í ¾ó¸¶³ª µé¿©¾²±â°¡ ÀÌ·ç¾îÁ®¾ß Çϴ°¡ ÀÔ´Ï´Ù.
¿ø±Û°ú ´äº¯±ÛÀÇ ±×·ìÇÎÀ» À§Çؼ­ family ¶ó´Â Çʵ带 Ãß°¡ÇÕ´Ï´Ù.
¿ø±Û¿¡ ´ëÇØ¼­ ¾ó¸¶³ª ¾Æ·¡¿¡ Àִ°¡¿¡ ÀúÀåÇϱâ À§Çؼ­ depth ¶ó°í Çʵ带 Ãß°¡ÇÕ´Ï´Ù.
µé¿©¾²±â¸¦ ÀúÀåÇϱâ À§Çؼ­ indent ¶ó´Â Çʵ带 Ãß°¡ÇÕ´Ï´Ù.

°èÃþÇü °Ô½ÃÆÇÀ» À§ÇØ Ãß°¡ÇÒ Çʵå

Ä÷³¸í µ¥ÀÌÅÍ Å¸ÀÔ ¼³¸í
family number ±×·ì¹øÈ£
depth number ±Û ±íÀÌ ¼öÁØ
indent number µé¿©¾²±â ¼öÁØ

À̰ÍÀ¸·Î ÃæºÐÇÑ °Íó·³ º¸ÀÔ´Ï´Ù.
´äº¯ÀÌ ÀÖ´Â ±ÛÀ» »èÁ¦ÇÒ ¶§¸¦ Çѹø »ý°¢ÇØ º¸°Ú½À´Ï´Ù.
À§ °èÃþÇü °Ô½ÃÆÇ ¿¹¿¡¼­ 30¹ø ±ÛÀ» »èÁ¦ÇÒ·Á°í ÇÒ¶§ 31¹ø ±ÛÀº ¾î¶»°Ô Çϸé ÁÁÀ»±î¿ä?
¸¸ÀÏ 30¹ø ±ÛÀÌ »èÁ¦µÇ¾ú´Âµ¥ 31¹ø ±ÛÀÌ »èÁ¦°¡ µÇÁö ¾Ê´Â´Ù¸é »ç¿ëÀÚ´Â °Ô½ÃÆÇÀÇ ¹ö±×¶ó°í »ý°¢ÇÒ °Ì´Ï´Ù.
31¹ø ±Ûµµ °°ÀÌ »èÁ¦°¡ µÇ¾î¾ß ÇÑ´Ù¸é family,depth,indent¸¸ °¡Áö°í¼­´Â ´äÀÌ ³ª¿ÀÁö ¾Ê½À´Ï´Ù. ´Ù¸¥ Çʵ尡 ÇÊ¿äÇÕ´Ï´Ù.
ÇѴܰè À§ ¼öÁØÀÇ ±ÛÀÌ ¹«¾ùÀÎÁö(ÇÑ ´Ü°è À§ ¼öÁØÀÇ ±ÛÀÇ ±Û¹øÈ£) °¡Áö°í ÀÖ´Â Çʵ尡 ÇÊ¿äÇÕ´Ï´Ù.
ÀÌ Çʵå¸íÀ» parent ¶ó°í Çϸé,
(´äº¯ÀÌ ÀÖ´Â ±ÛÀº »èÁ¦µÇÁö ¸øÇÏ°Ô ÇÏ´Â ·ÎÁ÷¿¡ À־µµ À§ »ý°¢Àº À¯È¿ÇÕ´Ï´Ù.)

¹øÈ£
(num)
ºÎ¸ð±Û
(parent)
Á¦¸ñ ÀÛ¼ºÀÚ ÀÛ¼ºÀÏ
29 29 Áú¹®4±èÅÂÈñ 2007/12/09
27 27 Áú¹®3±èÅÂÈñ 2007/11/27
32 27   ¤¤ Áú¹®3ÀÇ ´äº¯ ¼ÛÀ±¾Æ 2007/12/22
26 26 Áú¹®2ÀÌ¿µ¾Ö 2007/11/25
30 26   ¤¤ Áú¹®2ÀÇ ´äº¯(µÎ¹øÂ°)¼ÛÀ±¾Æ 2007/12/20
31 30     ¤¤ ´äº¯¿¡ ´ëÇÑ Áú¹®ÀÌ¿µ¾Ö 2007/12/21
33 31       ¤¤ ´äº¯¼ÛÀ±¾Æ 2007/12/23
28 30   ¤¤ Áú¹®2ÀÇ ´äº¯(ù¹øÂ°)¼ÛÀ±¾Æ 2007/12/01
25 25 Áú¹®1ÀüÁöÇö 2007/11/20

À§¿Í °°ÀÌ ÇÑ ¼öÁØ À§ÀÇ ±Û¿¡ ´ëÇÑ ±Û¹øÈ£¸¦ parent Çʵ尡 °¡Áö°í ÀÖ´Ù¸é
30¹ø ±ÛÀ» »èÁ¦ÇÒ ¶§ 30 ±Û¹øÈ£¸¦ parent Çʵå·Î °¡Áö°í ÀÖ´Â 31¹ø ±ÛÀ» »èÁ¦Çϰí , À̶§ 31¹ø ±ÛÀ» ±Û¹øÈ£¸¦ °¡Áö°í ÀÖ´Â 33¹ø ±ÛÀ» »èÁ¦ÇÏ´Â ½ÄÀ¸·Î »èÁ¦¸¦ ÇÏ¸é ´äº¯±ÛÀÌ ÀÖ´Â ±Û¿¡ ´ëÇÑ »èÁ¦°¡ °¡´ÉÇÏ°Ô µË´Ï´Ù.
¸¸ÀÏ °Ô½ÃÆÇÀÇ Á¤Ã¥ÀÌ ´äº¯±ÛÀÌ ÀÖ´Â °Ô½Ã±Û¿¡ ´ëÇØ¼­´Â »èÁ¦¸¦ ÇÏÁö ¸øÇÏ´Â °ÍÀÌ¶óµµ ¸¶Âù°¡ÁöÀÔ´Ï´Ù.
»èÁ¦ÇϰíÀÚ ÇÏ´Â °Ô½Ã±ÛÀÇ ´ëÇÑ ´äº¯ÀÌ ÀÖ°í ¾øÀ½ÀÇ ¿©ºÎ¸¦ ¾Ë±â À§Çؼ­´Â parent Çʵ尡 ÇÊ¿äÇÕ´Ï´Ù.
°á·ÐÀûÀ¸·Î ¿ì¸®°¡ ¸¸µé °èÃþÇü °Ô½ÃÆÇÀ» À§Çؼ­ Ãß°¡µÇ¾î¾ß ÇÏ´Â Çʵå´Â ¾Æ·¡¿Í °°½À´Ï´Ù.

°èÃþÇü °Ô½ÃÆÇÀ» À§ÇØ Ãß°¡ÇÒ Çʵå

Ä÷³¸í µ¥ÀÌÅÍ Å¸ÀÔ ¼³¸í
family number ±×·ì¹øÈ£
parent number ÇÑ ¼öÁØ À§ÀÇ ±ÛÀÇ ±Û¹øÈ£
depth number ±Û ±íÀÌ ¼öÁØ
indent number µé¿©¾²±â ¼öÁØ

2. °èÃþÇü °Ô½ÃÆÇ ÇÙ½É ¾Ë°í¸®Áò

1. »õ±Û¾²±â

¿ø±ÛÀ» ÀÔ·ÂÇÒ¶§´Â ÇØ´ç Çʵ忡 ¾Æ·¡¿Í °°ÀÌ insert µÇ°Ô ÇÕ´Ï´Ù.

Field Value
family °áÁ¤µÇ´Â °íÀ¯¹øÈ£(num)¿Í °°°Ô
parent 0
depth 0
indent 0

2. ´äº¯±Û ¾²±â

¸ÕÀú ºÎ¸ð±ÛÀÌ ¼ÓÇÑ family °ªÀ» °¡Áö°í ºÎ¸ð±ÛÀÇ depth º¸´Ù Å« °ªÀ» °¡Áø °Ô½Ã±ÛÀÇ depth ¸¦ 1¾¿ Áõ°¡½ÃŲ ÈÄ ´äº¯±ÛÀÇ ÇØ´ç Çʵ忡 ¾Æ·¡¿Í °°Àº °ªÀ¸·Î Insert ÇÕ´Ï´Ù.

Field Value
family ¿ø±ÛÀÇ family ¿Í °°°Ô
parent ºÎ¸ð±ÛÀÇ ±Û¹øÈ£
depth (ºÎ¸ð±ÛÀÇ depth ) + 1
indent (ºÎ¸ð±ÛÀÇ indent ) + 1

3. Áö±Ý±îÁö ±¸ÇöÇÑ °Ô½ÃÆÇÀ» °èÃþÇü °Ô½ÃÆÇÀ¸·Î ¼öÁ¤

¸ÕÀú board Å×ÀÌºí ±¸Á¶¸¦ ¼öÁ¤ÇÕ´Ï´Ù.
¸ðµç °Ô½Ã¹°À» Áö¿ì°í ¾Æ·¡ÀÇ ¸í·ÉÀ¸·Î board Å×ÀÌºí ±¸Á¶¸¦ º¯°æÇÕ´Ï´Ù.

alter table board add(family number);
alter table board add(parent number);
alter table board add(depth number);
alter table board add(indent number);

µðÀÚÀÎ ÅëÇÕÀ» À§Çؼ­ ÇöÀç ¾²°í ÀÖ´Â »õ±Û ¾²±â ¸ðµâ(write_form.jsp, BoardWriter.java)¿¡ ´äº¯ ¾²±â ±â´ÉÀ» Ãß°¡Çϵµ·Ï ÇϰڽÀ´Ï´Ù.
ÀÌÁ¦ write_form.jsp , BoardWriter.java ¿¡ »õ±Û ¾²±â »Ó¸¸ ¾Æ´Ï¶ó ´äº¯ ¾²±â ±â´ÉÀ» ±¸ÇöÇÕ´Ï´Ù.
±×¸®°í »èÁ¦¸ðµâ (delete_confirm.jsp , BoardDeleter.java)¿¡ ´äº¯±ÛÀ» »èÁ¦Çϱâ À§ÇÑ ±â´ÉÀ» Ãß°¡ÇÕ´Ï´Ù.
¼öÁ¤ ¼ø¼­´Â list.jsp -> view.jsp -> write_form.jsp -> BoardWriter.java -> BoardDeleter.java ¼øÀ¸·Î ÁøÇàÇÕ´Ï´Ù.

list.jsp ¼öÁ¤

1. °Ô½Ã¹°À» fetch ÇØ ¿À´Â ÄÚµå ºÎºÐ¿¡¼­ ±×·ìÇΰú ±×·ì³» Á¤·ÄÀÌ µÇµµ·Ï Äõ¸®¹®À» ¼öÁ¤ÇÕ´Ï´Ù.
°á°ú¼ÂÀ» °èÃþÇü °Ô½ÃÆÇ¿¡ ¸Â°Ô ±¸Çϱâ À§Çؼ­´Â Äõ¸®¹® ¸¶Áö¸·¿¡ ORDER BY family DESC, depth ASC ·Î ¹Ù²ß´Ï´Ù.
ÀÌ·¯¸é °á°ú¼ÂÀº ¿ì¼± family ·Î ³»¸²Â÷¼øÀ¸·Î Á¤·ÄÀÌ µÇ°í ´ÙÀ½¿¡ ±×·ì³»¿¡¼­´Â depth ·Î ¿À¸§Â÷¼øÀ¸·Î Á¤·ÄÀÌ µË´Ï´Ù.

.... ORDER BY family DESC, depth ASC
...
 
if ( keyfield.equals("") || key.equals("") ) {
  query =  "SELECT num,family,parent,depth,indent,subject,wdate" +
    " FROM ( SELECT ROWNUM R, A.* FROM " +
    " ( SELECT num,family,parent,depth,indent,subject,wdate " + 
    " FROM board ORDER BY family DESC, depth ASC ) A) " +
    " WHERE R BETWEEN " + start + " AND " + end;
} else { 
  query  = "SELECT num,family,parent,depth,indent,subject,wdate" +
    " FROM ( SELECT ROWNUM R, A.* FROM " + 
    "( SELECT num,family,parent,depth,indent,subject,wdate " +
    " FROM board WHERE " + keyfield + " LIKE '%" + key + "%' " +
    " ORDER BY family DESC, depth ASC ) A) " +
    " WHERE R BETWEEN " + start + " AND " + end; 
}

... 

2. indent Çʵ尪À» ÀÌ¿ëÇØ¼­ µé¿©¾²±â¸¦ ±¸ÇöÇÕ´Ï´Ù.

...

while ( rs.next() ) {
  int num = rs.getInt( "num" );
  String subject = rs.getString( "subject" );
  Date wdate = rs.getDate( "wdate" ); 
  int indent = rs.getInt( "indent" ); 
  for ( int i=0;i < indent;i++ ) { 
    out.println("&nbsp;&nbsp;");
  } 
  if ( indent != 0 ) {
    out.println( "¤¤" );
  }

...

À§ Äڵ带 º¸¸é indent ¸¸Å­ &nbsp;&nbsp; ¸¦ Ãß°¡ÇÏ¿© µé¿©¾²±â¸¦ ÇÑ ´ÙÀ½ ¿ø±ÛÀÌ ¾Æ´Ï¸é (Áï, indent!=0 À̸é) "¤¤" ¸¦ »ðÀÔÇϰí ÀÖ½À´Ï´Ù.
list.jsp ¿¡¼­ °èÃþÇü °Ô½ÃÆÇÀ¸·ÎÀÇ ¼öÁ¤ÀÌ ³¡³µ½À´Ï´Ù.

list.jsp

<%@ page contentType="text/html;charset=euc-kr" %>
<%@ page import="java.sql.*,javax.sql.*,javax.naming.*,net.java_school.util.Log" %>
<html>
<head>
<script language="javascript">

  function goView(num) {
    var form = document.frmView;
    form.num.value = num;
    form.submit();
  }

  function goList( cpage ) {
    var form = document.frmList;
    form.cur_page.value = cpage;
    form.submit();
  }

  function goWrite() {
    var form = document.frmWrite;
    form.submit();
  }

</script>
</head>
<body>
<%
  Log log = new Log();

  request.setCharacterEncoding("euc-kr");

  // ÆÄ¶ó¹ÌÅ͸¦ ¹Þ´Â´Ù.
  int cur_page = (request.getParameter("cur_page") == null) ? 1 : 
  Integer.parseInt(request.getParameter("cur_page"));
  String keyfield = request.getParameter("keyfield");
  if ( keyfield == null ) keyfield="";
  String key = request.getParameter("key");
  if ( key == null ) key = "";

  DataSource ds = null;
  Context ic = null;
  Connection conn = null;
  PreparedStatement prepare = null;
  ResultSet rs = null;
  String query = null;
	
  try {
    ic = new InitialContext();
    ds = (DataSource)ic.lookup("java:comp/env/jdbc/orcl");
  } catch ( NamingException ne ) {
    log.debug( ne.getMessage() );
  }

  int total_record = 0; //ÃÑ µ¥ÀÌÅÍ °³¼ö¸¦ ÀúÀåÇÒ º¯¼ö

  try {
    conn = ds.getConnection();

    if ( keyfield.equals("") || key.equals("") ) {
      query = "select count(*) from board";
    } else {
      query = "select count(*) from board where " + keyfield + " like '%" + key + "%'";
    }

    prepare = conn.prepareStatement( query );
    rs = prepare.executeQuery();
    rs.next();
    total_record = rs.getInt(1);
  } catch ( SQLException e ) {
  } finally {
    try {
      if ( rs != null ) rs.close();
      if ( prepare != null) prepare.close();
      conn.close();
      //log.close();·Î±×ÆÄÀÏÀÇ ÆÄÀÏ Ãâ·Â ½ºÆ®¸²À» ¹ÝȯÇÏÁö ¾Ê´Â´Ù. 
    } catch ( SQLException e ) {}
  }

  // Ãâ·Â¸®½ºÆ®  ½ÃÀÛ ·¹ÄÚµå °è»ê  
  int start = (cur_page - 1) * 10 + 1;
  // Ãâ·Â¸®½ºÆ®  ¸¶Áö¸· ·¹ÄÚµå °è»ê
  int end = start + 10 -1;

  // ÇØ´ç ÆäÀÌÁöÀÇ ·¹ÄÚµå ¼ÂÀ» ±¸ÇÑ ÈÄ Ãâ·ÂÇÕ´Ï´Ù.
  try {
    conn = ds.getConnection();
    if ( keyfield.equals("") || key.equals("") ) {
      query =  "SELECT num,family,parent,depth,indent,subject,wdate" +
      " FROM ( SELECT ROWNUM R, A.* FROM " +
      " ( SELECT num,family,parent,depth,indent,subject,wdate " + 
      " FROM board ORDER BY family DESC, depth ASC ) A) " +
      " WHERE R BETWEEN " + start + " AND " + end;
    } else { 
      query  = "SELECT num,family,parent,depth,indent,subject,wdate" +
      " FROM ( SELECT ROWNUM R, A.* FROM " + 
      "( SELECT num,family,parent,depth,indent,subject,wdate " +
      " FROM board WHERE " + keyfield + " LIKE '%" + key + "%' " +
      " ORDER BY family DESC, depth ASC ) A) " +
      " WHERE R BETWEEN " + start + " AND " + end; 
    }
    prepare = conn.prepareStatement( query );
    rs = prepare.executeQuery();

    while( rs.next() ) {
      
      int num = rs.getInt( "num" );
      String subject = rs.getString( "subject" );
      Date wdate = rs.getDate( "wdate" );
      int indent = rs.getInt( "indent" ); 

      for ( int i=0;i < indent;i++ ) { 
        out.println("  ");
      }
      if ( indent != 0 ) {
        out.println( "¤¤" );
      }
%>
  <a href="javascript:goView('<%=num%>')"><%=subject%></a><%=wdate.toString()%><br>
<%
    } // while statment end 
  } catch( SQLException e ) {
    log.debug( "Error Source:board1/list.jsp : SQLException" );
    log.debug( "SQLState : " + e.getSQLState() );
    log.debug( "Message : " + e.getMessage() );
    log.debug( "Oracle Error Code : " + e.getErrorCode() );
    log.debug( "Query : " + query );
  } finally {
    try {
      if ( rs != null ) rs.close();
      if ( prepare != null) prepare.close();
      conn.close();
      log.close(); // ´õÀÌ»ó »ç¿ëÀÚ Á¤ÀÇ ·Î±×¸¦ »ç¿ëÇÏÁö ¾Ê¾Æµµ µÇ±â ¶§¹®¿¡
    } catch ( SQLException e ){}
  }
%>
<br>
<%
  // Àüü ÆäÀÌÁö(total_page)¸¦ ±¸ÇÑ´Ù. 
  int total_page = 1;
  if ( total_record != 0 ) {
    if ( ( total_record % 10 ) == 0 ) {
      total_page = ( total_record / 10 );
    } else {
      total_page = ( total_record / 10 + 1);
    }
  }

  // ºí·Ï´ç ÆäÀÌÁö ¼ö¸¦ Á¤ÇÑ´Ù.
  int page_per_block = 7;


  // ÇöÀç ÆäÀÌÁö°¡ ¼ÓÇÑ ºí·Ï(block)À» °è»êÇÑ´Ù.
  int block = 1;
  if ( ( cur_page % page_per_block ) == 0 ) {
    block = cur_page / page_per_block;
  } else {
    block = cur_page / page_per_block + 1;
  }

  // ºí·Ï¿¡¼­ ¸µÅ©ÇÒ Ã¹¹øÂ° ÆäÀÌÁö¿Í ¸¶Áö¸· ÆäÀÌÁö¸¦ °è»êÇÑ´Ù. 
  int first_page = ( block - 1 ) * page_per_block + 1;
  int last_page = block * page_per_block;

  // ÃÑ ºí·Ï¼ö¸¦ °è»êÇÑ´Ù. 
  int total_block = 1; 
  if ( (total_page % page_per_block ) == 0 ) {
    total_block = total_page / page_per_block;
  } else {
    total_block = total_page / page_per_block + 1;
  }

  // ¾µµ¥¾ø´Â ÆäÀÌÁö ¸µÅ©¸¦ ¸¸µéÁö ¾Ê±â À§Çؼ­
  if ( block >= total_block ) {
    last_page = total_page;
  }
  // ÇöÀç block > 1 ¸é [ÀÌÀü]¸µÅ©¸¦ ¸¸µé°í first_page - 1 ÆäÀÌÁö¹øÈ£·Î ¸µÅ©
  int my_page = 0;
  if ( block > 1 ) {
    my_page = first_page -1;
%>
	<a href="javascript:goList( '<%=my_page%>' )">[ÀÌÀü]</a>
<%
  } // if statment end
	
  // ·çÇÁ¹®À» ÀÌ¿ëÇØ¼­ ù¹øÂ° ÆäÀÌÁöºÎÅÍ ¸¶Áö¸· ÆäÀÌÁö±îÁö ¸µÅ©¸¦ ¸¸µç´Ù. 
  for ( int i = first_page; i <= last_page; i++ ) {
%>
  <a href="javascript:goList( '<%=i%>' )">[<%=i%>]</a>
<%
  } // if statment end

  // block < total_block ¸é [´ÙÀ½]¸µÅ©¸¦ ¸¸µé°í  last_page + 1 ¸¦ ÆäÀÌÁö¹øÈ£·Î ¸µÅ© 
  if (block < total_block ) {
    my_page = last_page + 1;
%>
  <a href="javascript:goList( '<%=my_page%>' )">[´ÙÀ½]</a>
<%
  }
%>
  <br>

  <form name="frmSearch" action="list.jsp" method="post">
    <select name="keyfield">
      <option value="subject" selected>Á¦¸ñ</option>
      <option value="content">³»¿ë</option>
    </select>
    <input type="text" size="10" maxlength="30" name="key" />
    <input type="submit" value="search" />
  </form>

  <a href="javascript:goWrite()">»õ±Û ¾²±â</a>

  <form name="frmView" action="view.jsp" method="post">
    <input type="hidden" name="num" />
    <input type="hidden" name="cur_page" value="<%=cur_page%>" />
    <input type="hidden" name="keyfield" value="<%=keyfield%>" />
    <input type="hidden" name="key" value="<%=key%>" />
  </form>

  <form name="frmList" action="list.jsp" method="post">
    <input type="hidden" name="cur_page" />
    <input type="hidden" name="keyfield" value="<%=keyfield%>" />
    <input type="hidden" name="key" value="<%=key%>" />
  </form>

  <form name="frmWrite" action="write_form.jsp" method="post">
    <input type="hidden" name="cur_page" value="<%=cur_page%>" />
    <input type="hidden" name="keyfield" value="<%=keyfield%>" />
    <input type="hidden" name="key" value="<%=key%>" />
  </form>

</body>
</html>

view.jsp ¼öÁ¤

³»¿ëº¸±â ÆäÀÌÁö¿¡¼­ ´äº¯ ¾²±â ±â´ÉÀ» À§ÇØ ÀûÀýÇÑ À§Ä¡¿¡ ¾Æ·¡ Äڵ带 »ðÀÔÇÕ´Ï´Ù.

..

  function goReply() {
    var form = document.frmReply;
    form.submit();
  }

..

<form name="frmReply" action="write_form.jsp" method="post">
  <input type="hidden" name="num" value="<%=num%>" />
  <input type="hidden" name="cur_page" value="<%=cur_page%>" />
  <input type="hidden" name="keyfield" value="<%=keyfield%>" />
  <input type="hidden" name="key" value="<%=key%>" />
</form>

..

<input type="button" value="¸ñ·Ï" onClick="javascript:goList()" /> 
<input type="button" value="¼öÁ¤" onClick="javascript:goModify()" />
<input type="button" value="´äº¯" onClick="javascript:goReply()" />
<input type="button" value="»èÁ¦" onClick="javascript:goDelete()" />

..

view.jsp

<%@ page contentType="text/html;charset=euc-kr" %>
<%@ page import="java.sql.*,javax.sql.*,javax.naming.*,net.java_school.util.Log" %>
<html>
<head>
<script language="javascript">
	
  function goList() {
    var form = document.frmList;
    form.submit();
  }

  function goModify() {
    var form = document.frmModify;
    form.submit();
  }

  function goDelete() {
    var form = document.frmDelete;
    form.submit();
  }

  function goReply() {
    var form = document.frmReply;
    form.submit();
  }

</script>
</head>
<body>
<%
  request.setCharacterEncoding( "euc-kr" );

  // ÆÄ¶ó¹ÌÅ͸¦ ¹Þ´Â´Ù.
  int num = Integer.parseInt( request.getParameter( "num" ) );
  String cur_page = request.getParameter( "cur_page" );
  String keyfield = request.getParameter( "keyfield" );
  String key = request.getParameter( "key" );

  Log log = new Log();

  DataSource ds = null;
  Context ic = null;
  Connection conn = null;
  PreparedStatement prepare = null;
  ResultSet rs = null;
  String query = null;

  // Ä¿³Ø¼ÇÀ» ¾ò´Â´Ù.
  try {
    ic = new InitialContext();
    ds = (DataSource)ic.lookup("java:comp/env/jdbc/orcl");
  } catch ( NamingException ne ) {
    log.debug( ne.getMessage() );
  }

  query = "select num,subject,content,wdate from board where num = " + num;

  try {
    conn = ds.getConnection();
    prepare = conn.prepareStatement( query );
    rs = prepare.executeQuery();

    while ( rs.next() ) {
    String subject = rs.getString( "subject" );
    String content = rs.getString( "content" );
    Date wdate = rs.getDate( "wdate" );
%>
  <%=subject%></a><br>
  <hr>
  <%=content%><br>
  <hr>
  <%=wdate.toString()%><br>
<%
    } // while statement end
  } catch ( SQLException e ) {
    log.debug( "Error Source:board1/view.jsp : SQLException" );
    log.debug( "SQLState : " + e.getSQLState() );
    log.debug( "Message : " + e.getMessage() );
    log.debug( "Oracle Error Code : " + e.getErrorCode() );
    log.debug( "Query : " + query );
  } finally {
    try {
      if ( rs != null ) rs.close();
      if ( prepare != null ) prepare.close();
      conn.close();
      log.close(); // ´õÀÌ»ó »ç¿ëÀÚ Á¤ÀÇ ·Î±× ÆÄÀÏÀ» ÀÌ¿ëÇÏÁö ¾ÊÀ¸¹Ç·Î
    } catch ( SQLException e ){}
  }
%>
  <form name="frmModify" method="post" action="modify_form.jsp">
    <input type="hidden" name="num" value="<%=num%>" />
    <input type="hidden" name="cur_page" value="<%=cur_page%>" />
    <input type="hidden" name="keyfield" value="<%=keyfield%>" />
    <input type="hidden" name="key" value="<%=key%>" />
  </form>

  <form name="frmDelete" method="post" action="delete_confirm.jsp">
    <input type="hidden" name="num" value="<%=num%>" />
    <input type="hidden" name="cur_page" value="<%=cur_page%>" />
    <input type="hidden" name="keyfield" value="<%=keyfield%>" />
    <input type="hidden" name="key" value="<%=key%>" />
  </form>

  <form name="frmList" method="post" action="list.jsp">
    <input type="hidden" name="cur_page" value="<%=cur_page%>" />
    <input type="hidden" name="keyfield" value="<%=keyfield%>" />
    <input type="hidden" name="key" value="<%=key%>" />
  </form>

  <form name="frmReply" action="write_form.jsp" method="post">
    <input type="hidden" name="num" value="<%=num%>" />
    <input type="hidden" name="cur_page" value="<%=cur_page%>" />
    <input type="hidden" name="keyfield" value="<%=keyfield%>" />
    <input type="hidden" name="key" value="<%=key%>" />
  </form>

  <br />

  <input type="button" value="¸ñ·Ï" onClick="javascript:goList()" /> 
  <input type="button" value="¼öÁ¤" onClick="javascript:goModify()" />
  <input type="button" value="´äº¯" onClick="javascript:goReply()" />
  <input type="button" value="»èÁ¦" onClick="javascript:goDelete()" />

</body>
</html>

write_form.jsp ¼öÁ¤

write_form.jsp ¿¡¼­´Â num °ªÀÌ ³Ñ¾î¿Ô´ÂÁö ¿©ºÎ·Î »õ±Û ¾²±â ÀÎÁö ´äº¯ ¾²±â ÀÎÁö¸¦ ÆÇ´ÜÇÕ´Ï´Ù.
¸¸¾à¿¡ num ÆÄ¶ó¹ÌÅÍ °ªÀÌ ÀǹÌÀÖ´Â °ªÀÌ ³Ñ¾î¿Â´Ù¸é ÀÌ´Â »ç¿ëÀÚ°¡ ´äº¯ ¹öưÀ» Ŭ¸¯ÇÏ¿© write_form.jsp ÆäÀÌÁö¸¦ ¹æ¹®ÇÑ °æ¿ìÀÔ´Ï´Ù.
»õ±Û ¾²±â¿Í ´Þ¸® ´äº¯ ¾²±â¿¡¼­´Â ºÎ¸ð±Û ³»¿ë¿¡ ´äº¯À» ´Þ·Á´Â »ç¿ëÀÚ¿¡°Ô º¸¿©ÁÝ´Ï´Ù.
ÆÄ¶ó¹ÌÅÍ num (°Ô½Ã¹°ÀÇ °íÀ¯¹øÈ£)À¸·Î ºÎ¸ð±Û¿¡ ´ëÇÑ µ¥ÀÌÅ͸¦ °¡Áö°í ¿À´Â Äڵ尡 Ãß°¡µË´Ï´Ù.
ºÎ¸ð±ÛÀ» º¸ÀÏ ¶§ Á¦¸ñÀº ±×´ë·Î º¸ÀÌ°í ³»¿ëÀÎ °æ¿ì´Â ºÎ¸ð±ÛÀÇ ³»¿ë°ú ´äº¯±ÛÀÌ ºÐº°µÉ ¼ö ÀÖµµ·Ï ºÎ¸ð±Û ¾Õ¿¡ < À» Ãß°¡Çϵµ·Ï ±¸ÇöÇϰڽÀ´Ï´Ù.
¸¶Áö¸·À¸·Î ´äº¯±ÛÀ» ó¸®ÇÒ ¼ö ÀÖµµ·Ï num, family, parent, depth, indent, subject, content ÆÄ¶ó¹ÌÅÍ °ªÀ» ó¸® ¼­ºí¸´ÀÎ BoardWriter ·Î ³Ñ±â´Â °ÍÀÌ ¸¶Áö¸·ÀÔ´Ï´Ù.
´ÙÀ½Àº write_form.jsp ÀÇ ¼öÁ¤º»ÀÔ´Ï´Ù.

write_form.jsp

<%@ page contentType="text/html;charset=euc-kr" %>
<%@ page import="java.sql.*,javax.sql.*,javax.naming.*,net.java_school.util.Log" %>
<%
  request.setCharacterEncoding("euc-kr");

  Log log = new Log();

  // º¯¼ö¸¦ ÃʱâÈ­ ÇÑ´Ù.
  int num = 0;
  int family = 0;
  int parent = 0;
  int indent = 0;
  int depth = 0;

  String subject = "";
  String content = "";
  Date wdate = null;

  // mode: »õ±Û¾²±âÀÎÁö ´äº¯¾²±âÀÎÁö ¿©ºÎ
  String mode = "new";

  // ÆÄ¶ó¹ÌÅ͸¦ ¹Þ´Â´Ù.
  String cur_page = request.getParameter( "cur_page" );
  String keyfield = request.getParameter( "keyfield" );
  String key = request.getParameter( "key" );

  // ÆÄ¶ó¹ÌÅÍ num ÀÌ À¯È¿ÇÑ °ªÀ» °¡Áø´Ù¸é ´äº¯¾²±â ±â´ÉÀ» ¼öÇàÇÑ´Ù.
  String num_str = request.getParameter( "num" );
  if ( num_str != null ) {
    mode = "reply";
    num = Integer.parseInt(num_str);
  }

  DataSource ds = null;
  Context ic = null;
  Connection conn = null;
  PreparedStatement prepare = null;
  ResultSet rs = null;
  String query = null;

  // num ÆÄ¶ó¹ÌÅͰ¡ À¯È¿ÇÑ °ªÀ» °¡Áø´Ù¸é ÇØ´ç °Ô½Ã¹°À» fetch ÇÑ´Ù.
  if ( num != 0 ) {
    // Äõ¸®¹®ÀåÀ» ¸¸µç´Ù.
    query = "SELECT num, family, depth, indent, subject, content, wdate " +
        " FROM board " +
        " WHERE num = " + num;

    // Ä¿³Ø¼ÇÀ» ¾ò´Â´Ù.
    try {
      ic = new InitialContext();
      ds = (DataSource)ic.lookup("java:comp/env/jdbc/orcl");
    } catch ( NamingException ne ) {
      log.debug( ne.getMessage() );
    }

    try {
      conn = ds.getConnection();
      prepare = conn.prepareStatement( query );
      rs = prepare.executeQuery();

      rs.next();
      num = rs.getInt( "num" );
      family = rs.getInt( "family" );
      depth = rs.getInt( "depth" );
      indent = rs.getInt( "indent" );
      subject = rs.getString( "subject" );
      content = rs.getString( "content" );

      // subject, content´Â subject ÅØ½ºÆ® Çʵå¿Í content ÅØ½ºÆ®AreaÀÇ 
      // value ¼Ó¼º°ªÀ¸·Î ÁØ´Ù.
      // À̶§ content´Â ¿ø±ÛÀÓÀ» ¾Æ·¡¿Í °°ÀÌ Ç¥½ÃÇØÁØ´Ù.
      if ( num != 0 ) {
        content = content.replaceAll("\n", "\n>");
        content = "\n\n\n\n>" + content;
      }
      wdate = rs.getDate( "wdate" );
    } catch ( SQLException e ) {
      log.debug( "Error Source:board1/write_form.jsp : SQLException" );
      log.debug( "SQLState : " + e.getSQLState() );
      log.debug( "Message : " + e.getMessage() );
      log.debug( "Oracle Error Code : " + e.getErrorCode() );
      log.debug( "Query : " + query );
    } finally {
        try {
          if ( rs != null ) rs.close();
          if ( prepare != null ) prepare.close();
          conn.close();
          log.close(); // ´õÀÌ»ó »ç¿ëÀÚ Á¤ÀÇ ·Î±× ÆÄÀÏÀ» ÀÌ¿ëÇÏÁö ¾ÊÀ¸¹Ç·Î
        } catch ( SQLException e ){}
    }  
  } // if statement end
%>
<html>
<head>
<script language="javascript">

  function goList() {
    var form = document.frmList;
    form.submit();
  }

</script>
</head>
<body>

<h1>
<%
  if ( mode.equals( "new" ) ) {
    out.println( "»õ±Û¾²±â" );
  } else {
    out.println( "´ä±Û¾²±â" );
  }
%>
  </h1>
  <hr>

  <form name="frmWrite" method="post" action="../servlet/BoardWriter1">
    <input type="hidden" name="mode" value="<%=mode%>" />
    <input type="hidden" name="num" value="<%=num%>" />
    <input type="hidden" name="family" value="<%=family%>" />
    <input type="hidden" name="indent" value="<%=indent%>" />
    <input type="hidden" name="depth" value="<%=depth%>" />

    Á¦¸ñ : <input type="text" name="subject" size="45" value="<%=subject%>" /><br />
    º»¹® : <textarea name="content" rows="10" cols="60"><%=content%></textarea><br />
    <input type="submit" value="Àü¼Û" />
    <input type="reset" value="Ãë¼Ò" /><br />
  </form>

  <input type="button" value="¸ñ·Ï" onClick="javascript:goList()">

  <form name="frmList" method="post" action="list.jsp">
    <input type="hidden" name="cur_page" value="<%=cur_page%>" />
    <input type="hidden" name="keyfield" value="<%=keyfield%>" />
    <input type="hidden" name="key" value="<%=key%>" />
  </form>

</body>
</html>

À§ÀÇ °­Á¶µÈ ºÎºÐÀº BoardWriter1 ¼­ºí¸´À¸·Î ÆÄ¶ó¹ÌÅÍ mode, num, family, depth, indent °ªÀ» ³Ñ°Ü¾ß ÇϹǷΠ¼öÁ¤µÈ ºÎºÐÀÔ´Ï´Ù.
¿©±â¼­ mode ´Â ¼­ºí¸´ BoardWriter1 ¿¡ Àü´ÞµÇ¾î¼­ »õ±Û¾²±âÀÎÁö ´äº¯¾²±âÀÎÁö ±¸º°Çϴµ¥ ÀÌ¿ëµË´Ï´Ù.

BoardWriter1.java

package net.java_school.board;

import java.io.*;
import javax.servlet.*;
import javax.servlet.http.*;
import java.sql.*;
import javax.sql.*;
import javax.naming.*;
import net.java_school.util.*;

public class BoardWriter1 extends HttpServlet {
  PreparedStatement prepare = null;
  DataSource ds = null;

  // »õ±Û¾²±â¿ë Äõ¸®
  String query1 = "INSERT INTO board " + 
    "( num, family, parent, depth, indent, subject, content, wdate ) " + 
    "VALUES ( seq_board_num.nextval, seq_board_num.nextval, ?, ?, ?, ?, ?, sysdate )";
  // ´äº¯¾²±â¿ë Äõ¸®
  String query2 = "INSERT INTO board " + 
    "( num, family, parent, depth, indent, subject, content, wdate ) " + 
    "VALUES ( seq_board_num.nextval, ?, ?, ?, ?, ?, ?, sysdate )";
  // depth °»½Å¿ë Äõ¸®
  String query3 = "UPDATE board SET depth = depth + 1 WHERE family = ? AND depth > ? ";

  public void init() throws ServletException {
    try {
      Context ic = new InitialContext();
      ds = (DataSource)ic.lookup("java:comp/env/jdbc/orcl");
    } catch ( NamingException ne ) {}
  }

  public void doPost( HttpServletRequest req, HttpServletResponse res ) 
    throws ServletException, IOException {
    
    req.setCharacterEncoding( "euc-kr" );

    Log log = new Log();

    // ÆÄ¶ó¹ÌÅ͸¦ ¹Þ´Â´Ù.
    String mode = req.getParameter( "mode" );
    String num_str = req.getParameter( "num" );
    String family_str = req.getParameter( "family" );
    String depth_str = req.getParameter( "depth" );
    String indent_str = req.getParameter( "indent" );
    String subject = req.getParameter( "subject" );
    String content = req.getParameter( "content" );

    // º¯¼ö ÃʱâÈ­
    int family = 0;
    int parent = 0;
    int depth = 0;
    int indent = 0;

    if ( mode.equals( "reply" ) ) {
      family = Integer.parseInt(family_str);
      parent = Integer.parseInt(num_str);
      depth = Integer.parseInt(depth_str);
      indent = Integer.parseInt(indent_str) + 1;
    }
    
    Connection con	= null;
    
    try {
      con = ds.getConnection();

      if ( mode.equals( "reply" ) ) {
        prepare = con.prepareStatement(query3);
        prepare.setInt(1,family);
        prepare.setInt(2,depth++);
        prepare.executeUpdate();
      }	

      if ( mode.equals( "reply" ) ) {
        prepare = con.prepareStatement( query2 );
        prepare.setInt( 1, family );
        prepare.setInt( 2, parent );
        prepare.setInt( 3, depth  );
        prepare.setInt( 4, indent );
        prepare.setString( 5, subject );
        prepare.setString( 6, content );
      } else {
        prepare = con.prepareStatement( query1 );
        prepare.setInt( 1, parent );
        prepare.setInt( 2, depth  );
        prepare.setInt( 3, indent );
        prepare.setString( 4, subject );
        prepare.setString( 5, content );
      }
      prepare.executeUpdate();
    } catch ( SQLException e ) {
      log.debug( "Error Source:BoardWriter1.java : SQLException" );
      log.debug( "SQLState : " + e.getSQLState() );
      log.debug( "Message : " + e.getMessage() );
      log.debug( "Oracle Error Code : " + e.getErrorCode() );
      log.debug( "Query : " + query1 );
    } finally {
      try {
        if (prepare != null ) prepare.close();
		    con.close();
        log.close();
      } catch ( SQLException e ){}
      String path = req.getContextPath();
      res.sendRedirect( path + "/board1/list.jsp" );
    }
  }
}

4. »èÁ¦

´ÙÀ½À¸·Î »èÁ¦¸¦ ±¸ÇöÇϰڽÀ´Ï´Ù.
ÀϹÝÀûÀ¸·Î ´äº¯ÀÌ ÀÖ´Â ±ÛÀº »èÁ¦°¡ µÇÁö ¾Êµµ·Ï ±¸ÇöÇϰí À̾ »èÁ¦½Ã ´äº¯±Û±îÁö ¸ðµÎ »èÁ¦ÇÏ´Â ±¸Çö¿¡ ´ëÇØ »ìÆìº¾´Ï´Ù.

1. »èÁ¦ ¾Ë°í¸®Áò ( ´äº¯ÀÌ ÀÖÀ¸¸é »èÁ¦¾ÈµÊ )

  • ÆÄ¶ó¹ÌÅÍ·Î ³Ñ¾î¿Â ±ÛÀÇ °íÀ¯¹øÈ£(num) °ªÀ» parent °ªÀ» °¡Áö´Â ±ÛÀÌ ÀÖ´ÂÁö °Ë»çÇÑ´Ù.
  • ¸¸ÀÏ »èÁ¦ÇÏ·Á´Â ±ÛÀÇ °íÀ¯¹øÈ£¸¦ parent °ªÀ¸·Î °¡Áö´Â ±ÛÀÌ ÀÖ´Ù¸é °æ°íâÀ» ¿­°í ÀÌÀü È­¸éÀ¸·Î µ¹¾Æ°£´Ù.
  • »èÁ¦ÇÏ·Á´Â ±ÛÀÇ °íÀ¯¹øÈ£¸¦ parent °ªÀ¸·Î °¡Áö´Â ±ÛÀÌ ¾ø´Ù¸é »èÁ¦ÇÑ ÈÄ ¸ñ·ÏÈ­¸éÀ¸·Î À̵¿ÇÑ´Ù.

BoardDeleter1.java

package net.java_school.board;

import java.io.*;
import javax.servlet.*;
import javax.servlet.http.*;
import java.sql.*;
import javax.sql.*;
import javax.naming.*;
import net.java_school.util.Log;

public class BoardDeleter1 extends HttpServlet {

  DataSource ds = null;

  PreparedStatement prepare = null;
  String query1 = "DELETE board WHERE num = ?";
  String query2 = "SELECT count(*) FROM board WHERE parent = ?";

  public void init() throws ServletException {
    try {
      Context ic = new InitialContext();
      ds = (DataSource)ic.lookup("java:comp/env/jdbc/orcl");
    } catch ( NamingException ne ) {}
  }

  public void doPost( HttpServletRequest req, HttpServletResponse res ) 
  throws ServletException, IOException {

    req.setCharacterEncoding("euc-kr");
    res.setContentType("text/html;charset=euc-kr");

    PrintWriter out=res.getWriter();

    Log log = new Log();

    int num = Integer.parseInt( req.getParameter( "num" ) );
    String cur_page = req.getParameter( "cur_page" );
    String keyfield = req.getParameter( "keyfield" );
    String key = req.getParameter( "key" );

    Connection con = null;
    int isDel = 0; // »èÁ¦ ÇÒ °ÍÀΰ¡ ¿©ºÎ¸¦ ÀúÀåÇÏ´Â º¯¼ö 1ÀÌ¸é »èÁ¦, 0ÀÌ¸é »èÁ¦ÇÏÁö ¾ÊÀ½

    try {
      con = ds.getConnection();
      prepare = con.prepareStatement(query2);
      prepare.setInt(1,num);
      ResultSet rs = prepare.executeQuery();

      if ( rs.next() ) {
        int number = rs.getInt(1);
        if ( number == 0 ) {
          isDel = 1;
        }
      }
    } catch (SQLException e ) {
      log.debug( "Error Source:BoardDeleter.java : SQLException" );
      log.debug( "SQLState : " + e.getSQLState() );
      log.debug( "Message : " + e.getMessage() );
      log.debug( "Oracle Error Code : " + e.getErrorCode() );
      log.debug( "Query : " + query2 );
    } finally {
      try {
        if ( prepare != null ) prepare.close();
        //con.close();
        //log.close();
      } catch ( SQLException e ){}
    }

    if ( isDel == 1 ) {
      try {
        //con = ds.getConnection();
        prepare = con.prepareStatement( query1 );
        prepare.setInt( 1, num );
        prepare.executeUpdate();    // Äõ¸® ½ÇÇà
      } catch ( SQLException e ) {
        log.debug( "Error Source:BoardDeleter.java : SQLException" );
        log.debug( "SQLState : " + e.getSQLState() );
        log.debug( "Message : " + e.getMessage() );
        log.debug( "Oracle Error Code : " + e.getErrorCode() );
        log.debug( "Query : " + query1 );
      } finally {
        try {
          if ( prepare != null ) prepare.close();
          con.close();
          log.close();
        } catch ( SQLException e ){}
        String path = req.getContextPath();
        String formstr = "";
        formstr = "<form name=frmList method=post action="+path+"/board1/list.jsp>";
        formstr += "<input type=hidden name=cur_page value='"+cur_page+"' />";
        formstr += "<input type=hidden name=keyfield value='"+keyfield+"' />";
        formstr += "<input type=hidden name=key value='"+key+"' />";
        formstr += "</form>";
        out.println(formstr);
        String scriptstr = "";
        scriptstr += "<script language=javascript>";
        scriptstr += "function goList() {";
        scriptstr += " document.frmList.submit(); }";
        scriptstr += "</script>";
        scriptstr += "<script>goList();</script>";
        out.println(scriptstr);
      }
    } else {
      String scriptstr ="<script>alert('´äº¯ÀÌ ÀÖ´Â ±ÛÀº »èÁ¦ÇÒ ¼ö ¾ø½À´Ï´Ù');history.go(-1);</script>";
      out.println(scriptstr);
    }
  }
}

2. »èÁ¦ ¾Ë°í¸®Áò ¼Ò°³( ´äº¯ÀÌ ÀÖÀ¸¸é ´äº¯±îÁö ¸ðµÎ »èÁ¦ )

¾Æ·¡¿Í °°ÀÌ °Ô½Ã±ÛÀÌ ÀÖ´Ù°í °¡Á¤ÇÕ´Ï´Ù.
»èÁ¦ ¾Ë°í¸®Áò ¼Ò°³
¿ÞÂÊÀÇ ¹øÈ£´Â ±ÛÀÇ °íÀ¯¹øÈ£ num À» ³ªÅ¸³À´Ï´Ù.
85¹øÀÇ ±ÛÀÌ ¿ø±ÛÀÔ´Ï´Ù.
¿ø±ÛÀ̸é parent = 0 À̰í family ´Â num °ú °°°Ô µ¥ÀÌÅÍ º£À̽º¿¡ ÀÔ·ÂÀÌ µË´Ï´Ù.(Áï, family = 85)
86¹ø ±ÛÀº 85¹ø±Û¿¡ ´ëÇÑ ´äº¯±ÛÀÔ´Ï´Ù. ±×·¯¹Ç·Î parent = 85 À̰í family = 85 ·Î ÀúÀåµË´Ï´Ù.
87¹ø ±ÛÀº 86¹ø±Û¿¡ ´ëÇÑ ´äº¯±Û·Î parent = 86 À̰í family = 85 ÀÔ´Ï´Ù.
88¹ø ±ÛÀº 87¹ø±Û¿¡ ´ëÇÑ ´äº¯±Û·Î parent = 87 À̰í family = 85 ÀÔ´Ï´Ù.
´Ù½Ã ÇÑ ¹ø ÇʵåÀÇ Àǹ̸¦ »ý°¢Çϸé, num Àº ±ÛÀÇ °íÀ¯¹øÈ£À̰í, parent ´Â ¹Ù·Î À§ »óÀ§ÀÇ ºÎ¸ð±ÛÀ̸ç, family ´Â ±×·ìÇÎÀ» À§ÇÑ °ÍÀ¸·Î ¿ø±Û°ú ±×¿¡ °ü·ÃµÈ ´äº¯±ÛÀ» ±×·ìÀ¸·Î ¹­±â À§ÇÑ Çʵå¸íÀÔ´Ï´Ù.
À§ ³»¿ëÀ» ¾Æ·¡ ±×¸²Ã³·³ Ç¥ÇöµË´Ï´Ù.
»èÁ¦ ¾Ë°í¸®Áò ¼Ò°³

´äº¯±Û »èÁ¦ ¾Ë°í¸®Áò

  • »èÁ¦ÇÒ ±ÛÀÇ °íÀ¯¹øÈ£¸¦ »èÁ¦¸®½ºÆ®¿¡ Ãß°¡ÇÑ´Ù
  • »èÁ¦¸®½ºÆ®¿¡¼­ Â÷·Ê·Î °ªÀ» Çϳª¾¿ ²¨³»¾î ±× °ªÀ» parent·Î °¡Áö°í ÀÖ´Â ±ÛÀ» ã¾Æ¼­ »èÁ¦¸®½ºÆ®¿¡ Ãß°¡ÇÑ´Ù
  • »èÁ¦¸®½ºÆ®¿¡ ÀúÀåµÈ ±ÛÀ» »èÁ¦ÇÑ´Ù

86¹ø±ÛÀ» »èÁ¦ÇÏ·Á ÇÑ´Ù¸é ¿ì¼± 86À» »èÁ¦¸®½ºÆ®¿¡ Ãß°¡ÇÕ´Ï´Ù.
»èÁ¦¸®½ºÆ®¿¡ 86À̶ó´Â °ªÀÌ ÀúÀåµÇ¾úÀ¸¹Ç·Î »èÁ¦¸®½ºÆ®¿¡¼­ 86À̶ó´Â °ªÀ» ²¨³»¾î ±× °ªÀ» parent·Î °¡Áö°í ÀÖ´Â 87À» »èÁ¦¸®½ºÆ®¿¡ Ãß°¡ÇÕ´Ï´Ù.
´ÙÀ½¿¡ 87À» »èÁ¦¸®½ºÆ®¿¡¼­ ²¨³»¾î ±× °ªÀ» parent ·Î °¡Áö°í ÀÖ´Â 88À» »èÁ¦¸®½ºÆ®¿¡ Ãß°¡ÇÕ´Ï´Ù.
´Ù½Ã »èÁ¦¸®½ºÆ®¿¡¼­ 88À» ²¨³»¾î ±× °ªÀ» parent·Î °¡Áö°í ÀÖ´Â ±ÛÀ» ã½À´Ï´Ù.
ÇÏÁö¸¸ 88À» parent·Î °¡Áö°í ÀÖ´Â °ªÀÌ ¾øÀ¸¹Ç·Î »èÁ¦¸®½ºÆ®¸¦ ¿Ï¼ºµÇ¾ú½À´Ï´Ù.
»èÁ¦¸®½ºÆ®°¡ ¿Ï¼ºµÇ¾úÀ¸¹Ç·Î »èÁ¦¸®½ºÆ®¿¡ ÀÖ´Â ±ÛÀ» ¸ðµÎ Áö¿ó´Ï´Ù.
¾Æ·¡ ±¸Çö Äڵ忡¼­´Â À§ ³»¿ëÀ» ±¸ÇöÇϱâ À§ÇØ ¸Þ¼Òµå ³»¿¡¼­ ÀÚ±â ÀÚ½ÅÀ» ºÎ¸£´Â, Àç±Í ¸Þ¼Òµå¸¦ »ç¿ëÇß½À´Ï´Ù.
¹®Á¦´Â Àç±Í ¸Þ¼Òµå·Î ¸¸µé¾î°¡´Â »èÁ¦¸®½ºÆ®¿¡¼­ ¼ø¼­´ë·Î Çϳª¾¿ °ªÀ» ²¨³»¾ß ÇÏ¸ç ¶Ç Àç±Í¸Þ¼Òµå È£ÃâÀ» »èÁ¦¸®½ºÆ®°¡ ¿Ï¼ºµÇ¸é ³¡³»¾ß ÇÑ´Ù´Â °ÍÀÔ´Ï´Ù.
À̸¦ À§Çؼ­ »èÁ¦¸®½ºÆ®¿¡ À妽º(idx)¸¦ µµÀÔÇÕ´Ï´Ù.

¸ÕÀú 86¹øÀ» »èÁ¦ÇÒ ¶§´Â ¿ì¼± »èÁ¦¸®½ºÆ®¿¡ 86¹ø ±ÛÀ» Ãß°¡ÇÕ´Ï´Ù.
»èÁ¦¸®½ºÆ®·Î¼­ Vector ¸¦ ÀÌ¿ëÇÒÅÙµ¥ Vector ´Â ¹è¿­°ú °°ÀÌ 0ºÎÅÍ ¹æ¹øÈ£¸¦ ºÙÀÔ´Ï´Ù.

»èÁ¦ÇÒ ±Û¹øÈ£ 86À» ÀÎÀÚ·Î Àç±Í¸Þ¼Òµå¸¦ È£ÃâÇÕ´Ï´Ù.
Àç±Í¸Þ¼Òµå ³»ºÎ¿¡¼­ 86À» parent °ªÀ¸·Î °¡Áö´Â ±ÛÀÇ ±Û¹øÈ£¸¦ »èÁ¦¸®½ºÆ®¿¡ Ãß°¡ÇÕ´Ï´Ù.
(87ÀÌ »èÁ¦¸®½ºÆ®¿¡ Ãß°¡µË´Ï´Ù.) »èÁ¦¸®½ºÆ®ÀÇ Å©±â°¡ À妽º(ÇöÀç 1)º¸´Ù Å« Áö °Ë»çÇÕ´Ï´Ù.
Áï, 86 ´ÙÀ½¿¡ »èÁ¦¸®½ºÆ®¿¡ °ªÀÌ Ãß°¡µÇ¾ú´ÂÁö °Ë»çÇÕ´Ï´Ù.
87ÀÌ ÀÖÀ¸¹Ç·Î ´Ù½Ã 87À» ÀÎÀÚ·Î ÇØ¼­ Àç±ÍÇÔ¼ö¸¦ È£ÃâÇÕ´Ï´Ù.
È£ÃâÇϱâ Àü¿¡ À妽º´Â 1 Áõ°¡½Ãŵ´Ï´Ù. 87 À» ºÎ¸ð·Î ÇÏ´Â ±ÛÀÌ ÀÖ´ÂÁö ã°í ±× ±Û¹øÈ£¸¦ »èÁ¦¸®½ºÆ®¿¡ Ãß°¡ÇÕ´Ï´Ù.
88 ÀÌ »èÁ¦¸®½ºÆ®¿¡ Ãß°¡µË´Ï´Ù. »èÁ¦¸®½ºÆ®ÀÇ Å©±â°¡ À妽º(ÇöÀç 2)º¸´Ù Å« Áö °Ë»çÇÕ´Ï´Ù.
ÇöÀç »èÁ¦¸®½ºÆ®°¡ 86,87,88 À̹ǷΠũ±â°¡ 3À̹ǷΠ2º¸´Ù Å®´Ï´Ù.
µû¶ó¼­ À̹ø¿¡´Â À妽º°¡ °¡¸£Å°´Â º¤ÅÍÀÇ ¹æ¿¡ ÀúÀåµÈ 88À» ²¨³»¾î 88À» ÀÎÀÚ·Î ÇØ¼­ Àç±ÍÇÔ¼ö¸¦ È£ÃâÇÕ´Ï´Ù.
È£ÃâÇϱâ Àü¿¡ À妽º¸¦ 1 Áõ°¡½Ãŵ´Ï´Ù.
88 À» parent °ªÀ¸·Î °¡Áö´Â ±ÛÀÌ ¾øÀ¸¹Ç·Î »èÁ¦¸®½ºÆ®¿¡ Ãß°¡´Â ¾ø°Ô µË´Ï´Ù.
´Ù½Ã »èÁ¦¸®½ºÆ®ÀÇ Å©±â(ÇöÀç 3)°¡ À妽º(ÇöÀç 3) º¸´Ù Å« Áö °Ë»çÇÕ´Ï´Ù.
Å©Áö ¾ÊÀ¸¹Ç·Î Àç±ÍÇÔ¼ö°¡ ¿©±â¼­ Á¾·áµË´Ï´Ù.
¿Ï¼ºµÈ »èÁ¦¸®½ºÆ®¿¡´Â 86,87,88 ÀÌ ÀúÀåµÇ¾î ÀÖ½À´Ï´Ù.
»èÁ¦¸®½ºÆ®¿¡ ÀúÀåµÈ ±ÛÀ» »èÁ¦ÇÕ´Ï´Ù.
´ÙÀ½°ú °°ÀÌ RecursiveDeletion.java ¿Í BoardDeleter1.java ¸¦ ±¸ÇöÇÕ´Ï´Ù.

RecursiveDeletion.java

package net.java_school.util.db;

import java.sql.*;
import java.util.Vector;
//import net.java_school.db.dbpool.*;

public class RecursiveDeletion {
 //private ConnectionManager dbmgr;
 
 private String sql1 = "SELECT num FROM board WHERE parent = ?";
 private String sql2 = "DELETE FROM board WHERE num = ?";
 
 private int target;
 private ResultSet rs;
 
 private Vector<Integer> v = new Vector<Integer>();
 private int idx = 1;
 private PreparedStatement prepare = null;
 private Connection con = null;
 
 public RecursiveDeletion(Connection con) {
  this.con = con;
 }
 
 public void getDeleteList(int num) {
  try {
   prepare = con.prepareStatement(sql1);
   prepare.setInt(1,num);
   ResultSet rs = prepare.executeQuery();
   while (rs.next()) {
    target = rs.getInt("num");
    v.addElement(new Integer(target));
   }
   if (idx < v.size()) {
    Integer value = (Integer) v.elementAt(idx++);
    getDeleteList(value.intValue());
   }
  } catch (SQLException e) {
  } finally {
   try {
    prepare.close();
   } catch(SQLException e){}
  }
 }
 
 public void addDeleteList(int num) {
  v.addElement(new Integer(num));
 }
 
 public void delete() {
  try {
   prepare = con.prepareStatement(sql2);
   for( int i=0; i < v.size(); i++ ) {
    Integer value = (Integer)v.elementAt(i);
    prepare.setInt(1, value.intValue());
    prepare.executeQuery();
   }
  }catch ( SQLException e ) {
  }finally {
   try {
    prepare.close();
    con.close();
    v.removeAllElements();
   } catch ( SQLException e ){}
  }
 }
}

BoardDeleter1.java

package net.java_school.board;

import java.io.*;
import javax.servlet.*;
import javax.servlet.http.*;
import java.sql.*;
import javax.sql.*;
import javax.naming.*;
import net.java_school.util.Log;
import net.java_school.util.db.*;

public class BoardDeleter1 extends HttpServlet {

  DataSource ds = null;
  PreparedStatement prepare = null;

  public void init() throws ServletException {
    try {
      Context ic = new InitialContext();
      ds = (DataSource)ic.lookup("java:comp/env/jdbc/orcl");
    } catch ( NamingException ne ) {}
  }

  public void doPost( HttpServletRequest req, HttpServletResponse res ) 
  throws ServletException, IOException {

    req.setCharacterEncoding("euc-kr");
    res.setContentType("text/html;charset=euc-kr");

    PrintWriter out=res.getWriter();

    Log log = new Log();

    int num = Integer.parseInt( req.getParameter( "num" ) );
    String cur_page = req.getParameter( "cur_page" );
    String keyfield = req.getParameter( "keyfield" );
    String key = req.getParameter( "key" );

    Connection con = null;

    try {
      con = ds.getConnection();
    } catch ( SQLException e ) {}

    RecursiveDeletion rec = new RecursiveDeletion(con);

    // 1. ¸ÕÀú »èÁ¦ÇÏ·Á´Â ±ÛÀÇ °íÀ¯¹øÈ£¸¦ »èÁ¦¸®½ºÆ®¿¡ ¿Ã¸°´Ù
    rec.addDeleteList(num);
    // 2. »èÁ¦ÇÏ·Á´Â ±ÛÀÇ num°ªÀ¸·ÎºÎÅÍ »èÁ¦ ´ë»ó ±ÛÀ» »èÁ¦¸®½ºÆ®¿¡ Ãß°¡ÇÑ´Ù.
    rec.getDeleteList(num);
    // 3. »èÁ¦¸®½ºÆ®¿¡ ¿Ã¸° ±Û ¸ðµÎ¸¦ »èÁ¦ÇÑ´Ù. 
    rec.delete();

    String path = req.getContextPath();
    String formstr = "";
    formstr = "<form name=frmList method=post action="+path+"/board1/list.jsp>";
    formstr += "<input type=hidden name=cur_page value='"+cur_page+"' />";
    formstr += "<input type=hidden name=keyfield value='"+keyfield+"' />";
    formstr += "<input type=hidden name=key value='"+key+"' />";
    formstr += "</form>";
    out.println(formstr);
    String scriptstr = "";
    scriptstr += "<script language=javascript>";
    scriptstr += "function goList() {";
    scriptstr += " document.frmList.submit(); }";
    scriptstr += "</script>";
    scriptstr += "<script>goList();</script>";
    out.println(scriptstr);
  }
}