공적's life

4-5 JDBC-2 본문

Programing/Java programing

4-5 JDBC-2

melpis 2010. 8. 10. 21:47

이제 우리가 작성 했던 클래스를 조금 더 다듬어 볼까요?

 

일단 다듬어야 할 부분을 생각해보죠. 첫째로 저렇게 문자열을 끼어 넣는 건 실수 할 여지도 있고

 

조금 힘들지 않을까요? 그 부분을 어떻게 잘 처리 해보도록 하죠.

 

그리고 예외처리를 제대로 해보도록 하죠.

 

첫 번째 문제를 해결하기 위해서 일단 API를 한번 살펴 보도록 하죠.

 

찾아 보니 이런 예제가 있네요?

 

에고 오라클로 넘어가면서 api찾기가 힘드네요. 역시 영어가 많이 부족함을 느낍니다.

 

http://download.oracle.com/javase/6/docs/api/

 

혹시 저와 같은 고민을 하시는 분들에게 링크를 걸어 드리죠^^

 

PreparedStatement pstmt = con.prepareStatement("UPDATE EMPLOYEES

SET SALARY = ? WHERE ID = ?");

pstmt.setBigDecimal(1, 153833.00)

pstmt.setInt(2, 110592)

 

이러한 예제가 있네요. 앗 우리가 넣어 줄 값들을 "?" 하면 문자열 처리 안 해도 되는군요.

 

그럼 나머지 코드를 빠른 속도로 수정해 보도록 하죠.

 

제가 한 것을 빠르게 보여 드릴게요

//Insert

//3.3 sql문 준비하기

    String sql ="insert into TB_BOARD(SEQ, TITLE, CONTENT, REGIST_DATE, HIT)";

    sql+="values(SEQ_TB_BOARD.NEXTVAL, ?, ?, sysdate, 0) ";

    //3.4 prepardStatement에 sql넣기

    PreparedStatement preparedStatement = connection.prepareStatement(sql);

    //3.5 prepardStatement 값 맵핑

    preparedStatement.setString(1, userInputTitle);

    preparedStatement.setString(2, userInputContent);

 

//select

//3.3 sql문 준비하기

String sql =" select SEQ, TITLE, CONTENT, REGIST_DATE, HIT ";

    sql+=" from TB_BOARD ";

    sql+=" where SEQ= ? ";

    //3.4 prepardStatement에 sql넣기

    PreparedStatement preparedStatement = connection.prepareStatement(sql);

    //3.5 prepardStatement 값 맵핑

    preparedStatement.setInt(1, parameterSeq);

 

//delete

//3.3 sql문 준비하기

String sql =" delete from TB_BOARD ";

    sql+=" where SEQ= ? ";

    //3.4 prepardStatement에 sql넣기

    PreparedStatement preparedStatement = connection.prepareStatement(sql);

    //3.5 prepardStatement 값 맵핑

    preparedStatement.setInt(1, parameterSeq);

 

//update

//3.3 sql문 준비하기

    String sql =" update TB_BOARD set ";

    sql+=" TITLE = ? , ";

    sql+=" CONTENT = ? , ";

    sql+=" REGIST_DATE = sysdate ";

    sql+=" where SEQ= ? ";

    //3.4 prepardStatement에 sql넣기

    PreparedStatement preparedStatement = connection.prepareStatement(sql);

    //3.5 prepardStatement 값 맵핑

    preparedStatement.setString(1, userInputTitle);

    preparedStatement.setString(2, userInputContent);

    preparedStatement.setInt(3,parameterSeq);

 

뭐 전보다 많이 쉬워졌죠? 이제 예외처리를 해보도록 하죠.

 

왜 예외처리가 필요 하는 가 하면 한번 데이터베이스에 접속하게 되면 close() 하기 전까지 유지가 됩니다.

 

그런데 중간에 예외가 일어나서 close()문을 만나지 못하고 종료가 되는 상황이 있을 수도 있습니다.

 

그럼 접속 즉 커넥션은 살아 있게 되고, 그런 것이 계속 쌓이다 보면 데이터베이스는 어느새 접속을 차단 합니다.

 

왜냐하면 데이터베이스가 처리 할 수 있는 한계가 있기 때문입니다. 그렇기 때문에 접속을 차단하고 접속이 끊기기를

 

기다립니다. 그렇기 때문에 우리는 이 부분을 확실하게 해줘야 합니다. 그럼 한번 해볼까요?

 

일단 try catch부터 제대로 설명하고 진행 하겠습니다. 일단 try{ } 영역 즉 {부터 }까지 catch에서 지정된 예외가

 

발생되면 그쪽으로 바로 넘어가게 됩니다. 그럼 catch는 말 그대로 그 예외를 잡아서 처리하게 되는 것이지요.

 

아 그렇다면 정상적으로 실행 할 때는 기존처럼 진행하고 catch문에서 또 다시 close를 해주면 되겠네요?

 

하지만 이것보다 더 좋은 방법이 있습니다. 바로 finally라는 키워드 입니다. 이것은 무조건 실행하게 되는 영역입니다.

 

이 영역에 프로그래밍 하면 무조건 정상적으로 실행되던지 예외가 발생 되던지 무조건 이 영역을 거치게 되는 것입니다.

 

그렇기 때문에 이 영역에 close를 해놓으면 웬만하면 close를 할 수 있습니다. 이렇게 글보다 직접 보는 게 낫죠.

 

그럼 한번 해보죠.

 

간단합니다.

 

Connection connection = null;

    PreparedStatement preparedStatement = null;

    try {

        //3.2 연결하기

        connection = DriverManager.getConnection(DB_URI,DB_USER_NAME,DB_USER_PASSWORE);

        //3.3 sql문 준비하기

        String sql ="insert into TB_BOARD(SEQ, TITLE, CONTENT, REGIST_DATE, HIT)";

        sql+="values(SEQ_TB_BOARD.NEXTVAL, ?, ?, sysdate, 0) ";

        //3.4 prepardStatement에 sql넣기

        preparedStatement = connection.prepareStatement(sql);

        //3.5 prepardStatement 값 맵핑

        preparedStatement.setString(1, userInputTitle);

        preparedStatement.setString(2, userInputContent);

        //3.6 실행

        preparedStatement.executeUpdate();

        

    } catch (SQLException e) {

        // TODO Auto-generated catch block

        e.printStackTrace();

    }finally{

        if(preparedStatement !=null){ try {preparedStatement.close();} catch (SQLException e) {} }

        if(connection !=null){ try { connection.close();} catch (SQLException e) {}    }

    }

 

이렇게 하시면 됩니다. 무조건 finally 해석하면 마지막으로 최종적으로니까 최종적으로 무언가 한다는 뜻입니다. 역시나 영어를

 

잘하면 편하군요. 일단 null인 경우에는 애초에 connection을 연결한적이 없거나 혹은 preparedStatement에 객체가 생성된 적 없기에

 

닫아 줄 필요가 없는 것입니다. 그렇기 때문에 생성됐거나 접속 됐을 때만 처리 해주시면 됩니다.

 

음 중복 제거도 하고 싶었지만 그것은 추후로 미루도록 하죠. 그럼 두 번에 JDBC를 끝내고 XML을 해보도록 하죠.

 

XML로 무엇을 할거냐 저기 있는 sql문을 전부 xml로 빼서 처리 해보도록 하죠.

 

package com.tistory.melpis.board;

import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.text.ParseException;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

public class BoardManager {
	private final String DRIVER_NAME="oracle.jdbc.driver.OracleDriver";
	private final String DB_URI="jdbc:oracle:thin:@localhost:1521:XE";
	private final String DB_USER_NAME="user00";
	private final String DB_USER_PASSWORE="user00";
	
	public BoardManager(){
	}
	
	// 문서 등록 폼
	public void registDoumentForm() {

		// 1. 등록 폼출력
		System.out.println("제목: ");
		System.out.println("내용: ");

	}
	// 문서 등록
	public void registDocument(String[] outputData) {
		// 1.1 제목 추출
		String userInputTitle = outputData[1];
		// 1.2 내용 추출
		String userInputContent = outputData[2];
		// 2. 유효성 검사
		if (userInputTitle.length() < 1 && userInputTitle.length() > 600) {
			return;
		}
		if (userInputContent.length() < 1 && userInputContent.length() > 2000) {
			return;
		}
		try {
			//3.1 드라이버 로딩
			Class.forName(DRIVER_NAME);
		} catch (ClassNotFoundException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		Connection connection = null;
		PreparedStatement preparedStatement = null;
		try {
			//3.2 연결하기 
			connection = DriverManager.getConnection(DB_URI,DB_USER_NAME,DB_USER_PASSWORE);
			//3.3 sql문 준비하기
			String sql ="insert into TB_BOARD(SEQ, TITLE, CONTENT, REGIST_DATE, HIT)";
				sql+="values(SEQ_TB_BOARD.NEXTVAL, ?, ?, sysdate, 0) ";
			//3.4 prepardStatement에 sql넣기
			preparedStatement = connection.prepareStatement(sql);
			//3.5 prepardStatement 값 맵핑
			preparedStatement.setString(1, userInputTitle);
			preparedStatement.setString(2, userInputContent);
			//3.6 실행
			preparedStatement.executeUpdate();
		
		} catch (SQLException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}finally{
			if(preparedStatement != null){ try {preparedStatement.close();} catch (SQLException e) {} }
			if(connection != null){ try { connection.close();} catch (SQLException e) {}	}
		}
		
		// 4. 결과 출력
		System.out.println("등록 완료");

	}
	
	// 문서 상세 보기 
	public void viewDocument(String[] outputData){
		//1. 사용자가 입력한 문서 번호 가져오기
		String userInputSeq = outputData[1];
		//1.1 변환
		int parameterSeq = Integer.parseInt(userInputSeq);
		//2. 유효성 검사
		if(parameterSeq <=0){
			return;
		}
		
		try {
			//3.1 드라이버 로딩
			Class.forName(DRIVER_NAME);
		} catch (ClassNotFoundException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		Map data = null;
		
		Connection connection = null;
		PreparedStatement preparedStatement = null;
		ResultSet resultSet = null;
		
		try {
			//3.2 연결하기 
			connection = DriverManager.getConnection(DB_URI,DB_USER_NAME,DB_USER_PASSWORE);
			//3.3 sql문 준비하기
			String sql =" select SEQ, TITLE, CONTENT, REGIST_DATE, HIT ";
			sql+=" from TB_BOARD ";
			sql+=" where SEQ= ? ";
			//3.4 prepardStatement에 sql넣기
			preparedStatement = connection.prepareStatement(sql);
			//3.5 prepardStatement 값 맵핑
			preparedStatement.setInt(1, parameterSeq);
			//3.6 실행
			resultSet =preparedStatement.executeQuery();
			//3.7 결과값 매핑
			if(resultSet.next()){
				data = new HashMap();
				data.put("SEQ", String.valueOf(resultSet.getInt("SEQ")));
				data.put("TITLE",resultSet.getString("TITLE"));
				data.put("CONTENT",resultSet.getString("CONTENT"));
				data.put("REGIST_DATE",resultSet.getDate("REGIST_DATE").toString());
				data.put("HIT",String.valueOf(resultSet.getInt("HIT")));
			}
		} catch (SQLException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}finally{
			if(resultSet != null){try {resultSet.close();} catch (SQLException e) {} }
			if(preparedStatement != null){ try {preparedStatement.close();} catch (SQLException e) {} }
			if(connection != null){ try { connection.close();} catch (SQLException e) {}	}
		}
		//4. 결과 출력
		System.out.println("글번호 : " +data.get("SEQ"));
		System.out.println("제목  : "  +data.get("TITLE"));
		System.out.println("등록일 : " +data.get("REGIST_DATE"));
		System.out.println("조회수 : " +data.get("HIT"));
		System.out.println("내용 : "  +data.get("CONTENT"));
		
	}
	

	public void viewDocumentList(){
		
		try {
			//3.1 드라이버 로딩
			Class.forName(DRIVER_NAME);
		} catch (ClassNotFoundException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	
		List> dataList = new ArrayList>();
		
		Connection connection = null;
		PreparedStatement preparedStatement = null;
		ResultSet resultSet = null;
		
		try {
			//3.2 연결하기 
			connection = DriverManager.getConnection(DB_URI,DB_USER_NAME,DB_USER_PASSWORE);
			//3.3 sql문 준비하기
			String sql =" select SEQ, TITLE, CONTENT, REGIST_DATE, HIT ";
			sql+=" from TB_BOARD ";
			//3.4 prepardStatement에 sql넣기
			preparedStatement = connection.prepareStatement(sql);
			//3.5 실행
			resultSet =preparedStatement.executeQuery();
			//3.6 결과값 매핑
			while(resultSet.next()){
				Map data = new HashMap();
				data.put("SEQ", String.valueOf(resultSet.getInt("SEQ")));
				data.put("TITLE",resultSet.getString("TITLE"));
				data.put("CONTENT",resultSet.getString("CONTENT"));
				data.put("REGIST_DATE",resultSet.getDate("REGIST_DATE").toString());
				data.put("HIT",String.valueOf(resultSet.getInt("HIT")));
				dataList.add(data);
			}
			
		} catch (SQLException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}finally{
			if(resultSet != null){try {resultSet.close();} catch (SQLException e) {} }
			if(preparedStatement != null){ try {preparedStatement.close();} catch (SQLException e) {} }
			if(connection != null){ try { connection.close();} catch (SQLException e) {}	}
		}
		// 4. 결과 출력
		for(Map data:dataList){
			System.out.println("글번호 : " +data.get("SEQ"));
			System.out.println("제목  : "  +data.get("TITLE"));
			System.out.println("등록일 : " +data.get("REGIST_DATE"));
			System.out.println("조회수 : " +data.get("HIT"));
			System.out.println("내용 : "  +data.get("CONTENT"));
		}

	}

	public void deleteDocument(String[] outputData) {
		//1. 사용자가 입력한 문서 번호 가져오기
		String userInputSeq = outputData[1];
		//1.1 변환
		int parameterSeq = Integer.parseInt(userInputSeq);
		//2. 유효성 검사
		if(parameterSeq<=0){
			return ;
		}
		
		try {
			//3.1 드라이버 로딩
			Class.forName(DRIVER_NAME);
		} catch (ClassNotFoundException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		
		Connection connection = null;
		PreparedStatement preparedStatement = null;
		
		try {
			//3.2 연결하기 
			connection = DriverManager.getConnection(DB_URI,DB_USER_NAME,DB_USER_PASSWORE);
			//3.3 sql문 준비하기
			String sql =" delete from TB_BOARD ";
			sql+=" where SEQ= ? ";
			//3.4 prepardStatement에 sql넣기
			preparedStatement = connection.prepareStatement(sql);
			//3.5 prepardStatement 값 맵핑
			preparedStatement.setInt(1, parameterSeq);
			//3.6 실행
			preparedStatement.executeUpdate();
			
		} catch (SQLException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}finally{
			if(preparedStatement != null){ try {preparedStatement.close();} catch (SQLException e) {} }
			if(connection != null){ try { connection.close();} catch (SQLException e) {}	}
		}
		
		//4. 결과 출력
		System.out.println("삭제 되었습니다");

	}

	public void editDocumentForm(String[] outputData) throws ParseException {
		//1. 사용자가 입력한 문서 번호 가져오기
		String userInputSeq = outputData[1];
		//1.1 변환
		int parameterSeq = Integer.parseInt(userInputSeq);
		//2. 유효성 검사
		if(parameterSeq<=0){
			return;
		}
		
		try {
			//3.1 드라이버 로딩
			Class.forName(DRIVER_NAME);
		} catch (ClassNotFoundException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		Map data = null;
		
		Connection connection = null;
		PreparedStatement preparedStatement = null;
		
		try {
			//3.2 연결하기 
			connection = DriverManager.getConnection(DB_URI,DB_USER_NAME,DB_USER_PASSWORE);
			//3.3 sql문 준비하기
			String sql =" select SEQ, TITLE, CONTENT, REGIST_DATE, HIT ";
			sql+=" from TB_BOARD ";
			sql+=" where SEQ= ? ";
			//3.4 prepardStatement에 sql넣기
			preparedStatement = connection.prepareStatement(sql);
			//3.5 prepardStatement 값 맵핑
			preparedStatement.setInt(1, parameterSeq);
			//3.6 실행
			ResultSet resultSet =preparedStatement.executeQuery();
			//3.7 결과값 매핑
			if(resultSet.next()){
				data = new HashMap();
				data.put("SEQ", String.valueOf(resultSet.getInt("SEQ")));
				data.put("TITLE",resultSet.getString("TITLE"));
				data.put("CONTENT",resultSet.getString("CONTENT"));
				data.put("REGIST_DATE",resultSet.getDate("REGIST_DATE").toString());
				data.put("HIT",String.valueOf(resultSet.getInt("HIT")));
			}
		
		} catch (SQLException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}finally{
			if(preparedStatement != null){ try {preparedStatement.close();} catch (SQLException e) {} }
			if(connection != null){ try { connection.close();} catch (SQLException e) {}	}
		}
		//4. 결과 출력
		System.out.println("글번호 : " +data.get("SEQ"));
		System.out.println("제목  : "  +data.get("TITLE"));
		System.out.println("등록일 : " +data.get("REGIST_DATE"));
		System.out.println("조회수 : " +data.get("HIT"));
		System.out.println("내용 : "  +data.get("CONTENT"));
		
	}

	public void editDocument(String[] outputData) {
		//1.1 번호 추출
		String userInputSeq = outputData[1];
		//1.2 제목 추출  
		String userInputTitle = outputData[2];
		//1.3 내용 추출
		String userInputContent = outputData[3];
		//1.4 변환
		int parameterSeq = Integer.parseInt(userInputSeq);
		//2. 유효성검사
		if(parameterSeq<=0){
			return ;
		}
		if (userInputTitle.length() < 1 && userInputTitle.length() > 600) {
			return;
		}
		if (userInputContent.length() < 1 && userInputContent.length() > 2000) {
			return;
		}
		try {
			//3.1 드라이버 로딩
			Class.forName(DRIVER_NAME);
		} catch (ClassNotFoundException e1) {
			// TODO Auto-generated catch block
			e1.printStackTrace();
		}
		
		Connection connection = null;
		PreparedStatement preparedStatement = null;
		
		try {
			//3.2 연결하기 
			connection = DriverManager.getConnection(DB_URI,DB_USER_NAME,DB_USER_PASSWORE);
			//3.3 sql문 준비하기
			String sql =" update TB_BOARD set ";
			sql+=" TITLE = ? , ";
			sql+=" CONTENT = ? , ";
			sql+=" REGIST_DATE = sysdate ";
			sql+=" where SEQ= ? ";
			//3.4 prepardStatement에 sql넣기
			preparedStatement = connection.prepareStatement(sql);
			//3.5 prepardStatement 값 맵핑
			preparedStatement.setString(1, userInputTitle);
			preparedStatement.setString(2, userInputContent);
			preparedStatement.setInt(3,parameterSeq);
			//3.6 실행
			preparedStatement.executeUpdate();
			
		} catch (SQLException e) {
			e.printStackTrace();
		}finally{
			if(preparedStatement != null){ try {preparedStatement.close();} catch (SQLException e) {} }
			if(connection != null){ try { connection.close();} catch (SQLException e) {}	}
		}
		
		//4. 결과 출력
		System.out.println("수정완료 하였습니다");

	}
	
}

'Programing > Java programing' 카테고리의 다른 글

4-7 I.O File JDBC XML 회고  (0) 2010.08.15
4-6 XML  (0) 2010.08.13
4-4 JDBC -1  (0) 2010.08.10
4-3 DataBase network  (0) 2010.08.07
4-2 NetWork  (0) 2010.08.03