웹 애플리케이션의 구조
Q. 미니 프로젝트(네이버 짝퉁 페이지 만들기)를 이제 막 마쳤다. 소감이 어떠한가.
개인적으로 이번 작품은 아쉽다(웃음). 코드를 되돌아 보면 JDBC로 DB에 연결할 때마다 동일 코드를
반복하는 경우가 많았다.
반복하는 경우가 많았다.
본인이 이 부분에 익숙하지 않고 성격이 급해 코드를 작성하기 급급했기 때문이다. 그래서 효율적인
코드 구조에 대해서도 생각하지 못했다.
코드 구조에 대해서도 생각하지 못했다.
그래서 아쉽다.
Q. 효율적인 코드 구조란 무엇인가?
중복을 최소한으로 한 간결한 코드를 말한다.
코드들을 공통된 사용도를 기준으로 하나의 단위로 각각 묶어 보면, 대충 구조가 보인다. 이 때 중복되는 코드 부분이
많으면 많을 수록 비효율적인 코드 구조다.
많으면 많을 수록 비효율적인 코드 구조다.
그러나 무조건 중복을 제거한다고 좋은 것은 아니다. 체계적으로 중복을 제거해야 좋은 것이다.
그래야 누락하는 부분 없이 효율적인 코드 구조를 만들 수 있다.
그래야 누락하는 부분 없이 효율적인 코드 구조를 만들 수 있다.
JDBC의 경우를 보자. 효율적인 JDBC 구조를 만들기 위해서는,
- Connection 부분을 메서드로 만든다. 필요시마다 메서드를 부른다.
때로는 Connection을 위한 클래스를 만들고 그 안에 Connection 메서드를 만들기도한다.
이전에는 우리가 SQL문을 사용할 때마다 적어주지 않았는가.
이 방법으로 중복을 최소한으로 할 수 있다.
- 큰 구조를 만든다. 일반적인 구조는 다음과 같다.
역시 잘 모를 때는 남들 하는 거 비슷하게 따라하는 것이 최고다.
JSP
생각보다 JSP는 생각보다 많은 일을 한다. 요청을 받기도 하고 응답을 주기도 한다.
그런데 이때는 처리도 처리지만 전달의 개념이 강하다. 예를 들어, 만약 응답을 한다면
serivce 클래스에서 데이터를 받아와 request에 저장한다. 저장 후에는 forward()나
sendRedirect()와 같은 메서드로 전달도 한다.
sendRedirect()와 같은 메서드로 전달도 한다.
(사실 이 부분은 아직 확신이 들지 않는다.)
MVC 프레임워크
MVC 프레임워크는 컨트롤러 역할을 한다. 크게 세 가지 역할을 한다고 보면 된다.
분석/ 분배/ 응답선택.
분석/ 분배/ 응답선택.
MVC 프레임워크는 (1)사용자의 요청을 받아 분석하고 (2) 분석이 끝나면 처리할 수 있는
클래스를 찾아서 처리할 것을 요청한다. (3)해당 클래스가 처리를끝내면 MVC 프레임워크는
알맞는 JSP view를 찾아서 결과를 전송한다.
클래스를 찾아서 처리할 것을 요청한다. (3)해당 클래스가 처리를끝내면 MVC 프레임워크는
알맞는 JSP view를 찾아서 결과를 전송한다.
DAO 클래스
DAO 클래스는 DB 관련 CRUD 작업을 처리한다고 했다. DAO 클래스의 주 특기는
삽입/선택/수정/삭제 구문들을 각 하나의 메서드로 만들어 실행한다.
삽입/선택/수정/삭제 구문들을 각 하나의 메서드로 만들어 실행한다.
• CRUD를 위한 메서드 정의
– insert() 메서드 : INSERT 쿼리를 실행한다.
– select() 메서드 : SELECT 쿼리를 실행한다. 검색 조건에 따라서 한 개 이상의 select() 메서드를
제공한다.
제공한다.
– update() 메서드 : UPDATE 쿼리를 실행한다.
– delete() 메서드 : DELETE 쿼리를 실행한다.
또, DAO 클래스는 DB에서 가져온 데이터를 Java/JSP 상에서 용이하게 처리하기 위해 BEANS
클래스를 만든다. 예를 들면,
클래스를 만든다. 예를 들면,
public class member {
private String id;
private String pwd;
private String name;
private String birth_year;
private String birth_mon;
private String birth_day;
private String gender;
private String email;
private int phone;
public member() {
}
public member(String id, String pwd, String name, String birth_year, String birth_mon, String birth_day,
String gender, String email, int phone) {
super();
this.id = id;
this.pwd = pwd;
this.name = name;
this.birth_year = birth_year;
this.birth_mon = birth_mon;
this.birth_day = birth_day;
this.gender = gender;
this.email = email;
this.phone = phone;
}
public String getId() {
return id;
}
public void setId(String id) {
this.id = id;
}
...
}
이때 Private 변수의 이름은 DB 컬럼의 이름과 맞춰주는 것이 좋다.
Q. 본인은 DAO 클래스에 Connection을 전달하는 방법에는 세 가지 경우의 수가
있다고 알고 있다. 설명해 달라.
이 부분에는 본인이 확신을 가지지 못한다. 그러나 최대한 아는 것처럼 설명해
보겠다. 틀리면 정정하면 되니까.
■DAO에 Connection 전달 방법
• DAO 클래스의 메서드에서 직접 Connection을 생성
– 1개 이상의 DAO 메서드 호출을 하나의 트랜잭션에서 처리 불가
• DAO 객체를 생성할 때 생성자에서 Connection을 전달 받기
– 1개 이상의 DAO 메서드 호출을 트랜잭션으로 묶을 수 있음
– 불필요하게 DAO 객체를 매번 생성하는 단점
• DAO 클래스의 메서드 파라미터로 Connection을 전달 받기
– 1개 이상의 DAO 메서드 호출을 트랜잭션으로 묶을 수 있음
– DAO 객체를 매번 생성할 필요 없음
이 세 가지 방법의 예시는 링크로 걸어두겠다.
http://stage-diary.tistory.com/m/107?category=971371
Q. 본인이 이해한 전체적인 구조는 이렇다. JSP로 요청이 오면 컨트롤러 역할인 MVC 프레임
워크가 알맞은 서비스 클래스로 처리를 요청한다. 서비스 클래스는 SQL을 사용하기 위한 DAO클래스에서
이것저것 불러와 요청을 처리하고 결과물을 MVC 프레임워크로 돌려준다. MVC 프레임워크는 결과를
다시 알맞은 뷰(JSP)로 돌려준다. 이게 요청/응답 처리이다.
워크가 알맞은 서비스 클래스로 처리를 요청한다. 서비스 클래스는 SQL을 사용하기 위한 DAO클래스에서
이것저것 불러와 요청을 처리하고 결과물을 MVC 프레임워크로 돌려준다. MVC 프레임워크는 결과를
다시 알맞은 뷰(JSP)로 돌려준다. 이게 요청/응답 처리이다.
이 과정에서 서비스 클래스는 코드들의 중복을 피하기 위해 Connection과 SQL 구문들을
따로 클래스/메서드로 빼 저장하고 필요시 마다 불러와 사용한다.
따로 클래스/메서드로 빼 저장하고 필요시 마다 불러와 사용한다.
이 정도 이해하면 되었는가? 그런데, 서비스 클래스 사용이 구체적으로 그려지지 않는다.
예시 코드를 보여달라.
예시 코드를 보여달라.
서비스 클래스의 예시는 다음과 같다. 이 예시는 게시판의 게시글 읽기이다.
(1)화면에 게시글 내용이 보여야 하며, (2)게시물을 읽을 때마다 +1이 증가
해야한다.
따라서 DAO 클래스 이용하여 (1)데이터를 select(출력)해주고, (2)읽은 수의
데이터를 Update해준다.
public class ReadArticleService {
public Article read(int articleId)* {
Connection conn = null;
try {
conn = ...// Conneciton 구함
conn.setAutoCommit(false);*
// 기능을 구현하는 데 필요한 DAO를 구한다.
ArticleDao articleDao = ArticleDaoProvider.getInstance().getDao();*
Article article = articleDao.selectById(conn, articleId);
if (article == null) { throw new ArticleNotFoundException(articleId); }
article.increaseReadCount();
articleDao.updateReadCount(conn, article);
conn.commit();*
return article;
} catch (Exception ex) {
JdbcUtil.rollback(conn);
throw new ArticleServiceException("에러 발생:"+ex.getMessage());
} finally {
JdbcUtil.close(conn);
}
}
*ArticleDao articleDao = ArticleDaoProvider.getInstance().getDao();
는 Dao를 사용하기 위해서 선언하는 부분이다. 이 때 싱글톤(ArticleDaoProvider
.getInstance())을 사용했는데, 이는 추후에 설명하겠다.
*conn.setAutoCommit(false);/conn.commit(); 이 부분은 알다시피, 결과를 커밋해주는
부분이다. 만약 예외가 발생한다면 setAutoCommit(false)부분으로 Rollback 해준다.
부분이다. 만약 예외가 발생한다면 setAutoCommit(false)부분으로 Rollback 해준다.
*서비스 클래스의 예외처리는 서비스 클래스의 기능에 알맞게 설정해주는 것이
좋다. 예를 들어,
public Article readArticle(..) throws SQLException { … } 보다는
public Article readArticle(..) throws ArticleNotFoundException { … }이
좋다.
Q. 싱글톤 부분의 설명을 빠트렸다. 싱글톤을 설명해달라.
싱글톤이란 클래스 당 한 개의 객체만 생성되도록 제약하는 구현 패턴 방식이다.
싱글톤을 만들기 위해서는 세 가지가 필요하다.
public class 싱글톤 클래스{
- private 생성자
- (1)번 생성자를 참조하는 private 참조변수 선언 ((3)번에서 사용하기 위해서 만들었다.
- 외부에서 사용가능하게 하기 위한 public static 싱글톤 클래스 타입 getInstance() 메서드
}
싱글톤은 쉽게 말해, 이 클래스는 ‘나만 변경가능 하니 사용하기만 해라!’라는 목적으로 만들어 졌다 할 수 있다.
그러나 본인에게 권한 있다면 책임도 따른다. 싱글톤 클래스는 총대를 매고 혼자 객체를 생성한다. 그러면 다른
메서드나 서비스, Dao 클래스들은 매번 객체를 생성할 필요가 없다.
그러나 본인에게 권한 있다면 책임도 따른다. 싱글톤 클래스는 총대를 매고 혼자 객체를 생성한다. 그러면 다른
메서드나 서비스, Dao 클래스들은 매번 객체를 생성할 필요가 없다.
싱글톤의 예를 들면 이렇다.
public class ReadArticleService {
// 유일한 객체를 정적 필드에 저장
private static ReadArticleService instance = new ReadArticleService();
// 유일한 객체에 접근할 수 있는 정적 메서드 정의
public static ReadArticleService getInstance() {
return instance;
}
// 생성자를 private으로 설정해서 외부에서 접근하지 못함
private ReadArticleService() {}
...
}
댓글 없음:
댓글 쓰기