스프링 2주차 정리

선장원·2021년 12월 5일
1

Spring

목록 보기
12/16

2주차 (11/29~12/03)

postman / Spring( ajax / c태그 / 페이징 / 검색 등등)

postman

테스트를 도와주는 프로그램

workspace에서
1. 탭을 만들고
2. 주소를 치고
3. 값을 입력하고
4. 보낸다
5. 그럼 밑에 결과가 나온다

아직이걸 왜 쓰는지 잘 모르겠는뎅

Spring

@Autowired

객체를 생성했다가 지웠다가 하는게 아니라
@Autowired를 설정해두면 스프링이 해당 클래스를 객체로 생성해서 자기가 가지고 있다가
호출 될때마다 빼서 쓰고 다시 넣는다 이런 느낌??????

로그인 정보 유지하기

서버가 돌고 있을 때 로그인 정보를 유지 시키기
세션session객체

  • 브라우저를 모두 종료하거나 서버를 내리기 전까지 세션객체에 저장된 데이터는 계속 유지 된다.
  • 일반 model에 담은 데이터는 페이지가 변경되거나 새로운 주소를 요청하게 되면 사진다
    • model.addAttribute를 통해 담은 데이터는 request객체에 담기는 것
  • 세션에는 최소한의 필수정보만 저장(로그인정보)

로그인 정보 지우기

홈컨트롤으로 주소를 보내서 홈컨트롤에서 지워야한다

invalidate();
세션에 담겨있는 데이터를 다 지운다
다시 인덱스로

ajax로 하긴 좀 그런가
그럼 로그아웃을 하면 다시 해당 페이지로 이동하게 만드려면 로그아웃 메서드에 해당 페이지를 파라미터에 담아서 보내야 하는건가

파라미터 활용

수정 작업이 끝나면 detail으로 이동해서 해당 넘버의 상세페이지를 확인하게 주소에 파라미터를 넣어서 detail으로 간다.

ajax

asynchronous javascript and xml
비동기 처리방식

화면이 바뀌지 않고도 db를 다녀올 수 있다

ex) 아이디 중복체크

	function idDuplicate(){
		const id = document.getElementById('m_id').value;
		console.log(id);
		
		const checkResult =document.getElementById('id_dup_check')
		$.ajax({
			type: 'post', // 전송방식(get, post, delete, put등)
			url: 'idDuplicate', // 요청주소(컨트롤러로 요청하는 주속)
			data: {'m_id': id}, // 전송할 데이터 자바스크립트의객체표현방식
			dataType:'text', //요청후 리턴받을 때의 데이터 형식
			success: function(result){ // 요청이 성공적으로 처리 됐을 때 실행할 함수
				console.log('ajax성공');
				console.log(result);
				if (result=="ok"){
					checkResult.style.color = 'green';
					checkResult.innerHTML = '멋진 아이디에요!'
				} else{
					checkResult.style.color = 'red';
					checkResult.innerHTML = '사용중이에요!'
				}
					
			},
			error: function(){ // 요청이 실패했을 때 실행할 함수
				console.log('오타를 찾으세요');
			}
		});
	}

type : ‘post’ // 전송방식(get, post, delete, put등)
url : ‘idDuplicate’ // 요청주소(컨트롤러에 요청하는 주소) a태그의 href내용
data : {파라미터이름:파라미터데이터} // 전송할 데이터 자바스크립트의 객체표현방식
dataType : ‘text’ //요청후 리턴받을 때 의 데이터 형식 (DTO형식은 json형식으로 받는다)
success : function(result){ // 요청이 성공했을 때
result 는 컨트롤러에서 값을 보내주는 것
},
error: function(){ // 요청이 실패 했을 때
오타, 홈컨트롤러 문제
}

json

JSON은 속성-값 쌍 또는 "키-값 쌍"으로 이루어진 데이터 오브젝트를 전달하기 위해 인간이 읽을 수 있는 텍스트를 사용하는 개방형 표준 포맷이다. 비동기 브라우저/서버 통신 을 위해, 넓게는 XML을 대체하는 주요 데이터 포맷이다.
이라고 구글이 알려준다
한마디로 키-값 두가지로 나눠서 받아주는 아주 고마운 친구

@ResponseBody

홈컨트롤러 메소드 앞에 써준다
리퀘스트가 아니라 리스폰으로 페이지를 이동하지 않고 사용할 때 사용

ajax를 사용하는 메서드에서 사용

자바 스크립트로 form태그 서밋하기

form태그에 name속성값을 정하고
자바스크립트에서
name값.submit();
으로 하면 위의 코드가 모두 실행 되고 서밋으로 보내준다

주소에 패키지 이름 지우기

서버폴더의 server.xml파일 맨밑에

jsp파일 관리하기

views폴더 안에 폴더(/board)를 만들고 @RequestMapping의 value의 값에 /board를 추가해주고
리턴값에 board/를 추가해준다

@RequestMapping을 클래스 위에 써서 해당 클래스 안에 있는 모든 주소에 value값을 추가해준다

페이징

상수 선언

일단 상수를 선언한다

	private static final int PAGE_LIMIT = 3; // 한페이지에 보여질 글 개수 
	private static final int BLOCK_LIMIT = 3; // 한화면에 보여질 페이지 개수

위 값을 paging메서드와 pagingList메서드에서 사용한다

쇼핑몰에서 사용하는 것처럼 20개씩보기, 40개씩 보기를 하려면 상수말고 변수로 지정을 해야하는건가?

PageDTO

PageDTO를 만들고

	private int page;
	private int maxPage;
	private int startPage;
	private int endPage;

PageDTO에 값을 담는 메서드인 paging메서드를 실행하고(컨트롤러에서)
page에 현재 페이지 값
max페이지에 최대 페이지값
strart페이지에 처음나오는 페이지 값(3개씩 나온다고 하면 1,4,7,10~~)
end페이지에 마지막 페이지

페이징 메소드

이거는 페이지를 구하는 메소드

	public PageDTO paging(int page) {
		int boardCount = br.boardCount(); // 필요한 총 글 갯수
		// 전체페이지 계산
		int maxPage = (int)(Math.ceil((double)boardCount / PAGE_LIMIT)); // ceil() : 소수점이 붙으면 값을 올려준다
		// 2페이지를 요청했을 때 1페이지, 4페이지를 요청했을 때 4페이지, 8페이지를 요청했을 때 7페이지
		// 1, 2, 3 >> 1
		// 4, 5, 6 >> 4
		// 7, 8, 9 >> 7
		int startPage = (((int)(Math.ceil((double)page / BLOCK_LIMIT))) - 1) * BLOCK_LIMIT + 1; // BLOCK_LIMIT은 페이지에 보이는 페이지수 
		int endPage = startPage + BLOCK_LIMIT - 1;
		if(endPage > maxPage)
			endPage = maxPage; 
		PageDTO paging = new PageDTO();
		paging.setPage(page);
		paging.setStartPage(startPage);
		paging.setEndPage(endPage);
		paging.setMaxPage(maxPage);
		
		System.out.println("paging.toString(): "+ paging.toString());
		
		return paging;
	}

count 메서드를 실행해서 총 글의 갯수를 가져오고
그 값을 이용해서 총 페이지 수와 스타트 페이지 엔드페이지를 구한다

ceil()

자바의 math기능 중에 cail은 소수점이 있으면 값을 올림해준다.

페이징 리스트 메소드

이거는 페이지안의 글의 갯수와 글을 가져오는 메소드

paging메서드를 구하고 pagingList메서드를 실행해서 출력할 글을 가져온다

Map을 선언해서 limit에서 사용할 처음 글과 글의 갯수를 입력한다

리스트에 담아오기 위해 맵을 만든 것을 맵퍼로 보내서 sql 문법을 사용한다

limit

글을 가져올 때 처음 글을 정하고 몇개를 가져올 것인가를 정한다
select * from 테이블명 limit 처음글, 글의갯수

페이징 리스트 메소드는 설명하기 힘드네

컨트롤러

	@RequestMapping(value="paging", method=RequestMethod.GET)
	// value는 파라미터이름 , required는 필수 여부
	public String paging(@RequestParam(value="page", required=false, defaultValue="1")int page, Model model) {
		PageDTO paging = bs.paging(page);
		List<BoardDTO> boardList = bs.pagingList(page);
		model.addAttribute("bList", boardList);
		model.addAttribute("paging", paging);
		return "board/findAll";
	}

서비스

	private static final int PAGE_LIMIT = 3; // 한페이지에 보여질 글 개수 
	private static final int BLOCK_LIMIT = 3; // 한화면에 보여질 페이지 개수


	public List<BoardDTO> pagingList(int page) {
		// TODO Auto-generated method stub
		// 1페이지 limit 0,3 / 2페이지 3,3 / 3페이지 6,3
		int pagingStart = (page-1) * PAGE_LIMIT;
		Map<String, Integer> pagingParam = new HashMap<String, Integer>();
		pagingParam.put("start", pagingStart);
		pagingParam.put("limit", PAGE_LIMIT);
//		List<BoardDTO> pagingList = br.pagingList(pagingStart);
		List<BoardDTO> pagingList = br.pagingList1(pagingParam);
		for(BoardDTO b: pagingList) {
			System.out.println(b.toString());
		}
		return pagingList;
	}

	// 필요한 총 페이지 갯수 계산
	// 현재 사용자가 요청한 페이지가 2페이지라면 화면에는 1,2,3을 보여주고
	// 요청 페이지가 6페이지라면 화면에 4,5,6을 보여준다
	// 요청페이지가 7페이지라면 7을 보여준다
	public PageDTO paging(int page) {
		int boardCount = br.boardCount(); // 필요한 총 글 갯수
		// 전체페이지 계산
		int maxPage = (int)(Math.ceil((double)boardCount / PAGE_LIMIT)); // ceil() : 소수점이 붙으면 값을 올려준다
		// 2페이지를 요청했을 때 1페이지, 4페이지를 요청했을 때 4페이지, 8페이지를 요청했을 때 7페이지
		// 1, 2, 3 >> 1
		// 4, 5, 6 >> 4
		// 7, 8, 9 >> 7
		int startPage = (((int)(Math.ceil((double)page / BLOCK_LIMIT))) - 1) * BLOCK_LIMIT + 1; // BLOCK_LIMIT은 페이지에 보이는 페이지수 
		int endPage = startPage + BLOCK_LIMIT - 1;
		if(endPage > maxPage)
			endPage = maxPage; 
		PageDTO paging = new PageDTO();
		paging.setPage(page);
		paging.setStartPage(startPage);
		paging.setEndPage(endPage);
		paging.setMaxPage(maxPage);
		
		System.out.println("paging.toString(): "+ paging.toString());
		
		return paging;
	}

리퍼지토리

	public int boardCount() {
		return sql.selectOne("board.count");
	}
	
	public List<BoardDTO> pagingList(int pagingStart) {
		return sql.selectList("board.pagingList", pagingStart);
	}

	public List<BoardDTO> pagingList1(Map<String, Integer> pagingParam) {
		return sql.selectList("board.pagingList1", pagingParam);
	}

맵퍼

		<select id="pagingList" parameterType="int" resultType="bdto">
		select * from board order by b_number desc limit #{pagingStart}, 3
	</select>
	
	<select id="pagingList1" parameterType="java.util.HashMap" resultType="bdto">
		select * from board order by b_number desc limit #{start}, #{limit}
	</select>
	
	<select id="count" resultType="int">
		select count(b_number) from board
	</select>

jsp

	<div>
		<c:choose>
			<c:when test="${paging.page<=1}">
				[이전]&nbsp;
			</c:when>
			<c:otherwise>
				<!-- 현재 페이지에서 1감소한 페이지 요청하는 링크 -->
				<a href="/board/paging?page=${paging.page-1}">[이전]</a>&nbsp;
			</c:otherwise>
		</c:choose>

		<!-- for(int i = startPage; i<=endPage; i++)같은 느낌이다 -->
		<c:forEach begin="${paging.startPage}" end="${paging.endPage}" var="i"
			step="1">
			<c:choose>
				<c:when test="${i eq paging.page}">
					${i}
				</c:when>
				<c:otherwise>
					<a href="/board/paging?page=${i}">${i}</a>
				</c:otherwise>
			</c:choose>
		</c:forEach>

		<c:choose>
			<c:when test="${paging.page>=paging.maxPage}">
				[다음]
			</c:when>
			<c:otherwise>
				<a href="/board/paging?page=${paging.page+1}">[다음]</a>
			</c:otherwise>
		</c:choose>
	</div>

jsp부분을 안 넣었었군

페이지 유지

내가 페이지를 돌아다니다가 들어갓다가 목록을 눌렀을 때 다시 내가 봤던 페이지로 가기 위해 페이지 숫자를 파라미터에 담아서 다시 사용한다

대부분 목록 말고 뒤로가기를 누르지 않나?
새창으로 들어가거나...?
많은 사람들이 있으니 여러 방법을 쓰는 것도 좋지

검색 기능

나는 검색창에 자동완성으로 뜨는 것 만들고 싶었는데
그거는 아직 힘들어 보인다 ㅠㅠ

findAll에 form태그를 사용해서
searchtype과 keyword를 받는다

searchtype과 keyword를 서비스로 보내서
서비스에서 맵Map를 만들어서 담는다

나는 DTO에 담아서 보냈었는데

맵을 리퍼지토리로 보내서
sql문법을 이용해서 리스트에 담아온다

like연산자와 concat을 사용해서 검색어가 들어간 글을 리스트에 담아온다!

concat

스프링에서 사용하기 위해 단어를 합쳐주는 용도??
select * from 테이블 where 컬럼명 like concat(‘%’, ‘#{으갸갸갸갸}’, ‘%’)를 쓰면
‘%으갸갸갸갸%’로 만들어주는 용도인가

컨트롤러

	@RequestMapping(value="search", method = RequestMethod.GET)
	public String search(@RequestParam("searchtype") String searchtype, @RequestParam("keyword") String keyword, Model model) {
		List<BoardDTO> bList = bs.search(searchtype,keyword);
		model.addAttribute("bList", bList);
		return "board/findAll";
	}

서비스

	public List<BoardDTO> search(String searchtype, String keyword) {
		Map<String, String> searchParam = new HashMap<String, String>();
		searchParam.put("type", searchtype);
		searchParam.put("word", keyword);
		return br.search(searchParam);
	}

리퍼지토리

	public List<BoardDTO> search(Map<String, String> searchParam) {
		
		return sql.selectList("board.search", searchParam);
	}

맵퍼

	<select id="pagingList1" parameterType="java.util.HashMap" resultType="bdto">
		select * from board order by b_number desc limit #{start}, #{limit}
	</select>
	
	<select id="count" resultType="int">
		select count(b_number) from board
	</select>
	
	<!-- <select id="search" parameterType="java.util.HashMap" resultType="bdto">
		select * from board where ${type} like concat('%', #{word}, '%')	
	</select> -->
	<select id="search" parameterType="java.util.HashMap" resultType="bdto">
		select * from board 			
		<include refid="sear"></include>
	</select>
	
	<sql id="sear">
		<choose>
			<when test="type=='b_title'">
				where b_title like concat('%', #{word}, '%') 
			</when>
			<when test="type=='b_writer'">
				where b_writer like concat('%', #{word}, '%') 
			</when>
		</choose>
	</sql>

맵퍼에서 사용하는 방식은 두가지 방식이 있다

컬럼 부분을 가져오려면 #{}이 아니라 ${}를 사용해야한다

include

mybatis에서 사용하는 if문 같은 느낌

c태그

위에서 사용한 c태그들을 모아 봅시다

관리자만 보이게


위 c태그를 사용하면 해당 조건을 만족해야지만 보이게 설정 할 수 있다

관리자 페이지로 이동하게 만들거나 해당 ID가 만든 게시글만 수정할 수 있게

choose

c태그의 if문같은 느낌으로 html에서 if문을 쓰게 해주는 기능

test="" : 이 부분이 if()의 괄호의 기능

when

if()를 when test=""으로 쓰고

otherwise

이건 else같은 느낌이다

when을 여러 개를 써서 위에서 부터 순서대로 내려오는 건가?

forEach

html에서 for문을 사용하기 위해 쓰는 c태그의 기능이다

그외

Timestamp

import java.sql.Timestamp;

date 타입은 시간과 분 초를 못해서 타임스탬프 타입을 사용한다

타임스탬프 타입을 하고 root-context에서 sql의 serverTimezone을 Asia/Seoul으로 바꿔줘야 한다

profile
코딩도전기

0개의 댓글