EL태그 정리
- == : eq(equal)
- != : ne(not equal)
- < : lt(less than)
- > : gt(greater than)
- <= : le(less equal)
- >= : ge(greater equal)
list.jsp
<%@ page language="java" contentType="text/html; charset=UTF-8"%>
<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
<!DOCTYPE html>
<html>
<head>
<script type="text/javascript" src="/resources/js/jquery.min.js"></script>
<title>도서목록</title>
<script type="text/javascript">
$(function(){
$("#selCategory").on("change",function(){
$("#searchForm").submit();
})
$("input[type='reset']").on("click",function(){
window.location.href ="/list";
})
})
</script>
</head>
<body>
<h1>책 목록</h1>
<div>
<!--
요청URI : /list?category=드라마
요청파라미터 : category=드라마
요청방식 : get
URI 파라미터
param : category=드라마
param.category : 드라마
-->
<!-- <form id="searchForm" action="/list" method="get"> -->
<form id="searchForm">
<label for="selCategory">카테고리</label>
<select id="selCategory" name="category">
<option disabled="disabled" selected="selected">선택해주세요</option>
<c:forEach var="category" items="${categories}">
<option value="${category.CATEGORY}"
<c:if test="${param.category==category.CATEGORY}">selected</c:if>
>${category.CATEGORY}</option>
</c:forEach>
</select>
<br/><br/>
<label for="selGubun">제목/가격</label>
<select id="selGubun" name="gubun">
<option disabled="disabled" selected="selected">선택해주세요</option>
<option value="title"
<c:if test="${param.gubun=='title'}">selected</c:if> <%--GET방식으로 페이지가 이동되기 때문에 이동될때 저장될 목적--%>
>제목</option>
<option value="price"
<c:if test="${param.gubun=='price'}">selected</c:if>
>가격</option>
</select>
<input type="text" id="keyword" name="keyword" placeholder="검색어를 입력해주세요" value="${param.keyword}"/>
<br/><br/>
<input type="submit" value="검색">
<input type="reset" value="초기화">
</form>
</div>
<br>
<!--
forEach 태그? 배열(String[], int[][]), Collection(List, Set) 또는
Map(HashTable, HashMap, SortedMap)에 저장되어 있는 값들을
순차적으로 처리할 때 사용함. 자바의 for, do~while을 대신해서 사용함
var : 변수
items : 아이템(배열, Collection, Map)
varStatus : 루프 정보를 담은 객체 활용
- index : 루프 실행 시 현재 인덱스(0부터 시작)
- count : 실행 회수(1부터 시작. 보통 행번호 출력)
-->
<table border="1">
<thead>
<tr>
<th>번호</th>
<th>제목</th>
<th>카테고리</th>
<th>가격</th>
</tr>
</thead>
<tbody>
<c:forEach var="bookVO" items="${BookVOList}" varStatus="stat">
<tr>
<td>${bookVO.rnum}</td>
<td><a href="/detail?bookId=${bookVO.bookId}">${bookVO.title}</a></td>
<td>${bookVO.category}</td>
<td>${bookVO.price}</td>
</tr>
</c:forEach>
</tbody>
</table>
</body>
</html>
java에서 페이지 처리하지 않고 list에서 작성 할 경우
<!-- EL태그 정리
== : eq(equal)
!= : ne(not equal)
< : lt(less than)
> : gt(greater than)
<= : le(less equal)
>= : ge(greater equal)
-->
<p>${articlePage.startPage} to ${articlePage.endPage}</p>
<!-- startPage가 5보다 클 때에만 [이전] 활성화 -->
<c:if test="${articlePage.startPage gt 5}">
<a href="/list?currentPage=${articlePage.startPage-5}&keyword=${articlePage.keyword}&gubun=${articlePage.gubun}">[이전]</a>
</c:if>
<c:forEach var="pNo" begin="${articlePage.startPage}"
end="${articlePage.endPage}">
<a href="/list?currentPage=${pNo}&keyword=${articlePage.keyword}&gubun=${articlePage.gubun}">[${pNo}]</a>
</c:forEach>
<!-- endPage < totalPages일때만 [다음]활성 -->
<c:if test="${articlePage.endPage lt articlePage.totalPages}">
<a href="/list?currentPage=${articlePage.startPage+5}&keyword=${articlePage.keyword}&gubun=${articlePage.gubun}">[다음]</a>
</c:if>
BookController.java
@RequestParam(value="name",required=false,defaultValue="") String name,
required 필수설정 - false인 경우 필수가 아님
defaultValue="" 값이 없을 시 들어갈 기본 값
package kr.or.ddit.controller;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.servlet.ModelAndView;
import kr.or.ddit.service.BookService;
import kr.or.ddit.vo.BookVO;
import lombok.extern.slf4j.Slf4j;
/*
Controller 어노테이션
스프링 프레임워크에게 "이 클래스는 웹 브라우저의 요청(request)를
받아들이는 컨트롤러야" 라고 알려주는 것임.
스프링은 servlet-context.xml의 context:component-scan의 설정에 의해
이 클래스를 자바빈 객체로 등록(메모리에 바인딩).
*/
@Slf4j
@Controller
public class BookController {
@Autowired
BookService bookService;
// 책 입력 화면
/*
요청URI : /create
요청파라미터 : 없음
요청방식 : get
*/
/*
method 속성은 http 요청 메소드를 의미함. 일반적인 웹 페이지 개발에서 GEt 메소드는
데이터를 변경하지 않는 경우에, POST 메소드는 데이터가 변경될 경우 사용
책 생성 화면은 웹 브라우저에 화면을 보여줄 뿐 데이터의 변경이 일어나지 않으므로
GET 메소드를 사용함
*/
@RequestMapping(value="/create", method=RequestMethod.GET)
public ModelAndView create() {
/*
ModelAndView
1) Model : Controller가 반환할 데이터(String, int, List, Map, VO..)를 담당
2) View : 화면을 담당(뷰(View : JSP)의 경로)
*/
ModelAndView mav = new ModelAndView();
// <beans:property name="prefix" value="/WEB-INF/views/" />
// <beans:property name="suffix" value=".jsp" />
// prefix(접두어) : /WEB-INF/views/
// suffix(접미어) : .jsp
// /WEB-INF/views/ + book/create + .jsp
mav.setViewName("book/create");
//forwarding
return mav;
}
// 목록
/*
* 카테고리 선택 요청
* 요청URI : /list?category=드라마
* /list?category=그림책&gubun=title&keyword=제목
* 요청파라미터 : category=드라마
* 요청방식 : get
*
* @RequestParam(value="category",required=false,defaultValue="") String category
* required : 필수 설정
* defaultValue : 기본값 설정 (null 예외 처리)
*/
@RequestMapping(value="/list", method=RequestMethod.GET)
public ModelAndView list(ModelAndView mav,
@RequestParam(value="category",required=false,defaultValue="") String category, // required 필수설정 false인 경우 필수가 아님
@RequestParam(value="gubun", required=false,defaultValue="") String gubun,
@RequestParam(value="keyword", required=false,defaultValue="") String keyword
) {
Map<String,Object> map = new HashMap<>();
map.put("category", category);
map.put("gubun", gubun);
map.put("keyword", keyword);
log.info("map : "+map);
List<BookVO> BookVOList = this.bookService.list(map);
mav.addObject("BookVOList", BookVOList);
log.info("BookVOList : "+BookVOList);
List<Map<String,Object>> categories = this.bookService.getCategories();
mav.addObject("categories", categories);
log.info("categories : "+categories);
mav.setViewName("book/list");
return mav;
}
/*
Spring에서 파라미터 명과 매개변수 명이 같으면 파라미터 값이 매개변수 값으로 할당됨
모든 파라미터는 문자. 그래서 price의 값도 숫자형 문자이다
*/
@RequestMapping(value="/createPost", method=RequestMethod.POST)
public ModelAndView createPost(String title, String category, String price, BookVO vo) {
log.info("title : "+title);
log.info("category : "+category);
log.info("price : "+price);
log.info("vo : "+vo);
/*
| 프리젠테이션 계층 | 서비스 계층 | 퍼시스턴스 계층 |
*Controller
뷰(JSP) -> Controller클래스 -> Service인터페이스
*Service *Repository
-> ServiceImpl클래스 -> DAO클래스 -> 매퍼XML -> DB
*/
// 테이블에 도서를 등록
int result = this.bookService.createPost(vo);
System.out.println("createPost -> result : "+result);
ModelAndView mav = new ModelAndView();
mav.setViewName("redirect: /list");
return mav;
}
@RequestMapping(value="/detail", method=RequestMethod.GET)
public ModelAndView detail(BookVO vo) {
ModelAndView mav = new ModelAndView();
mav.setViewName("book/detail");
log.info("vo : "+vo);
vo = this.bookService.detail(vo);
//Model : 데이터
mav.addObject("vo", vo);
//forwarding
return mav;
}
@RequestMapping(value="/update", method=RequestMethod.POST)
public ModelAndView update(BookVO vo) {
ModelAndView mav = new ModelAndView();
mav.setViewName("redirect:/detail?bookId="+vo.getBookId());
log.info("vo : "+vo);
int result = this.bookService.update(vo);
//forwarding
return mav;
}
@RequestMapping(value="/delete", method=RequestMethod.GET)
public ModelAndView delete(BookVO vo) {
ModelAndView mav = new ModelAndView();
mav.setViewName("redirect:/list");
int result = this.bookService.delete(vo);
//forwarding
return mav;
}
}
book_SQL.xml
map으로 받을 경우 parameterType는 hashMap으로 할 것
ROW_NUMBER() OVER(ORDER BY BOOK_ID DESC) RNUM
- ROW_NUMBER()
- 결과 집합의 각 행에 대해 고유한 순번을 부여
- 이 순번은 특정 기준에 따라 정렬
- OVER()
- 적용범위를 정의
- 어떠한 기준으로 순번을 매길 것인지를 설정
- RNUM
- 별칭
<if test="조건">
- <choose>
- <when test="조건">
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="book">
<insert id="createPost" parameterType="bookVo">
<selectKey resultType="int" order="BEFORE" keyProperty="bookId">
select nvl(max(book_id),0)+1 from book
</selectKey>
insert into book(BOOK_ID, TITLE, CATEGORY, PRICE, INSERT_DATE)
values(#{bookId}, #{title}, #{category}, #{price}, SYSDATE)
</insert>
<!-- 도서 목록
return this.sqlSessionTemplate.selectList("book.list",map);
//1) map{"category":"소설","gubun":"","keyword":"127"}
//2) map{"category":"","gubun":"title","keyword":"127"}
//3) map{"category":"소설","gubun":"price","keyword":"127"}
-->
<select id="list" parameterType="hashMap" resultType="bookVO">
SELECT ROW_NUMBER() OVER(ORDER BY BOOK_ID DESC) RNUM
, BOOK_ID, TITLE, CATEGORY, PRICE, INSERT_DATE
FROM BOOK
WHERE 1 = 1
<if test="category!=null and category!=''">
AND CATEGORY = #{category}
</if>
<if test="gubun!=null and gubun!=''">
<choose>
<when test="gubun=='title'">
AND TITLE LIKE '%' || #{keyword} || '%'
</when>
<when test="gubun=='price'">
AND TO_CHAR(PRICE) = #{keyword}
</when>
</choose>
</if>
<!-- 드모르간 정리
A' . B'
의 반대는
A + B
-->
<if test="gubun==null or gubun==''">
AND (
TITLE LIKE '%' || #{keyword} || '%'
OR TO_CHAR(PRICE) = #{keyword}
)
</if>
</select>
<!-- 카테고리 목록 -->
<select id="getCategories" resultType="hashMap">
SELECT DISTINCT CATEGORY
FROM BOOK
ORDER BY 1
</select>
<select id="detail" resultType="bookVo" parameterType="bookVo">
select *
from book
where book_id = #{bookId}
</select>
<update id="update" parameterType="bookVo">
update book
set title=#{title},
category=#{category},
price=#{price}
where book_id = #{bookId}
</update>
<delete id="delete" parameterType="bookVo">
delete book
where book_id = #{bookId}
</delete>
</mapper>
'Spring' 카테고리의 다른 글
[Spring] jdbc_board crud 2 - 검색조건, 페이징 (0) | 2024.07.25 |
---|---|
[Spring] lprod crud 2 - 검색조건 + 페이징 처리 (1) | 2024.07.25 |
[Spring] 게시판 CRUD (0) | 2024.07.22 |
[Spring] lprod CRUD (0) | 2024.07.22 |
[Spring] 애노테이션 Annotation (0) | 2024.07.22 |