자바는 객체와 참조. DB는 FK로 각자의 연관관계 방식이 있는데, 두 방식의 차이를 해결하기 위해 JPA는 Java 어플리케이션 상에서
, DB의 연관관계
를 표현해주기위한 장치가 있다.
DB의 연관관계는 비즈니스 요구사항에 맞춰 이루어진다.
JPA가 제공하는 연관관계는 이러한 DB의 연관관계를 표현하기 위함이다.
JPA는 Entity 클래스 필드 위에 연관관계 @(어노테이션)을 설정해주면 된다.
연관관계 종류
: JPA를 편하게 쓰기 위해 스프링에서 JPA를 Wrapping.
스프링 개발자들이 JPA를 쓸 때 필수적으로 생성해야하나 예상가능하고 반복적인 코드
-> Spring Data JPA가 대신 작성.
Repository 인터페이스만 작성하면 필요한 구현은 스프링이 알아서한다.
// 1. 상품 생성
Product product = new Product(...);
productRepository.save(product);
// 2. 상품 전체 조회
List<Product> products = productRepository.findAll();
// 3. 상품 전체 개수 조회
long count = productRepository.count();
// 4. 상품 삭제
productRepository.delete(product);
.save() : 하나의 객체만 저장할 때 사용.
.saveAll() : 리스트형식처럼 되어있는걸 한번에 저장할 때 사용
.findAll : 전제 조회
.count() : 전체 '개수' 조회
.delete() : 삭제
public interface ProductRepository extends JpaRepository<Product, Long> {
// (1) 회원 ID 로 등록된 상품들 조회
List<Product> findAllByUserId(Long userId);
// (2) 상품명이 title 인 관심상품 1개 조회
Product findByTitle(String title);
// (3) 상품명에 word 가 포함된 모든 상품들 조회
List<Product> findAllByTitleContaining(String word);
// (4) 최저가가 fromPrice ~ toPrice 인 모든 상품들을 조회
List<Product> findAllByLpriceBetween(int fromPrice, int toPrice);
}
위처럼 조건에 따라서 사용할 수 있는 메서드들은 이미 다 구현이 되어있다.
Spring Data JPA 추가기능 구현방법
Optional<Member> findByMemberName(Strinf memberName)
이런 식으로 만들면클래스에 붙여주는 에너테이션
@Entity : 클래스를 Entity로 선언
@Getter : 값을 가져올때 쓰는 게터 추가
@NoArgsConstructor : 기본생성자 만들어줌
클래스 안에 넣어두는 애너테이션
@Id : 해당 엔티티의 주요 키(Primary Key, PK)가 될 값을 지정해주는 것.
Id만 사용할 시 기본키를 직접할당해야하는데 아래를 쓰면 안해도 된다.
@GeneratedValue(strategy = GenerationType.IDENTITY)
: @GeneratedValue는 기본키를 자동으로 생성해주는 어노테이션.
IDENTITY 전략은 기본 키 생성을 데이터베이스에 위임하는 것.
필드(컬럼,열)값은 private Long id; 처럼 클래스의 변수로 선언 id는 long으로!
join으로 orders 테이블에서 멤버랑 푸드테이블을 땡겨왔으면
멤버와 푸드에도 받아주는부분 넣어야 한다. 위의 mappedBy=
food에서 orders를 받는 컬럼을 만드는데 @OneToMany로 받는다.
음식 1개에 order 여러개가 될 수 있기 때문에?
컬럼은 ArrayList<Orders>로 설계
Repository는 인터페이스로 생성하고 extends JpaRepository<Food, Long>
JpaRepository를 상속하면서 제네릭스는 어떤 테이블과 연결할지 명시해야한다.
Long은 Id를 Long으로 지정했기때문에 그렇다.
JpaRepository<연결하려는테이블, Id타입>
상속으로 생성 수정시간 관리하기 Timestamped
Post클래스가 Timestamped(생성 수정시각 필드로)를 상속하는 것만으로도
DB에 추가가 될때 자동으로 시각이 기록된다.
Entity를 만들 때 Timestamped 객체를 만들고
@Getter
@MappedSuperclass
@EntityListeners(AuditingEntityListener.class)
public class Timestamped {
@CreatedDate
@Column(updatable = false)
private LocalDateTime createdAt;
@LastModifiedDate
@Column
private LocalDateTime modifiedAt;
}
public class Post extends Timestamped 처럼 테이블에 상속받으면
상속받은 Entity 객체는 항상 Timestamped의 칼럼을 가진다.
매번 등록해야하는 번거로움을 덜 수 있다.