로그인 로그아웃 구현부터 시작했는데, 난 이미 해 두어서 글 작성할 때, 로그인 하지 않으면 불가능하게끔, 그리고 유저 아이디를 넘겨서 글 작성자가 누군지 알 수 있게 만드는 작업부터 했다.
// 로그인 상태 확인
if (session.getAttribute("loginUser") == null)
return ResultData.from("F-0", "로그인 상태가 아닙니다.");
우선 이 코드는 로그아웃할 때 썻던 걸 그냥 doWrite 메서드에서 가져왔고,
Session을 사용해서 memberId 데이터를 가져올 필요가 있었기에 login 메서드를 약간 손을 봐서 memberId데이터를 저장할 수 있게 만들었다.
@RequestMapping("/usr/member/doLogin")
@ResponseBody
public ResultData<Member> doLogin(HttpServletRequest request, String loginId, String loginPw) {
HttpSession session = request.getSession();
// 이미 로그인된 상태인지 확인
if (session.getAttribute("loginUser") != null) {
return ResultData.from("F-0", "이미 로그인된 상태입니다.");
}
if (Ut.isEmptyOrNull(loginId))
return ResultData.from("F-1", "아이디를 입력해주세요.");
if (Ut.isEmptyOrNull(loginPw))
return ResultData.from("F-2", "비밀번호를 입력해주세요.");
ResultData<Member> loginRd = memberService.doLogin(loginId, loginPw);
if (loginRd.isFail()) return loginRd;
// 로그인 성공 시 세션에 사용자 정보 저장
Member member = loginRd.getData1();
session.setAttribute("loginUser", member);
session.setAttribute("memberId", member.getId()); // memberId를 세션에 저장
return memberService.doLogin(loginId, loginPw);
}
처음에 Member로 저장한게 아니라 Session 자체에 저장을 해서 데이터를 가져오지 못했다. 그래서 Member에 저장하게끔 수정하고, getId로 값을 가져온다.
@RequestMapping("/usr/article/doWrite")
@ResponseBody
public ResultData doWrite(HttpSession session, String title, String body) {
// 로그인 상태 확인
if (session.getAttribute("loginUser") == null)
return ResultData.from("F-0", "로그인 상태가 아닙니다.");
if (Ut.isEmptyOrNull(title)) {
return ResultData.from("F-1", "제목을 입력해주세요");
}
if (Ut.isEmptyOrNull(body)) {
return ResultData.from("F-2", "내용을 입력해주세요");
}
Integer memberId = (Integer) session.getAttribute("memberId");
ResultData writeArticleRd = articleService.writeArticle(memberId ,title, body);
int id = (int) writeArticleRd.getData1();
Article article = articleService.getArticleById(id);
return ResultData.from(writeArticleRd.getResultCode(), writeArticleRd.getMsg(), article);
}
그리고 여기서 session을 불러와서 memberId를 꺼내오고,
public ResultData writeArticle(int memberId, String title, String body) {
articleRepository.writeArticle(memberId, title, body);
int id = articleRepository.getLastInsertId();
return ResultData.from("S-1", Ut.f("%d번 글이 등록되었습니다", id), id);
}
서비스에 전달하고
// @Insert("INSERT INTO article SET regDate = NOW(), updateDate = NOW(), title = #{title}, `body` = #{body}")
public void writeArticle(int memberId, String title, String body);
<insert id="writeArticle">
INSERT INTO article
SET regDate = NOW(),
updateDate = NOW(),
title = #{title},
`body` = #{body},
memberId = #{memberId}
</insert>
쿼리문에 memberId까지 추가해주면 된다.

로그인 상태가 아닐 때, 글 작성 막아둔 것도 잘 작동하고,


로그인 시 글 작성까지 해당 memberId를 남겨서 저장하는 것 까지 잘 작동한다.
다음으로는 게시물에 대한 권한 체크다. 삭제가 조금 더 접근하기 쉬워 보이니까 삭제부터 보자.
@RequestMapping("/usr/article/doDelete")
@ResponseBody
public ResultData<Integer> doDelete(HttpSession session , int id) {
// 로그인 상태 확인
boolean isLogined = false;
int loginedMemberId = 0;
if (session.getAttribute("loginedMemberId") != null) {
isLogined = true;
loginedMemberId = (int) session.getAttribute("loginedMemberId");
}
if (isLogined == false) {
return ResultData.from("F-A", "로그인 하고 써");
}
Article article = articleService.getArticleById(id);
if (article == null) {
return ResultData.from("F-1", Ut.f("%d번 게시물은 없습니다.", id));
}
// 권한체크
if (article.getMemberId() != loginedMemberId)
return ResultData.from("F-B", "게시물에 대한 권한이 없습니다.");
articleService.deleteArticle(id);
return ResultData.from("S-1", Ut.f("%d번 게시물 삭제되었습니다.", id));
}
게시물에서 MemberId를 가져와서 그 값이랑 session에서 가져온 memberId만 구분해주면 된다.
처음에 메서드를 만들어서 쿼리까지 쐈다가 강사님이 하시는 것 보고 바로 바꿨다.


만들고 보니까 코드 몇줄만 있으면 되는거라 같은 코드를 modify에도 넣고 하니까 잘 된다.
여기까지 하고 JSP를 셋팅했다.
JSTL을 알아보자.
JSTL(JavaServer Pages Standard Tag Library)은 JSP(JavaServer Pages)에서 사용되는 태그 라이브러리라고 한다.
JSTL 설정을 하는데 애를 좀 먹었다. 일단 설정을 끝내고 연결이 잘 되는 것도 확인했다.
@RequestMapping("/usr/article/list")
public String showList(Model model) {
List<Article> articles = articleService.getArticles();
model.addAttribute("articles", articles);
return "/usr/article/list";
}
기존 코드를 고치면서 List 먼저 화면 구성을 만지기 시작했고, Model 객체를 사용해서 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">
<link rel="stylesheet" type="text/css" href="${pageContext.request.contextPath}/resources/static/css/style.css">
<title>Article List</title>
</head>
<body>
<h1>게시물 목록</h1>
<hr/>
<table class="article-table">
<thead>
<tr>
<th>ID</th>
<th>Registration Date</th>
<th>Title</th>
<th>Member ID</th>
</tr>
</thead>
<tbody>
<c:forEach var="article" items="${articles}">
<tr>
<td>${article.id}</td>
<td>${article.regDate.substring(0, 10)}</td>
<td><a href="detail?id=${article.id}">${article.title}</a></td>
<td>${article.memberId}</td>
</tr>
</c:forEach>
</tbody>
</table>
</body>
</html>
그리고 JSTL을 사용해서 게시물 목록을 볼 수 있게 화면을 구성했다.

다음 과제는 타이틀을 클릭했을 때 해당 게시물의 상세보기다.
@RequestMapping("/usr/article/detail")
public String detail(Model model, int id) {
Article article = articleService.getArticleById(id);
if (article == null) {
// return ResultData.from("F-1", Ut.f("%d번 게시물은 없습니다.", id));
}
model.addAttribute("article", article);
return "/usr/article/detail";
}
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c"%>
<c:set var="pageTitle" value="게시물 상세보기"></c:set>
<%@ include file="../common/head.jspf"%>
<hr/>
<div class="article-detail">
<div class="detail-item">
<span class="label">번호:</span> ${article.id}
</div>
<div class="detail-item">
<span class="label">날짜:</span> ${article.regDate}
</div>
<div class="detail-item">
<span class="label">작성자:</span> ${article.memberId}
</div>
<div class="detail-item">
<span class="label">제목:</span> ${article.title}
</div>
<div class="detail-item">
<span class="label">내용:</span> ${article.body}
</div>
<div class="actions">
<a href="delete" class="btn">게시물 삭제</a> <a href="modify" class="btn">게시물
수정</a>
</div>
</div>
<div class="navigation">
<a href="../home/main" class="btn">메인 페이지로</a> <a href="list"
class="btn">리스트로 돌아가기</a>
</div>
</body>
</html>

잘 나온다.
JSP 코드를 보면 위가 날라가고 새로운 것이 들어와 있는게 보일건데, 공통된 헤드를 jspf파일로 나누어서 따로 관리한다.
<%@ 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">
<link rel="stylesheet" type="text/css"
href="${pageContext.request.contextPath}/resource/common.css">
<script src="/resource/common.js" defer="defer"></script>
<title>${pageTitle}</title>
</head>
<body>
<h1>${pageTitle}</h1>
이게 나눈 헤드.
여기까지!