반응형
Spring JPA 란?
SQL을 쓰지 않고 데이터를 생성, 조회, 수정, 삭제 (CRUD) 할 수 있도록 해주는 번역기
프로젝트 구조는 다음과 같다.
1. Domain, Repository
- Domain - DB의 테이블 역할을 하는 클래스
- Repository - DB의 SQL 역할을 하는 인터페이스
먼저 Course.java 파일을 생성한다. 생성자를 직접 만들지 않고 Lombok을 사용하여 getter가 자동 생성 되도록 하였다.
@Getter // Lombok이 getter 자동 생성
@NoArgsConstructor // 기본 생성자를 대신 생성
@Entity // 그냥 클래스 아니고 DB의 테이블 역할을 하는 클래스라는 것을 알려줌
public class Course extends Timestamped{ // 생성일자, 수정일자 자동 갱신할 수 있도록 상속받음
@Id // ID 값, Primary Key로 사용하겠다는 의미
@GeneratedValue(strategy = GenerationType.AUTO) // id 생성시 자동으로 증가해줌
private Long id;
@Column(nullable = false) // 컬럼 값이 null이 아니고 반드시 값이 존재해야 함을 나타냄
private String title;
@Column(nullable = false)
private String tutor;
// 생성자
public Course(CourseRequestDto requestDto) {
this.title = requestDto.getTitle();
this.tutor = requestDto.getTutor();
}
public Course(String title, String tutor) {
this.title = title;
this.tutor = tutor;
}
public void update(CourseRequestDto requestDto) {
this.title = requestDto.getTitle();
this.tutor = requestDto.getTutor();
}
}
생성일자와 수정일자가 자동으로 갱신되도록 Timestamped 클래스를 만들어 상속받도록 하였다.
@MappedSuperclass // 상속했을 때, 컬럼으로 인식하게 함
@EntityListeners(AuditingEntityListener.class) // 생성/수정 시간을 자동으로 반영하도록 설정
public abstract class Timestamped { // abstract - 직접 구현을 불가능하고 상속으로만 쓸 수 있음을 명시
@CreatedDate // 생성 일자
private LocalDateTime createdAt;
@LastModifiedDate // 수정 일자
private LocalDateTime modifiedAt;
}
CourseRepository.java 파일을 생성한다. 이 파일은 꼭! 인터페이스로 생성해야한다. JPA를 사용하기 위해 JpaRepository<domain 클래스, id의 type> 을 상속받는다.
public interface CourseRepository extends JpaRepository<Course, Long> { // domain 클래스, id의 type
}
2. DTO (Data Transfer Object)
- 테이블에 값을 넣을 때 Course 클래스를 직접 사용하는 것은 좋지 않다. 그래서 완충재로 활용하는 것이 DTO 이다.
@Setter // Lombok이 getter, setter 자동 생성
@Getter
@RequiredArgsConstructor // 꼭 필요한 요소(final) 자동 생성
public class CourseRequestDto {
private final String title; // final 은 꼭 필요한 요소임을 명시하는 것, 값이 변경 될 수 없음
private final String tutor;
}
3. Service, Controller
- Controller - 가장 바깥 부분, 요청/응답을 처리한다
- Service - 중간 부분, 실제 중요한 동작이 많이 일어나는 부분이다
- Repo(Domain, Repository) - 가장 안쪽 부분, DB와 맞닿아 있다
CourseService.java 파일을 생성한다. Course 객체를 직접 변경하는 것은 좋지 않으므로 DTO를 사용해 값을 변경한다.
@RequiredArgsConstructor // 꼭 필요한 요소(final) 자동 생성
@Service // 이 클래스는 서비스임을 알려줌
public class CourseService {
private final CourseRepository courseRepository; // final 은 꼭 필요한 요소임을 명시하는 것, 값이 변경 될 수 없음
@Transactional // SQL 쿼리가 일어나야 함을 스프링에게 알려줌, 자동으로 DB에 업데이트 됨
public Long update(Long id, CourseRequestDto requestDto) {
// id로 Course 객체를 찾음. id에 해당하는 값이 없다면 메시지로 알려줌
Course course1 = courseRepository.findById(id).orElseThrow(
() -> new IllegalArgumentException("해당 아이디가 존재하지 않습니다.")
);
course1.update(requestDto); // 값 업데이트
return course1.getId();
}
}
CourseController.java 파일을 생성한다. Controller는 url로 들어온 요청과 응답을 처리한다.
@RequiredArgsConstructor // 꼭 필요한 요소(final) 자동 생성
@RestController // JSON 으로 응답하기 위한 RestController 라는 의미
public class CourseController {
private final CourseRepository courseRepository;
private final CourseService courseService;
// 등록된 전체 강의 목록 조회
@GetMapping("/api/courses")
public List<Course> getCourses() {
return courseRepository.findAll();
}
// 신규 강의 생성
@PostMapping("/api/courses")
public Course createCourse(@RequestBody CourseRequestDto requestDto) { // @RequestBody 는 응답받는 부분이라는 의미
// 저장하는 것은 Dto가 아니라 Course이니, Dto의 정보를 course에 담음
Course course = new Course(requestDto);
return courseRepository.save(course); // 값 저장
}
// 강의 정보 변경
@PutMapping("/api/courses/{id}") // {id}는 아이디 값이 오는데 유동적인 값이라는 의미
public Long updateCourse(@PathVariable Long id, @RequestBody CourseRequestDto requestDto) { // @PathVariable - {}로 감싸준 값을 가리킴
return courseService.update(id, requestDto); // 값 변경
}
// 강의 삭제
@DeleteMapping("/api/courses/{id}")
public Long deleteCourse(@PathVariable Long id) {
courseRepository.deleteById(id); // 값 삭제
return id;
}
}
기본적인 CRUD를 할 수 있는 코드는 작성이 완료되었다. ARC를 사용해 CRUD가 성공적으로 이루어지는지 확인할 수 있다. 프로젝트를 Run 한 다음 ARC에 요청할 url을 입력하면 된다. POST 로 데이터를 저장한 후 GET 으로 데이터를 조회해야 다음과 같은 화면을 볼 수 있다.
반응형
'Back-end > Spring' 카테고리의 다른 글
[SpringBoot] 4주차 스터디 ① (나만의 셀렉샵 만들기, 네이버 쇼핑 API) (0) | 2021.09.09 |
---|---|
[SpringBoot] 3주차 스터디 (메모장 만들기, Spring JPA) (0) | 2021.09.02 |
[SpringBoot] 1주차 스터디 (RestController) (0) | 2021.08.19 |
[SpringBoot] Spring Data JPA로 게시판 만들기(5) - JPA Auditing으로 생성시간/수정시간 자동화 (0) | 2020.11.22 |
[SpringBoot] Spring Data JPA로 게시판 만들기(4) - 수정/조회 API (0) | 2020.11.22 |