반응형

 

도서 'Spring in Action' 제 5판을 보고 책 내용과 그 이외의 부족한 부분을 채워가며 공부한 내용입니다.

 


키워드 : JPA


1. JPA

스프링 데이터 프로젝트

  • 여러개의 하위 프로젝트로 구성되는 다소 규모가 큰 프로젝트
    • 스프링 데이터 JPA : 관계형 데이터베이스 JPA 퍼시스턴스
    • 스프링 데이터 MongoDB : 몽고 문서형 데이터베이스의 퍼시스턴스
    • 스프링 데이터 Neo4 : Neo4j 그래프 데이터베이스의 퍼시스턴스
    • 스프링 데이터 레디스(Redis) : 레디스 키-값 스토어의 퍼시스턴스
    • 스프링 데이터 카산드라(Cassandra) : 카산드라 데이터베이스의 퍼시스턴스

<Ingredient>

@Data
@RequiredArgsConstructor
@NoArgsConstructor(access=AccessLevel.PRIVATE, force=true)
@Entity
public class Ingredient {
	
	@Id
	private final String id;
	private final String name;
	private final Type type;
	
	public static enum Type{
		WRAP, PROTEIN, VEGGIES, CHEESE, SAUCE
	}
}

<코드 분석>

  • @Entity
    • Ingredient를 JPA 개체(entity)로 선언
    • 속성에 반드시 @Id를 지정하여 이 속성이 데이터베이스의 개체를 고유하게 식별한다는 것을 나타내야함.
  • @NoArgsConstructor
    • JPA는 개체가 인자 없는 생성자를 가져야 함
    • 인자없는 생성자의 사용은 원치 않기 때문에 AccessLevel.PRIVATE 로 클래스 외부에서 사용할 수 없도록 함
    • 초기화에 필요한 final 속성이 있기 때문에 force 속성을 true로 설정

<Taco.java>

...

@Data
@Entity
@Table(name="TacoOrder")
public class Taco implements Serializable{
	
	private static final long serialVersionUID = 1L;
	
	@Id
	@GeneratedValue(strategy=GenerationType.AUTO)
	private Long id;
	private Date createdAt;
	
	@NotNull
	@Size(min=5, message="Name must be at least 5 characters long")
	private String name;
	
	@ManyToMany(targetEntity=Ingredient.class)
	@Size(min=1, message="You must choose at least 1 ingredient")
	private List<Ingredient> ingredients;
	
	@PrePersist
	void createdAt() {
		this.createdAt = new Date();
	}
}

<코드 분석>

  • Ingredient와 동일하게 Taco 클래스에도 @Entity가 지정되어 있으며, id 속성에는 @Id가 지정되어 있음
  • id속성에는 데이터베이스가 자동으로 생성해주는 ID값이 사용
    • 속성의 값이 GenerationType.AUTO로 설정된 @GeneratedValue 어노테이션이 지정
  • @ManyToMany
    • Taco와 Ingredient들 간의 관계를 선언
    • 1(Taco) 다 多(Ingredient) 관계
  • @PrePersist
    • createdAt()
      • Taco 객체가 저장되기 전에 createdAt 속성을 현재 일자와 시간으로 설정하는데 사용
@Data
@Entity
@Table(name="Taco_Order")
public class Order implements Serializable {
	
	private static final long serialVersionUID = 1L;
	@Id
	@GeneratedValue(strategy=GenerationType.AUTO)
	private Long id;
	private Date placedAt;
	
	@NotBlank(message="Name is required")
	private String deliveryName;
	
	@NotBlank(message="Street is required")
	private String deliveryStreet;
	
	@NotBlank(message="City is required")
	private String deliveryCity;
	
	@NotBlank(message="State is required")
	private String deliveryState;
	
	@NotBlank(message="Zip code is required")
	private String deliveryZip;
	
	@CreditCardNumber(message="Not a valid credit card number")
	private String ccNumber;
	
	@Pattern(regexp="^(0[1-9]|1[0-2])([\\/])([1-9][0-9])$",
			message="Must be formatted MM/YY")
	private String ccExpiration;
	
	@Digits(integer=3, fraction=0, message="Invalid CVV")
	private String ccCVV;
	
	@ManyToMany(targetEntity=Taco.class)
	private List<Taco> tacos = new ArrayList<>();
	
	public void addDesign(Taco design) {
		this.tacos.add(design);
	}
	
	@PrePersist
	void placedAt() {
		this.placedAt = new Date();
	}
}

<코드 분석>

  • @Table
    • Order객체가 데이터베이스의 Taco_Order에 저장

 

<IngredientRepository>

package tacos.data;

import org.springframework.data.repository.CrudRepository;
import tacos.Ingredient;

public interface IngredientRepository extends CrudRepository<Ingredient, String>{
	
}

<코드 분석>

  • CrudRepository
    • 데이터베이스의 CRUD(Create, Read, Update, Delete)
    • 첫번째 매개변수 = 리퍼지터리에 저장되는 개체 타입(Ingredient)
    • 두번째 매개변수 = 개체 ID 속성의 타입
    • 애플리케이션이 시작될 때 스프링 데이터 JPA가 각 인터페이스 구현체(클래스 등)를 자동으로 생성
      • 레퍼지터리들이 애당초 사용할 준비가 되어있다는 뜻
      • 그것들을 컨트롤러에 주입만 하면 됨.

<TacoRepository>

package tacos.data;

import org.springframework.data.repository.CrudRepository;
import tacos.Taco;

public interface TacoRepository extends CrudRepository<Taco, Long>{
}

 

 

<OrderRepository>

package tacos.data;

import org.springframework.data.repository.CrudRepository;
import tacos.Order;

public interface OrderRepository extends CrudRepository<Order, Long>{
}

 

 


참고 자료

1. 크레이그 월즈, Spring in Action, Fifth Edition(출판지 : 제이펍, 2020)

반응형

'Spring' 카테고리의 다른 글

JDBC - DataSource를 이용한 데이터 연결  (0) 2022.05.20
JDBC - 기본 구조와 API  (0) 2022.05.20
Spring 데이터로 작업하기 2  (0) 2022.05.18
Spring 데이터로 작업하기 1  (0) 2022.05.18
Spring 웹 애플리케이션 개발 3  (0) 2022.05.11

+ Recent posts