๐Ÿ’ป ์ฝ”๋”ฉ ์ผ๊ธฐ : [Spring] 'ํšŒ์›๊ฐ€์ž… ๋งŒ๋“ค๊ธฐ- ๋ถ€๊ฐ€๊ธฐ๋Šฅ' ํŽธ

ybkยท2024๋…„ 5์›” 2์ผ

spring

๋ชฉ๋ก ๋ณด๊ธฐ
25/55
post-thumbnail

๐Ÿ”” 'ํšŒ์›๊ฐ€์ž… ์‹œ ํ•„์š”ํ•œ ๋ถ€๊ฐ€๊ธฐ๋Šฅ'์— ๋Œ€ํ•ด์„œ ์•Œ์•„๋ณด์ž!


๐Ÿ’Ÿ ๋ชฉ๋ก ๋ฒˆํ˜ธ ์—ญ์ˆœ

1. JSTL ํ•จ์ˆ˜ ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ๋ฅผ ์„ ์–ธํ•ฉ๋‹ˆ๋‹ค.

<%@ taglib prefix="fn" uri="http://java.sun.com/jsp/jstl/functions" %>
  1. <c:forEach> ํƒœ๊ทธ์—์„œ varStatus๋ฅผ ์‚ฌ์šฉํ•ฉ๋‹ˆ๋‹ค. varStatus์˜ ์†์„ฑ์€ index, count, first, last ๋“ฑ์ด ์žˆ์Šต๋‹ˆ๋‹ค.
<c:forEach items="${memberList}" var="member" varStatus="status">
  1. fn:length() ํ•จ์ˆ˜๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ memberList์˜ ๊ธธ์ด๋ฅผ ๊ตฌํ•˜๊ณ , ์ด๋ฅผ ์ด์šฉํ•˜์—ฌ ๋ฒˆํ˜ธ๋ฅผ ์—ญ์ˆœ์œผ๋กœ ๋งŒ๋“ญ๋‹ˆ๋‹ค. ๋ฒˆํ˜ธ๋ฅผ ์—ญ์ˆœ์œผ๋กœ ๋งŒ๋“œ๋Š” ๋ฐฉ๋ฒ•์€ ๋ฆฌ์ŠคํŠธ์˜ ์ „์ฒด ๊ธธ์ด์—์„œ ์ธ๋ฑ์Šค 0๋ถ€ํ„ฐ ๋นผ์ฃผ๋ฉด ๋ฒˆํ˜ธ๊ฐ€ ์—ญ์ˆœ์œผ๋กœ ๋‚˜์˜ต๋‹ˆ๋‹ค.
<%-- ์ธ๋ฑ์Šค๋ฅผ ์ด์šฉํ•˜์—ฌ ๋ฒˆํ˜ธ๋ฅผ ์—ญ์ˆœ์œผ๋กœ ๋งŒ๋“ญ๋‹ˆ๋‹ค --%>
<c:set var="reverseIndex" value="${fn:length(memberList) - status.index}" />
  1. ํŽ˜์ด์ง€ ์ฒ˜๋ฆฌ ํ•˜๊ธฐ ์ „๊นŒ์ง€์˜ ์ฝ”๋“œ๋Š” ๋‹ค์Œ๊ณผ ๊ฐ™์Šต๋‹ˆ๋‹ค.
<c:forEach items="${memberList}" var="member" varStatus="status">
	~~~~
        <td style="color: blue">
                ${fn:length(memberList)-status.index}
        </td>
	~~
</c:forEach>
  1. ํŽ˜์ด์ง€ ์ฒ˜๋ฆฌ ํ•˜๊ธฐ ํ›„์—๋Š” JSTL ํ•จ์ˆ˜ ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ ์„ ์–ธ์—†์ด ๊ณต์‹์„ ์ด์šฉํ•˜๋ฉด ๋ฉ๋‹ˆ๋‹ค.

    ${์ „์ฒด ๊ฒŒ์‹œ๊ธ€ ์ˆ˜ - (ํ˜„์žฌ ํŽ˜์ด์ง€-1) * ํŽ˜์ด์ง€๋‹น ๋ณด์—ฌ์ง€๋Š” ๊ฒŒ์‹œ๋ฌผ์ˆ˜(10) - status.index}

    • ์ „์ฒด ๊ฒŒ์‹œ๊ธ€ ์ˆ˜ , ํ˜„์žฌ ํŽ˜์ด์ง€๋Š” ๋ชจ๋‘ ์ปจํŠธ๋กค๋Ÿฌ์—์„œ model์— ์ถ”๊ฐ€ํ•˜์—ฌ ๊ฐ€์ ธ์™€์•ผ ํ•ฉ๋‹ˆ๋‹ค.
<c:forEach items="${memberList}" var="member" varStatus="status">
	~~~~
        <td style="color:blue;">
          	${(pageInfo.numberOfBoard)- (pageInfo.currentPageNumber-1) * 10 - status.index}
  		</td>
	~~
</c:forEach>
  • ์ค‘๊ฐ„์— ๊ฒŒ์‹œ๊ธ€์ด ์‚ญ์ œ๋˜์–ด๋„ ์ค‘๊ฐ„ ๋ฒˆํ˜ธ๊ฐ€ ์ƒ๋žต๋˜์ง€ ์•Š๊ณ  ์—ญ์ˆœ์œผ๋กœ ์ •๋ ฌ๋ฉ๋‹ˆ๋‹ค.



๐Ÿ’Ÿ ํ…Œ์ด๋ธ” ํ–‰ ํด๋ฆญ ์‹œ ํ•ด๋‹น ํšŒ์› ์ •๋ณด ๋ณด์—ฌ์ฃผ๊ธฐ

tr ํƒœ๊ทธ์˜ onclick ์†์„ฑ์„ ์‚ฌ์šฉํ•˜์—ฌ ํ•ด๋‹น ํšŒ์› ์ •๋ณด ๋งํฌ๋ฅผ ์ž…๋ ฅํ•ด์ค๋‹ˆ๋‹ค.

<tr onclick="location.href='ํšŒ์› ์ •๋ณด ๋งํฌ'">

ํ–‰ ํด๋ฆญ ์‹œ /member/id=?๋กœ ์ด๋™ํ•ฉ๋‹ˆ๋‹ค.

<c:url value="/member" var="viewMember">
    <c:param name="id" value="${member.id}"/>
</c:url>
<tr onclick="location.href='${viewMember}'">

๐Ÿ’Ÿ ๋น„๋ฐ€๋ฒˆํ˜ธ ์ฒดํฌ

- submit ๋ฒ„ํŠผ ํด๋ฆญ ์‹œ ๋น„๋ฐ€๋ฒˆํ˜ธ ์ฒดํฌ

<form ~token tag"><script>
    function checkValues() {
        const password = document.getElementById("pwdInput").value;
        const passwordCheck = document.getElementById("pwdCheckInput").value;

        if (password != "" && password == passwordCheck) {
            return true;
        } else {
            alert("ํŒจ์Šค์›Œ๋“œ๊ฐ€ ์ผ์น˜ํ•˜์ง€ ์•Š์Šต๋‹ˆ๋‹ค.");
            return false;
        }
    }
</script>
  • onsubmit ์†์„ฑ์„ ์‚ฌ์šฉํ•˜์—ฌ ๋น„๋ฐ€๋ฒˆํ˜ธ์™€ ๋น„๋ฐ€๋ฒˆํ˜ธ ํ™•์ธ ์ž…๋ ฅ๋ž€์˜ ๊ฐ’์„ ๋น„๊ตํ•˜๋Š” ํ•จ์ˆ˜๋ฅผ ํ˜ธ์ถœํ•ฉ๋‹ˆ๋‹ค.

- submit ๋ฒ„ํŠผ ํด๋ฆญ ์ „์— ๋ฏธ๋ฆฌ ๋น„๋ฐ€๋ฒˆํ˜ธ ์ฒดํฌํ•˜๊ธฐ

<input oninput="passwordCheck()" id="pwdInput" >
<input oninput="passwordCheck()" id="pwdCheckInput" >
function passwordCheck() {
    const password = document.querySelector("#pwdInput").value;
    const passwordCheck = document.querySelector("#pwdCheckInput").value;

    if (password != passwordCheck) {
        //๋ฉ”์‹œ์ง€ ๋ณด์—ฌ์ฃผ๊ธฐ
        document.querySelector("#passwordMessage").textContent = "ํŒจ์Šค์›Œ๋“œ๊ฐ€ ์ผ์น˜ํ•˜์ง€ ์•Š์Šต๋‹ˆ๋‹ค.";
    } else {
        document.querySelector("#passwordMessage").textContent = "";
    }
}
  • oninput ์ด๋ฒคํŠธ๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ passwordCheck ํ•จ์ˆ˜๋ฅผ ํ˜ธ์ถœํ•ฉ๋‹ˆ๋‹ค.

๐Ÿ’Ÿ ํšŒ์› ๊ฐ€์ž… ์‹œ ์ด๋ฉ”์ผ ์ค‘๋ณต ํ™•์ธํ•˜๊ธฐ

ํšŒ์› ๊ฐ€์ผ ํ•  ๋•Œ ์ด๋ฉ”์ผ ์ค‘๋ณต์„ ํ™•์ธํ•˜๊ธฐ ์œ„ํ•ด์„œ๋Š” ํ™”๋ฉด์„ ์ด๋™ํ•˜์ง€ ์•Š๊ณ  ์ด๋ฉ”์ผ ์ค‘๋ณต ํ™•์ธ๋งŒ ํ•ด์ฃผ์–ด์•ผ ํ•ฉ๋‹ˆ๋‹ค. ์ด๋ ‡๊ฒŒ ํ•˜๊ธฐ ์œ„ํ•ด ajax๋ฅผ ์‚ฌ์šฉํ•ฉ๋‹ˆ๋‹ค.

ajax๋Š” ํŽ˜์ด์ง€๋ฅผ ๋‹ค์‹œ ๋กœ๋“œํ•˜์ง€ ์•Š๊ณ  ์„œ๋ฒ„ ํ†ต์‹ ์„ ์œ„ํ•ด ํด๋ผ์ด์–ธํŠธ๋ฅผ ์‹œ์ž‘ํ•˜๋Š” ๋ฉ”์†Œ๋“œ๋ฅผ ์ •์˜ํ•ฉ๋‹ˆ๋‹ค. ๋ถ€๋ถ„์ ์œผ๋กœ ํŽ˜์ด์ง€๋ฅผ ์—…๋ฐ์ดํŠธํ•  ์ˆ˜ ์žˆ๋Š” ๋ฐฉ๋ฒ•์„ ์ œ๊ณตํ•ฉ๋‹ˆ๋‹ค.

ajax๋ฅผ ์‚ฌ์šฉํ•˜๊ธฐ ์œ„ํ•ด ์ž๋ฐ”์ŠคํŠธ๋ฆฝํŠธ์˜ fetch ๋ฉ”์„œ๋“œ๋ฅผ ์‚ฌ์šฉํ•ฉ๋‹ˆ๋‹ค. ajax๋ฅผ ์‚ฌ์šฉํ•˜๊ธฐ ์œ„ํ•œ ์—ฌ๋Ÿฌ ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ๊ฐ€ ์กด์žฌ
ํŽ˜์ด์ง€๋ฅผ ๋‹ค์‹œ ๋กœ๋“œํ•˜์ง€ ์•Š๊ณ  , ๋ชจ๋ธ์— ๋‹ด์ง€ ์•Š๊ณ  view๋ฅผ ๊ฑฐ์น˜์ง€ ์•Š๊ณ  ์ผํ•œ ๊ฒฐ๊ณผ๋ฅผ ๋ฐ”๋กœ ์‘๋‹ต๋ฉ๋‹ˆ๋‹ค.


1. ์ด๋ฉ”์ผ ์ค‘๋ณต ํ™•์ธ ๋ฒ„ํŠผ ๋งŒ๋“ค๊ธฐ

<button onclick="emailCheck();" type="button" id="btnEmailCheck" ~>
  • ๋ฒ„ํŠผ์ด submit ํ•˜์ง€ ์•Š๋„๋ก type์„ button์œผ๋กœ ์ •ํ•ด์ค๋‹ˆ๋‹ค.
  • ๋ฒ„ํŠผ ํด๋ฆญ ์‹œ, emailCheck() ํ•จ์ˆ˜๋ฅผ ํ˜ธ์ถœํ•ฉ๋‹ˆ๋‹ค.

2. ์ปจํŠธ๋กค๋Ÿฌ

//์ด๋ฉ”์ผ check
@GetMapping("email")
@ResponseBody
public String emailCheck(String email) {
    String message = service.emailCheck(email);
    return message;
}
  • ์„œ๋น„์Šค์—์„œ ์ด๋ฉ”์ผ ์ค‘๋ณต ํ™•์ธ์„ ํ•˜๊ณ  ๋ฉ”์‹œ์ง€๋ฅผ ๋ฐ˜ํ™˜๋ฐ›์•„ ๋ฐ˜ํ™˜ํ•ฉ๋‹ˆ๋‹ค.
  • return์„ view๋กœ ๋ฐ›๋Š” ๊ฒƒ์ด ์•„๋‹ˆ๊ธฐ ๋•Œ๋ฌธ์— @ResponseBody๋ฅผ ์‚ฌ์šฉํ•ฉ๋‹ˆ๋‹ค.

3. ์„œ๋น„์Šค

public String emailCheck(String email) {
    Member member = mapper.selectByEmail(email);
    if (member == null) {
        //์‚ฌ์šฉ ๊ฐ€๋Šฅํ•œ ์ด๋ฉ”์ผ
        return "์‚ฌ์šฉ ๊ฐ€๋Šฅํ•œ ์ด๋ฉ”์ผ์ž…๋‹ˆ๋‹ค.";
    } else {
        // ์ด๋ฏธ ์กด์žฌํ•˜๋Š” ์ด๋ฉ”์ผ
        return "์ด๋ฏธ ์กด์žฌํ•˜๋Š” ์ด๋ฉ”์ผ์ž…๋‹ˆ๋‹ค.";
    }
}
  • mapper์—์„œ ๋ฐ›์€ ์ด๋ฉ”์ผ ์กด์žฌ ์œ ๋ฌด์— ๋”ฐ๋ผ ๋ฉ”์„ธ์ง€๋ฅผ ์ „๋‹ฌํ•ฉ๋‹ˆ๋‹ค.

4. mapper

@Select("SELECT * FROM member WHERE email = #{email}")
Member selectByEmail(String email);
  • ํ•ด๋‹น email์ด DB์— ์กด์žฌํ•˜๋Š”์ง€ ์กฐํšŒํ•ฉ๋‹ˆ๋‹ค.

5. emailCheck() ํ•จ์ˆ˜

async function emailCheck() {
    const emailValue = document.querySelector("#emailInput").value;
    const url = "/member/email?email=" + emailValue;

    //ajax ์š”์ฒญ
    const response = await fetch(encodeURI(url));

    // ์‘๋‹ต์ฒ˜๋ฆฌ
    // console.log(response.text());
    alert(await response.text())
}
  • ์ด๋ฉ”์ผ ์ž…๋ ฅ๋ž€์˜ id๊ฐ€ emailInput ์š”์†Œ์˜ ๊ฐ’์„ ๊ฐ€์ ธ์™€ /member/email?email=?๋กœ ์š”์ฒญ์„ ๋ณด๋‚ด๊ณ  ์ด๋ฉ”์ผ ๊ฐ’์€ ์ฟผ๋ฆฌ ๋ฌธ์ž์—ด๋กœ ์ „๋‹ฌํ•ฉ๋‹ˆ๋‹ค.
  • fetch() ํ•จ์ˆ˜๋Š” await ํ‚ค์›Œ๋“œ๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ๋น„๋™๊ธฐ์ ์œผ๋กœ ๊ธฐ๋‹ค๋ฆฌ๋ฉฐ ์„œ๋ฒ„๋กœ๋ถ€ํ„ฐ์˜ ์‘๋‹ต์€ reponse ๋ณ€์ˆ˜์— ์ €์žฅํ•ฉ๋‹ˆ๋‹ค.
  • response.text() ๋ฉ”์„œ๋“œ๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ํ…์ŠคํŠธ ํ˜•์‹์œผ๋กœ ์‘๋‹ต์„ ๊ฐ€์ ธ์™€ await ํ‚ค์›Œ๋“œ๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ๋น„๋™๊ธฐ์ ์œผ๋กœ ๊ธฐ๋‹ค๋ฆฐ ํ›„, alert() ํ•จ์ˆ˜๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ์‘๋‹ต ๋‚ด์šฉ์„ ์•Œ๋ฆผ์ฐฝ์œผ๋กœ ํ‘œ์‹œํ•ฉ๋‹ˆ๋‹ค.
  • async ํ•จ์ˆ˜ ์•ˆ์—์„œ await ํ‚ค์›Œ๋“œ๋ฅผ ์‚ฌ์šฉํ•˜๋ฉด ๋น„๋™๊ธฐ ์ž‘์—…์ด ์™„๋ฃŒ๋  ๋•Œ๊นŒ์ง€ ํ•จ์ˆ˜๊ฐ€ ์ผ์‹œ ์ค‘์ง€๋˜๋ฉฐ, ๊ทธ ๊ฒฐ๊ณผ๋ฅผ ๊ธฐ๋‹ค๋ฆฐ ํ›„ ๋‹ค์Œ ์ฝ”๋“œ๋ฅผ ์‹คํ–‰ํ•ฉ๋‹ˆ๋‹ค. ์ด๋ฅผ ํ†ตํ•ด ๋น„๋™๊ธฐ ์ฝ”๋“œ๋ฅผ ๋™๊ธฐ์‹์ฒ˜๋Ÿผ ์ž‘์„ฑํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.
    • async : ํ•จ์ˆ˜๋ฅผ ๋น„๋™๊ธฐ ํ•จ์ˆ˜๋กœ ์„ ์–ธํ•˜๋Š” ํ‚ค์›Œ๋“œ์ž…๋‹ˆ๋‹ค. ์ด ํ‚ค์›Œ๋“œ๋ฅผ ์‚ฌ์šฉํ•˜๋ฉด ํ•จ์ˆ˜ ๋‚ด์—์„œ await ํ‚ค์›Œ๋“œ๋ฅผ ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.
    • await : ๋น„๋™๊ธฐ ํ•จ์ˆ˜ ๋‚ด์—์„œ ์‚ฌ์šฉ๋˜๋ฉฐ, Promise๊ฐ€ ์ดํ–‰๋  ๋•Œ๊นŒ์ง€ ํ•จ์ˆ˜์˜ ์‹คํ–‰์„ ์ผ์‹œ ์ค‘์ง€ํ•ฉ๋‹ˆ๋‹ค. ์ดํ–‰๋œ ๊ฐ’์ด๋‚˜ ์ดํ–‰๋œ Promise์˜ ๊ฐ’์„ ๋ฐ˜ํ™˜ํ•ฉ๋‹ˆ๋‹ค.

emailCheck() ํ•จ์ˆ˜๋Š” ๋น„๋™๊ธฐ ํ•จ์ˆ˜๋กœ ์„ ์–ธ๋˜์–ด ์žˆ๊ณ , fetch() ํ•จ์ˆ˜์˜ ๊ฒฐ๊ณผ๋ฅผ ๊ธฐ๋‹ค๋ฆฌ๊ธฐ ์œ„ํ•ด await ํ‚ค์›Œ๋“œ๋ฅผ ์‚ฌ์šฉํ•˜๊ณ  ์žˆ์Šต๋‹ˆ๋‹ค. ์ด๋ ‡๊ฒŒ ํ•จ์œผ๋กœ์จ AJAX ์š”์ฒญ์ด ์™„๋ฃŒ๋  ๋•Œ๊นŒ์ง€ ํ•จ์ˆ˜๊ฐ€ ๋ฉˆ์ถ”๋ฉฐ, ์‘๋‹ต์„ ๋ฐ›์€ ํ›„์—์•ผ ๋‹ค์Œ ์ฝ”๋“œ๋ฅผ ์‹คํ–‰ํ•ฉ๋‹ˆ๋‹ค.

profile
๊ฐœ๋ฐœ์ž ์ค€๋น„์ƒ~

0๊ฐœ์˜ ๋Œ“๊ธ€