ABOUT ME

-

Today
-
Yesterday
-
Total
-
  • Servlet-JSP MVC01 (2) - Servlet과 Model 연결 (회원관리테이블)
    Web/Servlet-JSP 2023. 5. 24. 22:26

     

     

    1. 입력 받을 Html파일 준비 

     

    <!DOCTYPE html>
    <html>
    <head>
    <meta charset="UTF-8">
    <title>Insert title here</title>
    <meta charset="utf-8">
      <meta name="viewport" content="width=device-width, initial-scale=1">
      <link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.4.1/css/bootstrap.min.css">
      <script src="https://ajax.googleapis.com/ajax/libs/jquery/3.6.4/jquery.min.js"></script>
      <script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.4.1/js/bootstrap.min.js"></script>
    </head>
    <body>
    회원가입화면 
    <form action="/MVC01/memberInsert.do" method="post">
    <table class="table table-bordered">
    
      <tr>
        <td>아이디 </td>
        <td><input type="text" name="id"></td>
      </tr>
      <tr>
        <td>패스워드</td>
        <td><input type="password" name="pass"></td>
      </tr>
      <tr>
        <td>이름</td>
        <td><input type="text" name="name"></td>
      </tr>
      <tr>
        <td>나이</td>
        <td><input type="text" name="age"></td>
      </tr>
      <tr>
        <td>이메일</td>
        <td><input type="text" name="email"></td>
      </tr>
      <tr>
        <td>전화번호</td>
        <td><input type="text" name="phone"></td>
      </tr>
      <tr>
        <td colspan="2" align="center">
        <input type ="submit" value="가입" class="btn btn-primary"/>
        <input type ="reset" value="취소" class="btn btn-warning"/>
        </td>
      </tr>
    
    </table>
    </form>
    </body>
    </html

     

    > html은 tablegenrator사이트에 접속해서 만든 테이블이다. (쉽게 만들 수 있음!)

     

    > html파일의 위치는 webapp/member에 위치한다. 여기서 그냥 submit을 하면 webapp/member/memberInsert.do가 된다. 즉, member디렉토리 위치에서 memberInsert.do이름의 파일이나 관련 url매핑된 것이 있는지 찾는 것이다. 서블릿 클래스가 위치한 곳은 webapp/WEB-INF/classes이고, WEB-INF부터는 접근이 안되고 WAS가 알아서 찾아줌으로 action을 루트 디렉토리로 주도록 하자.

     

    > input에 파라미터들은 VO클래스 멤버들과 이름을 맞추는 것이 추후 작업시 편하다.

     

    2. 멤버 컨트롤러 만들어서 입력받고, VO객체에 저장하기 

    @WebServlet("/memberInsert.do")
    public class MemberInsertController extends HttpServlet {
    	
    	protected void service(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
    		//1. 파라미터 수집(vo)에 묶어주기 
    		//request로 넘어온 값을 인코딩 해줘야함 
    		request.setCharacterEncoding("utf-8");
    		String id = request.getParameter("id");
    		String pass = request.getParameter("pass");
    		String name = request.getParameter("name");
    		int age = Integer.parseInt(request.getParameter("age"));
    		String email = request.getParameter("email");
    		String phone = request.getParameter("phone");
    		
    		MemberVO vo = new MemberVO(id,pass,name,age,email,phone);
    		//vo를 DAO에 넘겨서 DB에 INSERT하자
    		
    		//model과 연결 (DAO)
    		MemberDAO dao = new MemberDAO();
    		int cnt = dao.memberInsert(vo);
    		PrintWriter out = response.getWriter();
    		if(cnt>0) { //가입성공
    	
    			out.println("Insert success"); //DB 서버 실행되있어야함
    		}else {//가입실패 
    			throw new ServletException("not insert");
    		}
    		
    		
    	}
    
    }

    > 파라미터를 수집해준다. 요청으로 넘어온 값을 VO와 묶는 과정이다.

    > 클라이언트와 서버간 통신에서 데이터는 바이트 단위로 전달된다.

    > 따라서 한글로 넘어온 입력은 인코딩이 맞지않으면 내부에서 깨지게 된다. request인코딩 변환을 통해 이를 방지할 수 있다. (post방식으로 넘어온 입력은 이렇게 request의 인코딩 변환으로 처리할 수 있지만 get방식으로 넘어온 입력을 변환하려면 다른 방식이 필요하다.)

    > 한글 출력을 위해서도 response도 인코딩을 해야하는데, -> setCharacterEncoding(), setContentType() 두가지 메서드를 통해 적절히 인코딩변환을 해줘야 한다.

     

    3. DAO만들기

     

    public class MemberDAO {
    	private Connection conn;//DB와 연결 
    	private PreparedStatement ps; //conn의 sql DB에 전송
    	private ResultSet rs; //select 실행결과 저장 //실행결과를 마치 이터레이터처럼
    	                      //한 행씩 받아올 수 있음
    	
    	//데이터 베이스 연결객체 생성해야함 커넥션
    	public void getConnect() {
    		String URL ="jdbc:mysql://localhost:3306/test?characterEncoding=UTF-8&serverTimeZone=UTC";
    		String user="root";
    		String password="-";
    		//mysql 드라이버를 로딩해야함 Driver Loading
    		//드라이버란 데이터베이스 종류는 많은데 이걸 드라이버로 
    		//드라이버 클래스 com.mysql.jdc.Driver
    		try {
    			//동적로딩
    			Class.forName("com.mysql.jdbc.Driver");
    			//드라이버를 얻고 실제 커넥션을 얻기
    			conn = DriverManager.getConnection(URL,user,password); //연결완료 후 연결정보 넘김
    			//그 연결정보를 받아오는게 Connetion클래스 
    		} catch (Exception e) {
    			e.printStackTrace();
    		} //동적로딩 실행시점에서 메모리를 올림 
    			
    		
    	}
    	public int memberInsert(MemberVO vo) {
    		//?sql파라미터 
    		String SQL ="INSERT INTO member(id,pass,name,age,email,phone) values(?,?,?,?,?,?)";
    		getConnect();
    		int cnt =-1;
    		//SQL문장 전송 객체 
    		try {
    			ps = conn.prepareStatement(SQL); //미리 컴파일 시킴(속도가 빨라서)
    			//ps는 이미 컴파일 된 sql(프리컴파일) 가지고 있음 (ps한테 준거임 미리 한번 컴파일해서)
    			ps.setString(1, vo.getId());
    			ps.setString(2, vo.getPass());
    			ps.setString(3, vo.getName());
    			ps.setInt(4, vo.getAge());
    			ps.setString(5, vo.getEmail());
    			ps.setString(6, vo.getPhone());
    			cnt = ps.executeUpdate(); // 전송(실행) ps가 채워서 진짜 보냄 (성공1,실패0)
    		} catch (Exception e) {
    			e.printStackTrace();
    		}
    		return cnt;
    		
    	}
    	
    	
    }

     

    > JDBC를 이용해 DB와 소통하기 위해 먼저 연결/인증객체, 문장실행객체, 결과패치객체 3가지를 순서대로 초기화 해야한다.

    > 먼저 Class.forName("드라이버 클래스")를 통해 드라이버 클래스를 로딩하자.

    > 다음은 케넥션을 얻자 conn = DriverManager.getConnection(URL,user,password);

    > 커넥션을 통해 문장실행 객체를 얻자 ps = conn.prepareStatement(SQL);

    >  cnt = ps.executeUpdate(); // 전송(실행)  (성공1,실패0)  -- (결과패치 ResultSet은 사용안했다)

    > ?은 sql파라미터이다.

    > conn이 문장 실행 객체를 얻으면서 sql을 pre컴파일했는데, 이는 ?제외 sql오류검사하고, 속도가빨라서 한다고한다.

     

    *왼쪽은 URL, 오른쪽은 Driver Class 

     

    3.2 동적로딩을 하는 이유 

     

    순서대로 객체를 생성하도록 하는 기능을 수행한다. 

    DB와 연결/인증이 완료되어야 문장을 실행하고,  문장을 실행해야 결과를 패치할 수 있기 때문에

    Class.forName()-드라이버 얻고-> Connertion (연결/인증)얻고 -> Statement 문장을 실행하고 -> ResultSet 결과 패치 순서로 가야한다는 것이다. 만약 정적로딩이 가능했다면, 연결/인증과정을 건너뛰고 Statement st = new Statement() 했을지도 모른다.

     

    > 유지보수의 이점이 있다.

     다른 DB를 쓰고 싶다면, Class.forName("드라이버 클래스 path") 여기서 드라이버 클래스 path만 변경하면 나머지는 크게   안바꿔도 된다. 어차피 JDBC에서 제공하는 API를 이용하고 있고, API구현체는 DB 드라이버 별로 내부적으로 구현되어 있기 때문이다. 

     

     

    다시한번 처리 과정에 따라 필요사항을 정리하자면,

    1. 입력받을 뷰 (클라이언트 입력)  :form태그, VO객체와 input 파라미터명 맞추기 ,(get & post)

    2. 클라이언트 입력 받을 컨트롤러 : 파라미터 수집,수집한 파라미터로 VO객체만들기(행)

    3. DB에 접근할 DAO객체: 드라이버, 동적로딩, URL 및 드라이버 class, lib에 관련 jar파일 추가 

    4. 컨트롤러 - 모델 연결 : VO객체를 DAO객체에 전달  

     

     

    참고자료: 인프런 나프1탄 - 박매일

Designed by Tistory.