프로젝트 개요
Spring Boot 3.4.3과 JDBC를 활용하여 일정 관리 웹 서비스를 개발했습니다.
CRUD 및 필터링 기능이 포함된 일정 관리 시스템으로,
사용자가 일정을 등록하고 수정, 삭제할 수 있도록 설계
1️⃣ 기술 스택
✅ 백엔드
- Java 21: 최신 Java 기능 활용
- Spring Boot 3.4.3: 경량화된 애플리케이션 개발
- Spring Web: RESTful API 개발
- Spring Data JDBC: MySQL과의 데이터 연동
- Validation: 입력값 검증
- Lombok: 코드 간결화
✅ 데이터베이스
- MySQL
- 일정(schedule) 및 작성자(author) 테이블 설계
- 외래 키(FK) 관계 설정 (작성자와 일정 연관)
- ON DELETE CASCADE 적용 (작성자 삭제 시 일정도 삭제)
✅ 빌드 및 배포
- Gradle: 의존성 및 빌드 관리
- GitHub: 버전 관리
- Postman: API 테스트
2️⃣ 테이블 설계
📌 schedule (일정)
| 컬럼 명 | 타입 | 설명 |
| schedule_id | BIGINT | 일정 ID (PK) |
| title | VARCHAR(255) | 일정 제목 |
| content | VARCHAR(2000) | 일정 내용 |
| create_date | TIMESTAMP | 생성 날짜 (기본값: 현재 시간) |
| updated_date | TIMESTAMP | 수정 날짜 (자동 업데이트) |
| author_id | BIGINT | 작성자 ID (FK) |
| password | VARCHAR(255) | 일정 삭제 및 수정 시 필요한 비밀번호 |
📌 author (작성자)
| 컬럼명 | 타입 | 설명 |
| author_id | BIGINT | 작성자 ID (PK) |
| name | VARCHAR(100) | 작성자 이름 |
| VARCHAR(255) | 이메일 (유니크) | |
| created_date | TIMESTAMP | 생성 날짜 (기본값: 현재 시간) |
| updated_date | TIMESTAMP | 수정 날짜 (자동 업데이트) |
3️⃣ 기능 구현
✅ 일정 등록 (Create)
- SimpleJdbcInsert를 활용하여 일정 저장
- author_id가 존재하는지 검증 후 등록
- create_date, updated_date는 현재 시간으로 설정
더보기
@Override
public ScheduleResponseDto saveSchedule(Schedule schedule) {
SimpleJdbcInsert jdbcInsert = new SimpleJdbcInsert(jdbcTemplate);
jdbcInsert.withTableName("schedule").usingGeneratedKeyColumns("schedule_id");
Map<String, Object> parameters = new HashMap<>();
parameters.put("title", schedule.getTitle());
parameters.put("content", schedule.getContent());
parameters.put("author_id", schedule.getAuthorId());
parameters.put("password", schedule.getPassword());
parameters.put("create_date", schedule.getCreateDate());
parameters.put("updated_date", schedule.getUpdatedDate());
Number key = jdbcInsert.executeAndReturnKey(parameters);
Long generatedId = key.longValue();
return new ScheduleResponseDto(
generatedId,
schedule.getTitle(),
schedule.getContent(),
schedule.getUpdatedDate().toString(),
schedule.getAuthorId()
);
}
✅ 일정 목록 조회 (Read)
- JOIN을 활용하여 작성자 이름과 함께 일정 조회
- updated_date 기준 내림차순 정렬
더보기
@Override
public List<ScheduleAuthorDto> findAllSchedule() {
return jdbcTemplate.query(
"SELECT s.title, s.content, s.updated_date, a.name " +
"FROM schedule s " +
"JOIN author a ON s.author_id = a.author_id " +
"ORDER BY s.updated_date DESC",
scheduleAuthorRowMapper()
);
}
✅ 일정 수정 (Update)
- 일정 ID로 데이터를 조회한 후 비밀번호 검증
- updated_date 값을 현재 시간으로 변경
- 수정이 실패할 경우 예외 발생
더보기
@Override
public ScheduleAuthorDto updateSchedule(Long scheduleId, String title, String content, Long authorId, String password) {
Timestamp updatedTime = new Timestamp(System.currentTimeMillis());
Schedule schedule = scheduleRepository.findScheduleEntityById(scheduleId)
.orElseThrow(() -> new ResponseStatusException(HttpStatus.NOT_FOUND, "존재하지 않는 일정입니다."));
if (!schedule.getAuthorId().equals(authorId)) {
throw new ResponseStatusException(HttpStatus.FORBIDDEN, "작성자만 일정을 수정할 수 있습니다.");
}
if (!schedule.getPassword().equals(password)) {
throw new ResponseStatusException(HttpStatus.UNAUTHORIZED, "비밀번호가 일치하지 않습니다.");
}
int updatedRow = scheduleRepository.updatedSchedule(scheduleId, title, content, updatedTime, authorId);
if (updatedRow == 0) {
throw new ResponseStatusException(HttpStatus.NOT_FOUND, "일정 수정 실패");
}
return scheduleRepository.findScheduleByIdOrElseThrow(scheduleId);
}
✅ 일정 삭제 (Delete)
- 비밀번호 검증 후 삭제 수행
- 삭제 실패 시 예외 처리
더보기
@Override
public void deleteSchedule(Long scheduleId, String password) {
Schedule schedule = scheduleRepository.findScheduleEntityById(scheduleId)
.orElseThrow(() -> new ResponseStatusException(HttpStatus.NOT_FOUND, "존재하지 않는 일정입니다."));
if (!schedule.getPassword().equals(password)) {
throw new ResponseStatusException(HttpStatus.UNAUTHORIZED, "비밀번호가 일치하지 않습니다.");
}
int deleteRow = scheduleRepository.deleteSchedule(scheduleId);
if (deleteRow == 0) {
throw new ResponseStatusException(HttpStatus.NOT_FOUND, "일정 삭제 실패");
}
}
5️⃣ API 엔드포인트 정리
| HTTP Method | HTTP Method | URL기능 |
| POST | /schedules | 일정 생성 |
| GET | /schedules | 모든 일정 조회 |
| GET | /schedules/author/{authorId} | 특정 작성자의 일정 조회 |
| PUT | /schedules/{scheduleId} | 일정 수정 (비밀번호 필요) |
| DELETE | /schedules/{scheduleId} | 일정 삭제 (비밀번호 필요) |
6️⃣ 배운 점
✅ Spring Boot의 JDBC 활용법
- JdbcTemplate을 사용한 SQL 쿼리 실행
- SimpleJdbcInsert을 활용하여 Insert 간소화
- RowMapper를 활용한 객체 매핑
'TIL' 카테고리의 다른 글
| [250324 TIL] SOLID 원칙과 Spring의 객체 지향 설계 원칙 (2) | 2025.03.24 |
|---|---|
| [250321 TIL] 일정 관리 과제 완성 (3) | 2025.03.21 |
| [250318 TIL] 프레임워크, 라이브러리, Java 웹 기술의 역사 (3) | 2025.03.18 |
| [250317 TIL] 스프링 기초(네트워크) (1) | 2025.03.17 |
| [250314 TIL] 깃과 허깅페이스로 배포해보기 (3) | 2025.03.14 |