본문 바로가기
개인공부/스프링 부트 3 백엔드 개발자 되기

스프링 부트 - 3장_스프링부트3 구조 이해하기

by 응가1414 2023. 6. 25.

스프링 부트 3 구조 살펴보기

양 옆의 계층과 통신하는 구조를 따릅니다.

여기서 계층이라는 단어가 낯설게 느껴질 수 있다.

카페와 빵집으로 이해하는 계층

  1. 카페와 빵집이 있다고 생각하자.
  2. 카페는 커피를, 빵집은 빵을 판다.
  3. 그런데 필요한 경우 협업 관계를 맺어 어떤 손님이 커피를 사면 빵을 할인할 수도 있다.
    1. 이것이 계층간의 소통이다
  4. 빵집 알바생이 커피를 팔수는 없다.
    1. 계층은 서로 영향을 끼치지는 못한다.
  5. 계층관은 협력을 하되, 서로 영향을 끼치지는 못한다.

(사진)

프레젠테이션 계층 - Controller

  1. HTTP 요청을 받고 이 요청을 비즈니스 계층으로 전송하는 역활
  2. 컨트롤러는 앞서 살펴본 TestController 클래스와 같은 것을 말한다.

비즈니스 계층 - service, 비즈니스 로직

  1. 비즈니스 로직이란 서비스를 만들기 위한 로직을 말합니다.
  2. 이를테면 주문 서비스라고 한다면 주문 개수, 가격 등의 데이터를 처리학 위한 로직, 주문 처리를 하다가 발생하는 예외 처리 로직, 주문을 받거나 취소하는 것같이 프로세스를 구현하기 위한 로직
  3. 서비스가 비즈니스 계층의 역할을 한다.

퍼시스턴스 계층 - db 관련

  1. 모든 데이터베이스 관련 로직을 처리합니다.
  2. DAO는 데이터 베이스 계층과 상호작용하기 위한 객체라고 이해하면 된다.
  3. 리포지토리가 퍼시스턴스 계층의 역할을 한다.

컨트롤러, 서비스 리포지토리(퍼시스턴스)는 실제 구현을 위한 영역이라는 거다.

스프링 부트 프로젝트 디렉터리 구성하며 살펴보기

main

실제 코드를 작성하는 공간입니다.

프로젝트 실행에 필요한 소스 코드나 리소스 파일은 모두 이 폴더 않에 있다.

Test

프로젝트의 소스 코드를 테스트를 할 목적의 코드나 리소스 파일이 들어 있다.

build.gradle

빌드를 설정하는 파일

의존성이나 플러그인 설정 등과 같이 빌드에 필요한 설정을 할 때 사용

setting.gradle

빌드할 프로젝트의 정보를 설정하는 파일

이 이상의 저의 git을 보며 확인하시게요

스프링 부트 3 프로젝트 발전시키기

  1. 각 계층의 코드를 추가해보겠습니다.
  2. 프레젠테이션 계층 (controller), 비즈니스 계층 (service), 퍼시스턴스 계층 (리포지토리)
  3. 순서대로 코드를 추가.

build.gradle에 의존성 추가하기

  1. 스프링 부트용 JPA인 스프링 데이터 : JPA
  2. 로컬 환경과 테스트 환경에서 사용할 인메모리 데이터베이스인 : H2
  3. 반복 메서드 작성 작업을 줄여주는 라이브러리인 : 룸복
dependencies{
  ... 생략 ...
    // 스프링 데이터 JPA
    implementation 'org.springframework.boot:spring-boot-starter-data-jpa'
    runtimeOnly 'com.h2database:h2' // 인메모리 데이터 베이스
    compileOnly 'org.projectlombok' // 룸복 반복 메서드 작성 작업을 줄여주는 라이브러리
    annotationProcessor 'org.projectlombok:lombok' 
}

프레젠테이션, 서비스, 퍼시스턴스 계층 만들기

프레젠테이션 - Controller

TestController.java

@RestController
public class TestController {
  
  @Autowired // TestService 빈 주입
  TestService testService;
  
  @GetMapping("/test") // @GetMapping을 통해 URL "/test"과 HTTPS Get메서드의 매핑을 하는 라우터
  public List<Member> getAllMembers(){ // 서비스 계층의 로직을 통해 멤버들의 정보를 가져온다.
    List<Member> members = testService.getAllMember(); 
    return members; 
  }
}

비즈니스 계층 - 서비스 - 로직

TestService.java

@Service
public class TestService {
  
  @Autowired // 객체 주입
  MemberRepository memberRepository; // 빈 주입할 대상
  
  public List<Member> getAllMembers(){
    // Repository을 이용해 db에서의 멤버 정보를 얻는다.
    return memberRepository.findAll(); // 멤버 목록 얻기
  }
}

 

퍼시스턴트 - db 관련

Member.java (모델 클래스)

@NoArgsConstructor(access = AccessLever.PROTECTED)
@AllArgsConstructor
@Getter
@Entity
public class Member {
  @Id
  @GeneratedValue(strategy = GenerationType.IDENTITY)
  @Column(name = "id", updatable = false)
  private Long id;  // DB 테이블의 'id' 컬럼과 매칭
  
  @Column(name = "name", nullable = false)
  private String name;  // DB 테이블의 'name' 컬럼과 매칭
}

퍼시스턴트 계층의 Repository 클래스 작성

매핑 작업에는 인터페이스 파일이 피룡

// 퍼시스턴트 계층을 의미한다.
// Member 클래스와 db의 매핑을 해주는 역할
@Repository
public interface MemberRepository extends JpaRepository<Member, Long> {
}

작동확인하기 - sql, .yml 확인

작동을 확인 할것입니다.

저의 깃의 6월 25일자 커밋을 보면서 차근차근 해보시게요

  1. 애플리케이션을 실행할 때마다 SQL 문을 실행해 데이터베이스에 직접 데이터를 넣는데요
  2. 인메모리 데이터베이스 (h2)를 사용하기 있기 때문에 애플리케이션을 새로 실행 할 때 마다 데이터가 사라져서 매우 불편하다.
  3. 이를 해결하기 위해 애플리케이션을 실행할 때 원하는 데이터를 자동으로 넣는 작업

저장할 더미 데이터를 넣을 SQL 파일을 생성하겠습니다.

resources 디렉터리에 data.sql 파일을 생성

  1. SQL 문작성

data.sql

// data.sql
INSERT INTO member (id, name) VALUES (1, 'name 1')
INSERT INTO member (id, name) VALUES (2, 'name 2')
INSERT INTO member (id, name) VALUES (3, 'name 3')

  1. yml 파일 작성

Application.yml

# 스프링 부트 설정하룻 있는 application.yml
# 스프링 부트서버가 실행되면 자동으로 로딩
# 데이터베이스의 설정정보, 로깅 설정 정보
# 직접 설정을 정의할 때 사용
​
spring:
  jpa:
    show-sql: true   # 전송 쿼리 확인
    properties:
      hibernate:
        format_sql: true
    defer-datasource-initialization: true #  테이블 생성 후에 data.sql 실행

  1. postman을 이용한 HTTP 요청

스프링 부트 요청-응답 과정 한 방에 이해하기

HTTP 요청이 오면 어떤 과정을 처치며 실행되고 응답하는지 알아보자.

(그림 책)

  1. 그림을 보면 포스트맨에서 톰캣에 /test GET 요청을 한다.
    1. 그러면 이 요청은 스프링 부트 내로 이동하는데
  2. 이때 스프링 부트의 디스패처 서블릿이라는 녀석이 URL을 분석하고
    1. 이 요청을 처리할 수 ㅇ컨트롤러를 찾습니다.
    2. TestController가 /test라는 패스에 대한 GET 요청을 처리할 수 있는 getAllMembers() 메서드를 가지고 있고
    3. 디스패처 서블릿은 TestController에게 /test GET 요청을 전달합니다.
  3. 마침내 /test GET 요청을 처리할 수 있는 getALLMembers() 메서드와 이 요청이 매치됩니다.
    1. 그리고 getAllMembers() 메서드에는 비즈니스 계층과 퍼시스턴스 계층을 통하면서 필요한 데이터를 가져옵니다.
  4. 그러면 뷰 리졸버는 템플릿 엔진을 사용해 HTML 문서를 만들거나 JSON, XML 들의 데이터를 생성합니다.
  5. 그 결과 members를 return하고 그 데이터를 포스트맨에서 볼 수 있게 됩니다.