Notice
Recent Posts
Recent Comments
Link
| 일 | 월 | 화 | 수 | 목 | 금 | 토 |
|---|---|---|---|---|---|---|
| 1 | 2 | 3 | 4 | 5 | 6 | |
| 7 | 8 | 9 | 10 | 11 | 12 | 13 |
| 14 | 15 | 16 | 17 | 18 | 19 | 20 |
| 21 | 22 | 23 | 24 | 25 | 26 | 27 |
| 28 | 29 | 30 |
Tags
- continue문
- this예약어
- IntelliJ IDEA
- 메서드 오버로딩
- 접근제어지시자
- java변수
- JAVA객체지향
- 컴파일
- 메서드
- 자바 멀티스레딩
- 상수
- Thread
- 연관관계
- 집합관계
- function
- While
- 생성자
- for문
- 인텔리제이 한글 깨짐 해결법
- Java
- 포함관계
- JAVA기초
- break문
- 형 변환
- multi-threading
- 인텔리제이 기초 설정
- 반복문
- OPP개념
- Java데이터 타입
- 시스템 환경 변수 편집
Archives
- Today
- Total
최원종의 개발 블로그
V3-7 게시글 쓰기(로그인한 사용자와 게시글 연결) 본문

save-form.mustache파일
{{> layout/header}}
<div class="container p-5 flex-grow-1">
<div class="card">
<div class="card-header"><b>글쓰기 화면입니다</b></div>
<div class="card-body">
<form action="/board/save" method="post">
<div class="mb-3">
<input type="text" name="title" class="form-control" placeholder="enter title">
</div>
<div class="mb-3">
<textarea type="text" name="content" rows="5" class="form-control" placeholder="enter content"></textarea>
</div>
<button class="btn btn-primary">글쓰기 완료</button>
</form>
</div>
</div>
</div>
{{> layout/footer}}
BoardPersistRepository 코드
// 게시글 저장
@Transactional
public Board save(Board board) {
em.persist(board); // insert 처리 완료
return board;
}
BoardRequest 주요 메서드 상세 분석
toEntity(User user) - 객체 변환의 기술
역할: DTO에 담긴 정보를 바탕으로 DB에 저장할 Board 엔티티 객체를 생성함.
특징: 게시글은 반드시 작성자 정보가 필요하므로,
파라미터로 User 객체를 전달받아 연관관계를 맺어주는 것이 핵심.
장점: 서비스 레이어나 컨트롤러에서 복잡한 빌더 코드를 작성할 필요 없이
saveDTO.toEntity(sessionUser) 한 줄로 깔끔하게 처리가 가능.
② validate() - 데이터 무결성 보장
제목 검증: null 체크 및 공백 제거(trim()) 후 필수 입력 여부를 확인함.
내용 검증: 단순 존재 여부를 넘어 length() < 3 조건을 통해 최소 글자 수 제한 로직을 포함함.
BoardRequest 코드
package com.tenco.blog.board;
import com.tenco.blog.user.User;
import lombok.Builder;
import lombok.Data;
// 요청 데이터를 담는 DTO 클래스
// 컨트롤러.. 비즈니스 .. 데이터 계층 사이에서 데이터 전송 역할 객체
public class BoardRequest {
@Data
@Builder
public static class SaveDTO {
private String title;
private String content;
// 편의 기능 설계 가능
// DTO 에서 Entity로 변환해주는 편의 메서드
public Board toEntity(User user) {
return Board.builder()
.title(title)
.user(user)
.content(content)
.build();
}
public void validate() {
if(title == null || title.trim().isEmpty()) {
throw new IllegalArgumentException("제목은 필수입니다");
}
if(content == null || content.length() < 3) {
throw new IllegalArgumentException("내용은 3글자 이상 작성해야 합니다.");
}
}
}
// 내부 정적 클래스 게시글 수정 DTO 설계
@Data
public static class UpdateDTO {
private String username;
private String title;
private String content;
// 게시글 수정시 유효성 검사 편의 메서드
public void validate() {
if(username == null ||username.trim().isEmpty()) {
throw new IllegalArgumentException("작정자 이름은 필수입니다");
}
if(title == null || title.trim().isEmpty()) {
throw new IllegalArgumentException("제목은 필수입니다");
}
if(content== null || content.length() < 3) {
throw new IllegalArgumentException("내용은 3글자 이상 작성해야 합니다.");
}
}
}
}
BoardController 주요 메서드 분석
saveForm (GET): 작성 화면 제공
역할: 로그인된 사용자에게만 글쓰기 양식(board/save-form)을 보여줌.
흐름: 요청 접수 → 세션 확인 → (성공 시) 뷰 반환 / (실패 시) 로그인 페이지로 이동.
② saveProc (POST): 작성 기능 수행
사용자가 입력한 데이터를 실제로 DB에 저장하는 핵심 로직.
세션 재확인: 보안을 위해 데이터를 서버에 전송하는 시점에도 한 번 더 로그인 여부를 체크.
데이터 검증 (validate): 제목이나 내용이 비어있지 않은지 DTO 내부 로직으로 검사.
엔티티 변환 (toEntity): DTO 데이터를 엔티티로 바꾸되,
세션에서 가져온 sessionUser 정보를 함께 넘겨 "누가 썼는지" 연결해 줌.
예외 처리 (try-catch): 저장 중 오류가 발생하면 에러 메시지를 출력하고,
다시 작성 폼 페이지로 돌려보내 사용자가 내용을 수정할 수 있게 함.
BoardController 코드
/**
* 게시글 작성 화면 요청
* @return 페이지 반환
* 주소설계 : http://localhost:8080/board/save-form
*/
@GetMapping("/board/save-form")
public String saveForm(HttpSession httpSession) {
// 로그인 여부 체크 - 즉 로그인 한 사용자만 이 페이지 안에 들어 올 수 있음.
// 1. 인증 검사
User sessionUser = (User)httpSession.getAttribute("sessionUser");
if(sessionUser == null) {
return "redirect:/login-form";
}
return "board/save-form";
}
/**
* 게시글 작성 기능 요청
* @return 페이지 반환
* 주소설계 : http://localhost:8080/board/save-form
*/
@PostMapping("/board/save")
// 사용자 요청 -> HTTP 요청 메시지(Post)
public String saveProc(BoardRequest.SaveDTO saveDTO, HttpSession session) {
log.info("=== 게시글 저장 요청 ===");
// 이 요청 시 사용자가 로그인을 했다면 로그인 정보를 세션 메모리에서 가져오면 된다.
// 1. 세션에서 로그인한 사용자 정보 가져오기
User sessionUser = (User) session.getAttribute("sessionUser");
// 2. 로그인 여부 확인
if(sessionUser == null) {
return "redirect:/login-form";
}
try {
// 3. 로그인 된 사용자
// 3.1 유효성 검사
saveDTO.validate();
Board board = saveDTO.toEntity(sessionUser);
boardPersistRepository.save(board);
return "redirect:/";
} catch (Exception e) {
System.out.println("에러 발생 : " + e.getMessage());
return "board/save-form";
}
}
핵심 학습 포인트 정리
1. 세션 사용자 정보 활용
// 세션에서 로그인한 사용자 가져오기
// 로그인 여부 체크 - 즉 로그인 한 사용자만 이 페이지 안에 들어 올 수 있음.
// 1. 인증 검사
User sessionUser = (User)httpSession.getAttribute("sessionUser");
// 게시글과 사용자 연관관계 설정
public Board toEntity(User user) {
return Board.builder()
.title(title)
.user(user)
.content(content)
.build();
}
2. 연관관계 저장의 자동화
// Board 저장 시 user_id 외래키 자동 설정
// User 객체의 ID가 board_tb.user_id 컬럼에 저장됨
em.persist(board);'Spring boot 입문' 카테고리의 다른 글
| V3-9 게시글 수정(Dirty Checking과 권한 관리) (0) | 2026.05.13 |
|---|---|
| V3-8 게시글 삭제(인증 검사와 인가처리 ) (0) | 2026.05.13 |
| V3-6 연관 관계 및 N + 1 문제 확인 (0) | 2026.05.13 |
| V3-5 로그인& 로그아웃(세션 기반 사용자 인증) (1) | 2026.05.12 |
| V3-4 회원가입(사용자 등록과 JPA 영속성 활용) (0) | 2026.05.12 |
