기록방

[9일차] 9장 : CRUD와 SQL 쿼리 종합 본문

FrameWork/스프링

[9일차] 9장 : CRUD와 SQL 쿼리 종합

Soom_1n 2024. 6. 22. 16:46

길벗 IT도서에서 주관하는 코딩 자율학습단 8기 : Spring Boot 파트에 참여한 기록입니다 [ 목록 ]

9.1 JPA 로깅 설정하기

  • 쿼리(query) : DB에 정보를 요청하는 구문
  • 로깅(logging) : 시스템이 작동할 때 당시의 상태와 작동 정보를 기록하는 것
    • JPA 로깅 설정은 application.properties 파일에서 가능
server.servlet.encoding.force=true
spring.h2.console.enabled=true
spring.jpa.defer-datasource-initialization=true

**# JPA 로깅 설정
# 디버그 레벨로 쿼리 출력
logging.level.org.hibernate.SQL=DEBUG
# 쿼리 줄바꿈하기
spring.jpa.properties.hibernate.fomat_sql=true
# 물음표(??)로 나타나는 매개변수 값 보여 주기
logging.level.org.hibernate.type.descriptor.sql.BasicBinder=TRACE

# DB URL 설정
# 유니크 URL 생성하지 않기
spring.datasource.generate-unique-name=false
# 고정 URL 설정하기
spring.datasource.url=jdbc:h2:mem:testdb**
  • 로깅 레벨은 7단계 : INFO(레벨 3)을 선택하면, 그 이상 로그 레벨(4, 5, 6 7)의 로그를 보여준다.
    1. TRACE(레벨 1) : DEBUG 레벨보다 더 상세한 정보
    2. DEBUG(레벨 2) : 응용 프로그램을 디버깅하는 데 필요한 세부 정보
    3. INFO(레벨 3) : 응용 프로그램을 순조로운 진행 정보
    4. WARN(레벨 4) : 잠재적으로 유해한 상황 정보
    5. ERROR(레벨 5) : 응용 프로그램이 수행할 수 있는 정도의 오류 정보
    6. FATAL(레벨 6) : 응용 프로그램이 중단될 만한 심각한 오류 정보
    7. OFF(레벨 7) : 로깅 기능 해제
  • 디버그 모드로 바꾸면 DB 생성 과정이 보이고, 줄 바꿈을 켰음

  • h2 URL도 jdbc:h2:mem:testdb로 고정

9.2 SQL 쿼리 로그 확인하기

9.2.1 데이터 생성 시 : INSERT

데이터를 생성(Create)할 때 어떤 SQL 쿼리가 동작하는지 확인

id 자동 생성 전략 추가하기

  • 현재 새로운 게시글을 작성하면 오류가 남

  • data.sql 파일에서 3개의 더미 데이터를 넣는데, 새로운 데이터를 넣을 때 id값이 1부터 시작해서 중복이 일어나기 때문
  • 기본키(primary key) : 테이블에서 저장된 각 데이터를 유일하게 구분할 수 있도록 지정한 속성(여기서는 id가 기본키)
  • Article.java 수정
// @GeneratedValue // 자동 생성 기능 추가(숫자가 자동으로 매겨짐)
@GeneratedValue(strategy = GenerationType.IDENTITY) // DB가 id 자동 생성
private Long id;
  • data.sql의 입력 값으로 준 id도 제거

잘 적용 됨

  • 로그를 보면 어떤 쿼리가 동작했는지 보임

  • id는 default가 들어있는데, DB가 알아서 id를 생성한다는 뜻
  • content와 title의? 는 객체에 값이 들어가 있음

9.2.2 데이터 조회 시 : SELECT

데이터를 조회(Read_할 때 SQL 쿼리 동작 확인

 

1. localhost:8080/articles 게시글 실행하면 SELECT문이 수행됨

 

2. 4번 데이터 하나만 조회했을 경우

9.2.3 데이터 수정 시 : UPDATE

데이터를 수정(Update) 할 때 SQL 쿼리 동작 확인

  • 4번 게시 글 내용을 4444로 변경

9.2.4 데이터 삭제 시 : DELETE

데이터를 삭제(Delete) 할 때 SQL 쿼리 동작 확인

🚀 1분 퀴즈

  1. 다음 빈칸에 들어갈 SQL 쿼리를 작성하세요.
번호 SQL 구분 설명
1 INSERT INTO article(id, title, content)
VALUES(4, '제목4', '내용4');
데이터 생성 (Create) article 테이블에 데이터를 생성하는데, id, title, content를 특정 값으로 입력
2 SELECT id, email
FROM member
WHERE id = 3;
데이터 조회 (Read) member 테이블에서 id가 3인 데이터 중 id와 email 속성만 조회
3 UPDATE comment
SET nickname = ‘익명’
WHERE id = 1;
데이터 수정 (Update) comment 테이블에서 id가 1인 데이터를 수정하는데, nickname을 ‘익명’으로 변경
4 DELETE FROM orders
WHERE id = 4;
데이터 삭제 (Delete) orders 테이블에서 id가 4인 데이터 삭제

 

9.3 기본 SQL 쿼리 작성하기

9.3.1 coffee 테이블 만들기

create table coffee (
      id bigint generated by default as identity,
      name varchar(255),
      price integer,
      primary key (id)
  )

9.3.2 coffee 데이터 생성하기

insert 
into
    coffee
    (id, name, price) 
values
    (1, '아메리카노', 4100),
    (2, '라떼', 4600),
    (3, '모카', 5100),
    (4, '오늘의 커피', 3800)

9.3.3 coffee 데이터 조회하기

SELECT
    id, name, price
FROM
    coffee
WHERE
    id = 3;

 

9.3.4 coffee 데이터 수정하기

UPDATE
    coffee
SET
    price = 9900
WHERE
    id = 4;

 

9.3.5 coffee 데이터 삭제하기

DELETE
FROM
    coffee
WHERE
    id = 4;

 

🚀 1분 퀴즈

  1. 앞서 실습한 coffee 테이블에서 가격이 5,100원인 커피를 찾으려고 합니다. 이를 위한 쿼리를 작성해 보세요.
SELECT * FROM coffee WHERE price = 5100;

✅ 셀프 체크

  • 다음은 burgers 테이블의 생성 코드입니다.
CREATE TABLE burgers (
	id BIGINT GENERATED BY DEFAULT AS IDENTITY,
	name VARCHAR(50), -- 이름(최대 50글자)
	price INTEGER, -- 가격(숫자)
	gram INTEGER, -- 무게(숫자)
	kcal INTEGER, -- 열량(숫자)
	protein INTEGER, -- 단백질량(숫자)
	PRIMARY KEY (id)
);
  • bugers 테이블에서 데이터를 생성 및 조회해 다음과 같은 결과가 나오도록 SQL 쿼리를 작성하세요.
ID NAME  PRICE  GRAM  KCAL  PROTEIN
1 행운버거 골드 5300 222 540 25
2 트리플 치즈버거 6300 219 619 36
3 빅맥 5300 223 583 27

 

INSERT
INTO
	burgers
	(name, price, gram, kcal, protein)
VALUES
	('행운버거 골드', 5300, 222, 540, 25),
	('트리플 치즈버거', 6300, 219, 619, 36),
	('빅맥', 5300, 223, 583, 27);

SELECT * FROM burgers;

 

🏓 더 알아볼 내용

1. JPA 쿼리 로그

스프링 부트에서 로깅 레벨을 설정을 하지 않고 JPA를 사용하면 다음과 같이 아무것도 보이지 않습니다.

그런데 우리는 단순히 로깅 레벨을 설정하는 것이 아니라 JPA에서 어떤 SQL 문이 실행되는지 보고 싶습니다. 이를 위해서는 properties 파일에 다음 옵션을 설정해야 합니다.

Unset
spring.jpa.show-sql=true

이렇게 하고 서버를 재실행하는 순간,

바로 쿼리 로그가 보이기 시작합니다.

이 상태에서 HTTP 조회 요청을 보내면 다음과 같이 SELECT 문 쿼리가 정상적으로 찍히는 것을 확인할 수 있습니다.

🥕 멘토 Tip

로깅 레벨을 써봐서 알겠지만 처음 서버가 실행되고 나오는 대부분의 로깅은 INFO 수준입니다. 그렇기 때문에 에러를 디버깅할 경우 꼭 로깅 레벨을 debug로 설정해 주어야 합니다.

2. @GeneratedValue

@GeneratedValue 어노테이션은 기본키에 사용되는 어노테이션입니다.
코드 내부를 살펴보죠.

/**
* Provides for the specification of generation strategies for the
* values of primary keys.
*
* <p> The <code>GeneratedValue</code> annotation
* may be applied to a primary key property or field of an entity or
* mapped superclass in conjunction with the {@link Id} annotation.
* The use of the <code>GeneratedValue</code> annotation is only
* required to be supported for simple primary keys. Use of the
* <code>GeneratedValue</code> annotation is not supported for derived
* primary keys.
*
* <pre>
*
*     Example 1:
*
*     @Id
*     @GeneratedValue(strategy=SEQUENCE, generator="CUST_SEQ")
*     @Column(name="CUST_ID")
*     public Long getId() { return id; }
*
*     Example 2:
*
*     @Id
*     @GeneratedValue(strategy=TABLE, generator="CUST_GEN")
*     @Column(name="CUST_ID")
*     Long id;
* </pre>
*
* @see Id
* @see TableGenerator
* @see SequenceGenerator
*
* @since 1.0
*/
@Target({METHOD, FIELD})
@Retention(RUNTIME)

public @interface GeneratedValue {
    /**
        * (Optional) The primary key generation strategy
        * that the persistence provider must use to
        * generate the annotated entity primary key.
    */
    GenerationType strategy() default AUTO;

    /**
        * (Optional) The name of the primary key generator
        * to use as specified in the {@link SequenceGenerator}
        * or {@link TableGenerator} annotation.
        * <p> Defaults to the id generator supplied by persistence provider.
    */
    String generator() default "";
}
  • 여기서 재밌는 것은 GenerationType입니다. JPA의 GenerationType에는 총 5가지가 있습니다.
    • TABLE
    • SEQUENCE
    • IDENTITY
    • UUID
    • AUTO
  1. TABLE
    • 데이터베이스에 키 생성 전용 테이블을 하나 만들고 이를 사용해 기본키를 생성하는 방식입니다.
    • 여러 가지 고려해야 할 점이 많은 방식이죠. 이 옵션을 사용하면 다음과 같은 로그가 보입니다.
    • create table hibernate_sequences ( sequence_name varchar(255) not null, next_val bigint, primary key (sequence_name) )
  2. SEQUENCE
    • DB의 특별한 오브젝트 시퀀스를 사용해 기본키를 생성하는 방식입니다.
    • 이 전략은 DB가 반드시 시퀀스를 지원해야 합니다.
  3. IDENTITY
    • 기본키 생성을 DB에 위임하는 방식으로, 가장 흔하게 사용하는 방식입니다.
    • MySQL을 예로 들면 AUTO_INCREMENT 옵션을 사용하는 것과 같습니다.
  4. AUTO

 

  1. UUID

 

728x90