본문으로 바로가기

스프링[Spring] 게시판 만들기_03

category 언어/Spring 2020. 7. 7. 19:14
728x90

일반적인 웹 프로젝트의 구성


- 영속 계층, 데이터 계층 (Persistence Tier) : 데이터를 어떤 방식으로 보관하고 사용할지 설계하는 영역
-> (우리는) MyBatis Mapper를 이용하기로 함

 

 

- 비즈니스 계층 (Business Tier) : 순수한 비즈니스 로직을 담고 있는 곳 
(고객이 원하는 요구사항을 반영하는 곳) 
-> xxxService라는 이름의 자바 코드로 구현 

 

 

- 화면 계층 (Presentation Tier) : 화면에 보여주는 기술을 사용하는 영역 
-> Servlet/JSP 

 

1. 영속 계층

 

MyBatis Mapper를 이용해 각 테이블의 CRUD를 구현하는 것을
Spring 웹 프로젝트의 영속 계층(Persistence Tier)이라고 한다.

 

CREATE : 새로운 데이터 생성
READ : 저장되어 있는 데이터 읽기
UPDATE : 수정
DELETE : 삭제


어노테이션(@)이 아닌 xml을 이용해서 설정을 주는 방법

이유? 나중에 어노테이션(@)이 길어지면 페이지가 지저분해지기 때문에

 

* 방법

 

패키지 위치와 똑같이 src/main/resources에 아래와 같이 폴더 생성

com->myboard->mapper->MyBoardMapper.xml(파일)

 

 

 

xml 파일에 대한 설정을 위해서는

 

구글에 google -> mybatis 검색 -> mybatis.org에 들어간다.

 

시작하기 탭에서 중간쯤에 위치한

 

 

 

위와 같은 소스를 복사하여 mapper의 namespace 및

id, resultType을 상황에 맞게 수정을 해준다.

 

 

이후, root-context.xml의 Namespaces탭에서 context를 체크해준다.

 

 

이제, MyBoardMapper.java에서 아래와 같이 어노테이션(@)을 주석처리해도

xml문에서 처리했기 때문에

MyBoardTest의 junit 테스트가 잘 처리되는 것을 확인할 수 있다.

 

 

 

 

2. 비즈니스 로직 구현

 

# 비즈니스 계층 (Business Tier)

- 고객의 요구사항을 반영하는 계층
- 데이터 계층에서 구현해놓은 기능을 활용해 비즈니스 로직을 구현한다

 

# 고객의 요구사항 예

EX : 책을 구매하면 회원의 마일리지를 올려주고 싶은 경우

- 책 테이블에 접근해서 책을 구매해야 한다
- 회원 테이블에 접근해서 마일리지를 올려줘야 한다

※ 하나의 비즈니스 로직은 하나 이상의 테이블을 건드리게 될 수 있기 때문에
비즈니스 계층과 데이터 계층의 분리해서 개발하면 훨씬 효율적으로 개발이 진행된다 (거의 국룰된듯)

 

src/main/java에 com.myboard.service라는 패키지를 생성 후 MyBoardService 인터페이스를 생성한다.

 

 

이후, 같은 패키지에 MyBoardServiceImpl라는 자바파일을 생성 후 아래와 같이 MyBoardService 인터페이스를 add 해준다.

 

 

이후 아래와 같이 

@Service로 비즈니스 로직을 구현한 뒤, @Autowired로 mapper를 추가해준다.

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
package com.myboard.service;
 
import java.util.List;
 
import org.apache.log4j.Logger;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
 
import com.myboard.mapper.MyBoardMapper;
import com.myboard.vo.MyBoardVo;
 
 
@Service
public class MyBoardServiceImpl implements MyBoardService {
    
    @Autowired
    private MyBoardMapper mapper;
    
    private Logger log=Logger.getLogger(MyBoardServiceImpl.class);
 
    @Override
    public List<MyBoardVo> getList() {
        log.info("글 목록");
        return mapper.getList();
    }
 
}
 

 

이때, pom.xml에서 <exclusions>에 해당하는 부분을 지워줘야 에러가 발생하지 않는다.

 

 

다음에는 root-context.xml에

<context:component-scan base-package="com.myboard.service"/>

를 추가해준다.

 

이제 마지막으로 테스트를 해보자.

 

src/test/java에 com.myboard.service 패키지를 생성 후, MyBoardServiceTests 자바파일을 생성한다.

 

아래와 같이 @Test를 생성 후 Run as-> Junit test를 해보면 문제없이 잘 작동한다.

 

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
package com.myboard.service;
 
import org.apache.log4j.Logger;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
 
import com.myboard.vo.MyBoardVo;
 
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration("file:src/main/webapp/WEB-INF/spring/root-context.xml")
 
public class MyBoardServiceTests {
 
    private Logger log = Logger.getLogger(MyBoardServiceTests.class);
 
    @Autowired
    private MyBoardService service;
    // MyBoardService가 MyBoardServiceImpl의 상위개념이므로 다음과 같이 사용가능
 
    @Test
    public void testGetList() {
        for (MyBoardVo board : service.getList()) {
            log.info(board);
        }
    }
 
}
 
 

 

3. 화면 계층 

 

src/main/java->com.myboard.controller 패키지에 MyBoardController의 자바 파일을 생성한다.

 

이후 어노테이션으로 컨트롤러 설정 및 매핑에 대한 작업을 아래와 같이 해준다.

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
package com.myboard.controller;
 
import org.apache.log4j.Logger;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
 
import com.myboard.service.MyBoardService;
 
@Controller
@RequestMapping("/board/*")
public class MyBoardController {
    
    @Autowired
    private MyBoardService service;
    
    private Logger log=Logger.getLogger(MyBoardController.class);
    
    
    @GetMapping("/list")
    public void list(Model model) {//model은 request.setAttribute와 동일
        model.addAttribute("list",service.getList());
    }
 
}
 

 

이제는 매핑을 통해 이동하게 되는 list.jsp에 대한 부분을 수정해야 한다.

 

views 폴더 아래에 @RequestMapping("/board/*")으로 처리했으므로 board 폴더를 만들고 그 아래 

@GetMapping("/list")에 대한 list.jsp 파일을 만든다.

 

이때, list.jsp 파일을 GetMapping으로 만드는 이유는 select문으로 조회하는 정보를 보여주는 화면이기 때문이다.

 

* Get vs Post 방식

 

GET 방식 : 어떠한 정보를 가져와서 조회하기 위해서 사용되는 방식

POST 방식 : 데이터를 서버로 제출하여 추가 또는 수정하기 위해서 사용하는 방식

 

이제, 아래와 같은 경로에 list.jsp 파일을 생성한 뒤, 이동해보자.

 

 

먼저 list의 목록을 반복문을 통해 출력하기 위해, <c:forEach> 태그를 활용한다.

 

<c:foreach var="for문 내부에서 사용할 변수"

              items="${리스트가 받아올 배열이름}" 
              varStatus="상태용 변수">

 

그리고, 이때 jstl에 대한 라이브러리를 추가해줘야 한다.

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

 

완성된 list.jsp는 아래와 같이 작성하였다.

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
    
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>
</head>
<body>

<h3>List Page</h3>

<c:forEach var="board" items="${list}" varStatus="status">
    <h5><c:out value="${board }"/></h5>
</c:forEach> 

</body>
</html>

 

MVC 패턴을 통해 추후에 수정에 유리하도록 하기 위해

server.xml의 path 부분에서 아래와 같이 controller를 지워준다.

이렇게 설정하면 url 이동시 controller입력없이 이동할 수 있게 된다.

 

<Context docBase="MyBoard" path="/" reloadable="true" source="org.eclipse.jst.jee.server:MyBoard"/></Host>

 

서버를 실행했을 때 아래와 같은 에러가 발생했는데, 이는

ERROR: com.zaxxer.hikari.HikariConfig - Failed to load driver class oracle.jdbc.driver.OracleDriver from HikariConfig class classloader ParallelWebappClassLoader
  context: ROOT
  delegate: false
----------> Parent Classloader:
java.net.URLClassLoader@5a07e868

 

 

프로젝트 우클릭 -> Deployment Assembly에서 Maven Dependencies 클릭->Add

->Java Build Path Entries->ojdbc8.jar 클릭을 통해 해결하였다.

 

 

 

 

 

이제, Run as->Run on server를 실행 후, 아까 설정했던 url인 http://localhost:8080/board/list로 이동해보면

 

아래와 같이 데이터가 웹 페이지 상에 출력된다.

 

728x90