본문 바로가기

Spring

240220 스프링 프로젝트

댓글 숫자가 3글자 미만일 시 댓글 작성 막기

function commentInsert() {
  let comment = document.querySelector("#commentTextarea");
  if (comment.value.length < 5) {
    Swal.fire({
      title: "글자가 너무 짧아요.",
      text: "5글자 이상으로 작성해주세요.",
      icon: "warning",
      timer: 1200,
      showConfirmButton: false
    });
    comment.focus();
    return false;
  }
}

 

스크립트 코드 작성, 처음에는 button 의 type 을 버튼으로 변경하고 onclick 을 넣었으나,

어제 한 것을 다시 보니,, form 에 onsubmit 옵션이 있었음

<form action="./commentWrite" method="post" onsubmit="commentInsert()">

 

이렇게 작성하고 넣었는데, 알림창은 잘 뜨지만 스크립트의 return false 가 잘 안먹음

 

왜 그런가 다시 보니..

onsubmit 에 return 을 넣어야만 return 이 작동

 

<form action="./commentWrite" method="post" onsubmit="return commentInsert()">

 

을 넣어서 return false 가 작동하는지 확인하니 잘 작동되는 것을 확인함

 

필수 입력값은 textarea 에 required 옵션을 넣어 진행

 

글 삭제하기

어제 만들어둔 delete 아이콘에 onclick 옵션을 달아둠

<div class="detailInfo">
  <span class="mname">${detail.mname }
    <i class="xi-document"></i>
    <i class="xi-close-circle-o" onclick="deletePost(${detail.board_no})"></i>
  </span><span class="bcount">${detail.board_count }</span>
</div>

 

스크립트로 가상 폼 진행하기

function deletePost(bno) {
  Swal.fire({
    title: "정말 삭제하시겠습니까?",
    text: "삭제를 진행하려면 아래 버튼을 눌러주세요.",
    icon: "warning",
    showCancelButton: true,
    confirmButtonColor: "#3085d6",
    cancelButtonColor: "#d33",
    confirmButtonText: "삭제하기",
    cancelButtonText: "취소"
  }).then((result) => {
    if(result.isConfirmed) {
      // java 에 삭제하라고 명령
      // 가상 form 을 post 로 보내기
      // let vform = $("<form name='vform' method='post' action='./postDel'></form>");
      let vform = $("<form></form>");
      vform.attr("name", "vform");
      vform.attr("method", "post");
      vform.attr("action", "./postDel");
      vform.append($("<input/>", {type:'hidden', name:'bno' value:${detail.board_no}}));
      vform.appendTo('body');
      vform.submit();
      Swal.fire({
        title: "삭제를 완료하였습니다.",
        icon: "success",
        showConfirmButton: false,
        timer: 2000
      });
    }    
  });
}

 

BoardController 부터 쭉 삭제 진행하기

@PostMapping("/postDel")
public String postDel(@RequestParam("bno") int no) {
  int result = boardService.postDel(no);
  if (result == 1) {
    return "redirect:/board";
  } else {
    return "redirect:/error";
  }
}

 

public int postDel(int no) {
  return boardRepository.postDel(no);
}

 

public int postDel(int no) {
  return sqlSession.update("board.postDel", no);
}

 

board-mapper 에 삭제 sql 문 적기

<update id="postDel" parameterType="Integer">
  update board set board_del = '0' where board_no = #{no}
</update>

 

해당 문구는 안에 글이 sql 문이라는 것을 알려주기 위해 다른 명령어를 추가할 수 있음

<update id="postDel" parameterType="Integer">
  <![CDATA[
    update board set board_del = '0' where board_no = #{no}
  ]]>
</update>

 

페이징 만들기

 

전자정부 페이징으로 진행해보기

 

egovframework:rte:ptl:view:paginationtag [eGovFrame]

전자정부프레임워크에서는 페이징 처리의 편의를 위해 <ui:pagination/> 태그를 제공한다. 페이징 기능을 사용할때 기능은 유사하지만 이미지나 라벨등의 포맷만 다양하게 사용하게 되는 경우가 있

www.egovframe.go.kr

 

root-context.xml 에 bean 추가

<bean id="textRenderer" class="egovframework.rte.ptl.mvc.tags.ui.pagination.DefaultPaginationRenderer" />
<bean id="imageRenderer" class="org.solbum.util.ImagePaginationRenderer" />
<bean id="paginationManager" class="egovframework.rte.ptl.mvc.tags.ui.pagination.DefaultPaginationManager">
  <property name="rendererType">
    <map>
      <entry key="image" value-ref="imageRenderer" />
      <entry key="text" value-ref="textRenderer" />
    </map>
  </property>
</bean>

 

imagePaginationRenderer 클래스 추가

package org.solbum.util;

import egovframework.rte.ptl.mvc.tags.ui.pagination.AbstractPaginationRenderer;

public class ImagePaginationRenderer extends AbstractPaginationRenderer {
  public ImagePaginationRenderer() {
    firstPageLabel = "<a href=\"#\" onclick=\"{0}({1}); return false;\"><image src=\"/easycompany/images/bt_first.gif\" border=0/></a>&#160;"; 
    previousPageLabel = "<a href=\"#\" onclick=\"{0}({1}); return false;\"><image src=\"/easycompany/images/bt_prev.gif\" border=0/></a>&#160;";
    currentPageLabel = "<strong>{0}</strong>&#160;";
    otherPageLabel = "<a href=\"#\" onclick=\"{0}({1}); return false;\">{2}</a>&#160;";
    nextPageLabel = "<a href=\"#\" onclick=\"{0}({1}); return false;\"><image src=\"/easycompany/images/bt_next.gif\" border=0/></a>&#160;";
    lastPageLabel = "<a href=\"#\" onclick=\"{0}({1}); return false;\"><image src=\"/easycompany/images/bt_last.gif\" border=0/></a>&#160;";
  }
}

 

이제 기존 /board 로 GetMapping 하던 곳에 작업 진행

먼저 글의 총 개수 받아오기

int totalRecordCount = boardService.totalRecordCount();

 

컨트롤러부터 -> board-mapper 로 쭉 이어주기

public int totalRecordCount() {
  return boardRepository.totalRecordCount();
}

public int totalRecordCount() {
  return sqlSession.selectOne("board.totalRecordCount");
}

<select id="totalRecordCount" resultType="Integer">
  select count(*) from board where board_del='1'
</select>

 

BoardController 의 board 수정하기

// 페이징 추가하기
@GetMapping("/board")
public String boardList(@RequestParam(value = "page", required = false) String no, Model model) {
  // page 가 안오면
  int currentPageNo = 1;
  if(util.str2Int(no) > 0) { // 여기 수정 필요
    currentPageNo = Integer.valueOf(no);
  }
    
  // 전체 글 수 받아오기
  int totalRecordCount = boardService.totalRecordCount();
//  System.out.println(totalRecordCount);
  // pagination
  PaginationInfo paginationInfo = new PaginationInfo();
  paginationInfo.setCurrentPageNo(currentPageNo); // 현재 페이지 번호
  paginationInfo.setRecordCountPerPage(15); // 한 페이지에 게시되는 게시글 수
  paginationInfo.setPageSize(10); // 페이지 리스트 사이즈
  paginationInfo.setTotalRecordCount(totalRecordCount); // 총 페이지 수
    
  model.addAttribute("list", boardService.boardList(paginationInfo.getFirstRecordIndex()));
  model.addAttribute("paginationInfo", paginationInfo);
  return "board";
}

 

board.jsp 에 태그 추가하기

<div>
  <ui:pagination paginationInfo="${paginationInfo}" type="text" jsFunction="linkPage" />
</div>

 

스크립트 추가, 페이지 넘어가기

function linkPage(page) {
  location.href="./board?page=" + page;
}

 

톰캣이 실행이 안되는 오류 발생, 서버 삭제 후 프로그램 재실행하니 정상 작동

 

로그인 만들기, menu.jsp 의 login 을 클릭하면 login.jsp 로 이동하도록 설정

LoginColtroller 생성

@Controller
public class LoginController {
  
  @GetMapping("/login")
  public String login() {
    return "login";
  }
}

 

login.jsp 만들기, 기존 index 를 복사하여 생성, section 하나만 남기고 나머지 삭제

로그인 레이아웃 만들기

<div class="loginBox">
  <div class="loginBoxTitle">Login</div>
    <form action="./login" method="post" onsubmit="return login()">
      <div class="loginIdBox input-form-box">
        <span>아이디</span> <input class="form-control " type="text" name="id" id="id" maxlength="15">
      </div>
      <div class="loginPwbox input-form-box">
        <span>비밀번호</span> <input class="form-control" type="password" name="pw" id="pw" maxlength="20">
      </div>
      <button class="btn btn-dark">회원가입</button>
      <button type="submit" class="btn btn-dark">로그인</button>
    </form>
</div>

 

해서 한글과 id, pw 길이 검사하기

<script type="text/javascript">
  function login() {
    // alert("버튼누름");
    let id = document.querySelector("#id");
    let pw = document.querySelector("#pw");
    const korean = /[ㄱ-ㅎ|ㅏ-ㅣ|가-힣]/;
    if (id.value.length < 5 || korean.test(id.value)) {
      alert("정확한 아이디를 입력하세요.");
      id.focus();
      return false;
    }
    if (pw.value.length < 6) {
      alert("정확한 비밀번호를 입력하세요.");
      pw.focus();
      return false;
    }
  }
</script>

 

LoginColtroller 에 Post 로 로그인 값 받기

@PostMapping("/login")
public String login(HttpServletRequest request) {
  String id = request.getParameter("id");
  String pw = request.getParameter("pw");
//  System.out.println("id : " + id + " pw : " + pw);
  return "redirect:/board";
}

 

이렇게 받아도 되지만, Login DTO 를 따로 만들기

@Getter
@Setter
public class LoginDTO {
  private int count, mgrade;
  private String mid, pw, mname, mdate;
}

 

Service, Repository 쭉 만들고

login-mapper, mybatis-config 에 설정하기

<mapper namespace="login">
	<select id="login" resultType="loginDTO" parameterType="loginDTO">
      <![CDATA[
      select count(*) as count, mname, mdate, mgrade 
      from member where mid=#{mid} and mpw=#{pw} and mgrade >= 5
      ]]>
	</select>
</mapper>

<typeAlias type="org.solbum.dto.LoginDTO" alias="loginDTO"/>

 

이제 컨트롤러에서 count 가 1 이면 세션 만들기

  @PostMapping("/login")
  public String login(HttpServletRequest request) {
//    System.out.println("id : " + loginDTO.getId() + " pw : " + loginDTO.getPw());
    LoginDTO dto = new LoginDTO();
    dto.setMid(request.getParameter("mid"));
    dto.setPw(request.getParameter("pw"));
    LoginDTO login = loginService.login(dto);
    System.out.println(login.getCount());
    if (login.getCount() == 1) {
      // 세션 만들기
      HttpSession session = request.getSession();
      session.setAttribute("mid", login.getMid());
      session.setAttribute("mname", login.getMname());
      return "redirect:/index";
    } else {
      return "redirect:/error";
    }
  }

 

저렇게 객체를 안만드려고 스프링 쓰는건데 객체를 최소한으로 만드려면 어떻게 해야할까..

 

로그아웃 만들기

@GetMapping("/logout")
public String logout(HttpServletRequest request) {
  HttpSession session = request.getSession();
  if (session.getAttribute("mid") != null) {
    session.removeAttribute("mid");
  }
  if (session.getAttribute("mname") != null) {
    session.removeAttribute("mname");
  }
  session.invalidate();
  return "redirect:/login";
}

 

menu.jsp 에 로그인 한 사용자는 이름, 로그아웃 버튼 이 보이고

로그인하지 않은 사람은 로그인 버튼 보이게 하기

<c:choose>
  <c:when test="${sessionScope.mname ne null }">
    <li class="nav-item"><a class="nav-link" href="./myInfo">${sessionScope.mname } 님</a></li>
    <li class="nav-item"><a class="nav-link" href="./logout">로그아웃</a></li>
  </c:when>
  <c:otherwise>
    <li class="nav-item"><a class="nav-link" href="./login">로그인</a></li>
  </c:otherwise>
</c:choose>

 

기존 글쓰기 이제 로그인 한 사용자 이름으로 글 작성하게 하기

service 쪽에 request 도 같이 보냄

  @PostMapping("/write")
  public String write(BoardDTO dto, HttpServletRequest request) {
    dto.setBoard_ip(request.getRemoteAddr());
    int result = boardService.write(dto, request);
    // 여기서 result 는 executeUpdate 의 결과 값과 같음
    
    if (result == 1) { // 작성이 제대로 안되면 else 로 이동
//      return "redirect:/board"; // List 로 가기
      return "redirect:/detail?no=" + dto.getBoard_no(); // 작성한 글로 가기
    } else {
      return "redirect:/error";
    }
  }

 

Service 에서 request 에서 세션을 받아 처리하기

public int write(BoardDTO dto, HttpServletRequest request) {
  HttpSession session = request.getSession();
  dto.setMid((String) session.getAttribute("mid"));
  return boardRepository.write(dto);
}

 

댓글은 controller 에서 전체 처리하기

@PostMapping("/commentWrite")
public String commentWrite(CommentDTO comment, HttpServletRequest request) {
//  System.out.println(comment.getNo() + " : " + comment.getComment());
  HttpSession session = request.getSession();
  comment.setMid((String) session.getAttribute("mid"));
  int result = boardService.commentWrite(comment);
  if (result == 1) {
    return "redirect:/detail?no=" + comment.getNo();
  } else {
    return "redirect:/error";
  }
}

 

menu.jsp 와 다른 페이지에서도 jstl 을 사용하기 때문에,

menu.jsp 에 들어있는 core 태그 문장을 삭제, 이럴 경우에는 import 방식을 변경해야 함

<c:import url="menu.jsp" /> 
<%@ include file="menu.jsp" %>

 

위 문장 대신 아래 문장으로 적어줘야 함

 

차이점은 아래 글로..

 

# <%@ include file="" %> <jsp:include> <c:import> 차이

# <%@ include file="" %> <jsp:include> <c:import> 차이 (1) 스크립...

blog.naver.com

 

 

'Spring' 카테고리의 다른 글

240222 스프링 프로젝트  (0) 2024.02.22
240221 스프링 프로젝트  (2) 2024.02.21
240219 스프링 프로젝트  (0) 2024.02.19
240216 스프링 프로젝트  (2) 2024.02.16
240215 스프링 프로젝트  (0) 2024.02.15